]> git.sur5r.net Git - freertos/commitdiff
Add FAT SL code and demo project.
authorrichardbarry <richardbarry@1d2547de-c912-0410-9cb9-b8ca96c0e9e2>
Tue, 30 Apr 2013 20:37:52 +0000 (20:37 +0000)
committerrichardbarry <richardbarry@1d2547de-c912-0410-9cb9-b8ca96c0e9e2>
Tue, 30 Apr 2013 20:37:52 +0000 (20:37 +0000)
git-svn-id: https://svn.code.sf.net/p/freertos/code/trunk@1879 1d2547de-c912-0410-9cb9-b8ca96c0e9e2

51 files changed:
FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/ConfigurationFiles/FreeRTOSConfig.h [new file with mode: 0644]
FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/ConfigurationFiles/config_fat_sl.h [new file with mode: 0644]
FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/ConfigurationFiles/config_mdriver_ram.h [new file with mode: 0644]
FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/File-Releated-CLI-commands.c [new file with mode: 0644]
FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/File-system-demo.c [new file with mode: 0644]
FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/FreeRTOS_Plus_FAT_SL_with_CLI.sln [new file with mode: 0644]
FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/READ_ME.url [new file with mode: 0644]
FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/Run-time-stats-utils.c [new file with mode: 0644]
FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/Sample-CLI-commands.c [new file with mode: 0644]
FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/UDPCommandServer.c [new file with mode: 0644]
FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/WIN32.vcxproj [new file with mode: 0644]
FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/WIN32.vcxproj.filters [new file with mode: 0644]
FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/WIN32.vcxproj.user [new file with mode: 0644]
FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/main.c [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/ReadMe.url [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/api/api_mdriver.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/api/api_mdriver_ram.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/api/fat_sl.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/config/config_fat_sl_template.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/config/config_mdriver_ram_template.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/dir.c [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/dir.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/drv.c [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/drv.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/f_lock.c [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/f_lock.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/fat.c [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/fat.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/file.c [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/file.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/util.c [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/util.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/util_sfn.c [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/util_sfn.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/volume.c [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/volume.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/test/test.c [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/test/test.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/media-drv/ram/ramdrv_f.c [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/psp/include/psp_rtc.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/psp/include/psp_string.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/psp/target/fat_sl/psp_test.c [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/psp/target/fat_sl/psp_test.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/psp/target/rtc/psp_rtc.c [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/version/ver_fat_sl.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/version/ver_mdriver.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/version/ver_mdriver_ram.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/version/ver_psp_fat_sl.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/version/ver_psp_rtc.h [new file with mode: 0644]
FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/version/ver_psp_string.h [new file with mode: 0644]
FreeRTOS/Source/include/FreeRTOS.h

diff --git a/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/ConfigurationFiles/FreeRTOSConfig.h b/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/ConfigurationFiles/FreeRTOSConfig.h
new file mode 100644 (file)
index 0000000..04793be
--- /dev/null
@@ -0,0 +1,171 @@
+/*\r
+    FreeRTOS V7.4.0 - Copyright (C) 2013 Real Time Engineers Ltd.\r
+\r
+    FEATURES AND PORTS ARE ADDED TO FREERTOS ALL THE TIME.  PLEASE VISIT\r
+    http://www.FreeRTOS.org TO ENSURE YOU ARE USING THE LATEST VERSION.\r
+\r
+    ***************************************************************************\r
+     *                                                                       *\r
+     *    FreeRTOS tutorial books are available in pdf and paperback.        *\r
+     *    Complete, revised, and edited pdf reference manuals are also       *\r
+     *    available.                                                         *\r
+     *                                                                       *\r
+     *    Purchasing FreeRTOS documentation will not only help you, by       *\r
+     *    ensuring you get running as quickly as possible and with an        *\r
+     *    in-depth knowledge of how to use FreeRTOS, it will also help       *\r
+     *    the FreeRTOS project to continue with its mission of providing     *\r
+     *    professional grade, cross platform, de facto standard solutions    *\r
+     *    for microcontrollers - completely free of charge!                  *\r
+     *                                                                       *\r
+     *    >>> See http://www.FreeRTOS.org/Documentation for details. <<<     *\r
+     *                                                                       *\r
+     *    Thank you for using FreeRTOS, and thank you for your support!      *\r
+     *                                                                       *\r
+    ***************************************************************************\r
+\r
+\r
+    This file is part of the FreeRTOS distribution.\r
+\r
+    FreeRTOS is free software; you can redistribute it and/or modify it under\r
+    the terms of the GNU General Public License (version 2) as published by the\r
+    Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+\r
+    >>>>>>NOTE<<<<<< The modification to the GPL is included to allow you to\r
+    distribute a combined work that includes FreeRTOS without being obliged to\r
+    provide the source code for proprietary components outside of the FreeRTOS\r
+    kernel.\r
+\r
+    FreeRTOS is distributed in the hope that it will be useful, but WITHOUT ANY\r
+    WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS\r
+    FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more\r
+    details. You should have received a copy of the GNU General Public License\r
+    and the FreeRTOS license exception along with FreeRTOS; if not itcan be\r
+    viewed here: http://www.freertos.org/a00114.html and also obtained by\r
+    writing to Real Time Engineers Ltd., contact details for whom are available\r
+    on the FreeRTOS WEB site.\r
+\r
+    1 tab == 4 spaces!\r
+\r
+    ***************************************************************************\r
+     *                                                                       *\r
+     *    Having a problem?  Start by reading the FAQ "My application does   *\r
+     *    not run, what could be wrong?"                                     *\r
+     *                                                                       *\r
+     *    http://www.FreeRTOS.org/FAQHelp.html                               *\r
+     *                                                                       *\r
+    ***************************************************************************\r
+\r
+\r
+    http://www.FreeRTOS.org - Documentation, books, training, latest versions, \r
+    license and Real Time Engineers Ltd. contact details.\r
+\r
+    http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+    including FreeRTOS+Trace - an indispensable productivity tool, and our new\r
+    fully thread aware and reentrant UDP/IP stack.\r
+\r
+    http://www.OpenRTOS.com - Real Time Engineers ltd license FreeRTOS to High \r
+    Integrity Systems, who sell the code with commercial support, \r
+    indemnification and middleware, under the OpenRTOS brand.\r
+    \r
+    http://www.SafeRTOS.com - High Integrity Systems also provide a safety \r
+    engineered and independently SIL3 certified version for use in safety and \r
+    mission critical applications that require provable dependability.\r
+*/\r
+\r
+#ifndef FREERTOS_CONFIG_H\r
+#define FREERTOS_CONFIG_H\r
+\r
+/*-----------------------------------------------------------\r
+ * Application specific definitions.\r
+ *\r
+ * These definitions should be adjusted for your particular hardware and\r
+ * application requirements.\r
+ *\r
+ * THESE PARAMETERS ARE DESCRIBED WITHIN THE 'CONFIGURATION' SECTION OF THE\r
+ * FreeRTOS API DOCUMENTATION AVAILABLE ON THE FreeRTOS.org WEB SITE.\r
+ * http://www.freertos.org/a00110.html\r
+ *\r
+ * The bottom of this file contains some constants specific to running the UDP\r
+ * stack in this demo.  Constants specific to FreeRTOS+UDP itself (rather than\r
+ * the demo) are contained in FreeRTOSIPConfig.h.\r
+ *----------------------------------------------------------*/\r
+\r
+#define configUSE_PREEMPTION                   1\r
+#define configMAX_PRIORITIES                   ( ( unsigned portBASE_TYPE ) 7 )\r
+#define configTICK_RATE_HZ                             ( 1000 ) /* In this non-real time simulated environment the tick frequency has to be at least a multiple of the Win32 tick frequency, and therefore very slow. */\r
+#define configMINIMAL_STACK_SIZE               ( ( unsigned short ) 60 ) /* In this simulated case, the stack only has to hold one small structure as the real stack is part of the Win32 thread. */\r
+#define configTOTAL_HEAP_SIZE                  ( ( size_t ) ( 32U * 1024U ) )\r
+#define configMAX_TASK_NAME_LEN                        ( 7 )\r
+#define configUSE_TRACE_FACILITY               1\r
+#define configUSE_16_BIT_TICKS                 0\r
+#define configIDLE_SHOULD_YIELD                        1\r
+#define configUSE_CO_ROUTINES                  0\r
+#define configUSE_MUTEXES                              1\r
+#define configUSE_RECURSIVE_MUTEXES            1\r
+#define configQUEUE_REGISTRY_SIZE              0\r
+#define configUSE_APPLICATION_TASK_TAG 0\r
+#define configUSE_COUNTING_SEMAPHORES  1\r
+#define configUSE_ALTERNATIVE_API              0\r
+\r
+/* Hook function related definitions. */\r
+#define configUSE_TICK_HOOK                            0\r
+#define configUSE_IDLE_HOOK                            1\r
+#define configUSE_MALLOC_FAILED_HOOK   1\r
+#define configCHECK_FOR_STACK_OVERFLOW 0 /* Not applicable to the Win32 port. */\r
+\r
+/* Software timer related definitions. */\r
+#define configUSE_TIMERS                               1\r
+#define configTIMER_TASK_PRIORITY              ( configMAX_PRIORITIES - 1 )\r
+#define configTIMER_QUEUE_LENGTH               5\r
+#define configTIMER_TASK_STACK_DEPTH   ( configMINIMAL_STACK_SIZE * 2 )\r
+\r
+/* Run time stats gathering definitions. */\r
+unsigned long ulGetRunTimeCounterValue( void );\r
+void vConfigureTimerForRunTimeStats( void );\r
+#define configGENERATE_RUN_TIME_STATS  1\r
+#define portCONFIGURE_TIMER_FOR_RUN_TIME_STATS() vConfigureTimerForRunTimeStats()\r
+#define portGET_RUN_TIME_COUNTER_VALUE() ulGetRunTimeCounterValue()\r
+\r
+/* Co-routine definitions. */\r
+#define configUSE_CO_ROUTINES                  0\r
+#define configMAX_CO_ROUTINE_PRIORITIES ( 2 )\r
+\r
+/* Set the following definitions to 1 to include the API function, or zero\r
+to exclude the API function. */\r
+#define INCLUDE_vTaskPrioritySet                       1\r
+#define INCLUDE_uxTaskPriorityGet                      1\r
+#define INCLUDE_vTaskDelete                                    1\r
+#define INCLUDE_vTaskCleanUpResources          0\r
+#define INCLUDE_vTaskSuspend                           1\r
+#define INCLUDE_vTaskDelayUntil                                1\r
+#define INCLUDE_vTaskDelay                                     1\r
+#define INCLUDE_uxTaskGetStackHighWaterMark    1\r
+#define INCLUDE_xTaskGetSchedulerState         1\r
+#define INCLUDE_xTimerGetTimerTaskHandle       0\r
+#define INCLUDE_xTaskGetIdleTaskHandle         0\r
+#define INCLUDE_xQueueGetMutexHolder           1\r
+\r
+/* Assert call defined for debug builds. */\r
+#ifdef _DEBUG\r
+       extern void vAssertCalled( const char *pcFile, unsigned long ulLine );\r
+       #define configASSERT( x ) if( ( x ) == 0 ) vAssertCalled( __FILE__, __LINE__ )\r
+#endif /* _DEBUG */\r
+\r
+\r
+\r
+/* Application specific definitions follow. **********************************/\r
+\r
+/* The UDP port to use for incoming command inputs.  The outgoing port is\r
+set to ( configUDP_CLI_PORT_NUMBER + 1 ). */\r
+#define configUDP_CLI_PORT_NUMBER      5001\r
+\r
+/* The size of the global output buffer that is available for use when there\r
+are multiple command interpreters running at once (for example, one on a UART\r
+and one on TCP/IP).  This is done to prevent an output buffer being defined by\r
+each implementation - which would waste RAM.  In this case, there is only one\r
+command interpreter running, and it has its own local output buffer, so the\r
+global buffer is just set to be one byte long as it is not used and should not\r
+take up unnecessary RAM. */\r
+#define configCOMMAND_INT_MAX_OUTPUT_SIZE 1\r
+\r
+#endif /* FREERTOS_CONFIG_H */\r
diff --git a/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/ConfigurationFiles/config_fat_sl.h b/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/ConfigurationFiles/config_fat_sl.h
new file mode 100644 (file)
index 0000000..373d780
--- /dev/null
@@ -0,0 +1,67 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * FreeRTOS+FAT SL is an complementary component provided to Real Time Engineers\r
+ * Ltd. by HCC Embedded for use with FreeRTOS.  It is not, in itself, part of\r
+ * the FreeRTOS kernel.  FreeRTOS+FAT SL is licensed separately from FreeRTOS,\r
+ * and uses a different license to FreeRTOS.  FreeRTOS+FAT SL uses a dual\r
+ * license model, information on which is provided below:\r
+ *\r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified and distributed\r
+ * without charge provided the user adheres to version two of the GNU General\r
+ * Public license (GPL) and does not remove the copyright notice or this text.\r
+ * The GPL V2 text is available on the gnu.org web site, and on the following\r
+ * URL: http://www.FreeRTOS.org/gpl-2.0.txt\r
+ *\r
+ * - Commercial licensing -\r
+ * Businesses and individuals who wish to incorporate FreeRTOS+FAT SL into\r
+ * proprietary software for redistribution in any form must first obtain a\r
+ * commercial license - and in-so-doing support the maintenance, support and\r
+ * further development of the FreeRTOS+FAT SL product.  Commercial licenses can\r
+ * be obtained from http://shop.freertos.org and do not require any source files\r
+ * to be changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef _CONFIG_FAT_SL_H\r
+#define _CONFIG_FAT_SL_H\r
+\r
+#include "../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+#include "../api/api_mdriver.h"\r
+\r
+#ifdef __cplusplus\r
+extern "C" {\r
+#endif\r
+\r
+\r
+/**************************************************************************\r
+**\r
+**  FAT SL user settings\r
+**\r
+**************************************************************************/\r
+#define F_SECTOR_SIZE           512u  /* Disk sector size. */\r
+#define F_FS_THREAD_AWARE       1     /* Set to one if the file system will be access from more than one task. */\r
+#define F_MAXPATH               64    /* Maximum length a file name (including its full path) can be. */\r
+#define F_MAX_LOCK_WAIT_TICKS   20    /* The maximum number of RTOS ticks to wait when attempting to obtain a lock on the file system when F_FS_THREAD_AWARE is set to 1. */\r
+\r
+#ifdef __cplusplus\r
+}\r
+#endif\r
+\r
+#endif /* _CONFIG_FAT_SL_H */\r
+\r
diff --git a/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/ConfigurationFiles/config_mdriver_ram.h b/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/ConfigurationFiles/config_mdriver_ram.h
new file mode 100644 (file)
index 0000000..1c3ce96
--- /dev/null
@@ -0,0 +1,52 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * FreeRTOS+FAT SL is an complementary component provided to Real Time Engineers\r
+ * Ltd. by HCC Embedded for use with FreeRTOS.  It is not, in itself, part of\r
+ * the FreeRTOS kernel.  FreeRTOS+FAT SL is licensed separately from FreeRTOS,\r
+ * and uses a different license to FreeRTOS.  FreeRTOS+FAT SL uses a dual\r
+ * license model, information on which is provided below:\r
+ *\r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified and distributed\r
+ * without charge provided the user adheres to version two of the GNU General\r
+ * Public license (GPL) and does not remove the copyright notice or this text.\r
+ * The GPL V2 text is available on the gnu.org web site, and on the following\r
+ * URL: http://www.FreeRTOS.org/gpl-2.0.txt\r
+ *\r
+ * - Commercial licensing -\r
+ * Businesses and individuals who wish to incorporate FreeRTOS+FAT SL into\r
+ * proprietary software for redistribution in any form must first obtain a\r
+ * commercial license - and in-so-doing support the maintenance, support and\r
+ * further development of the FreeRTOS+FAT SL product.  Commercial licenses can\r
+ * be obtained from http://shop.freertos.org and do not require any source files\r
+ * to be changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef _CONFIG_MDRIVER_RAM_H_\r
+#define _CONFIG_MDRIVER_RAM_H_\r
+\r
+#include "../version/ver_mdriver_ram.h"\r
+#if VER_MDRIVER_RAM_MAJOR != 1 || VER_MDRIVER_RAM_MINOR != 2\r
+ #error Incompatible MDRIVER_RAM version number!\r
+#endif\r
+\r
+#define MDRIVER_RAM_SECTOR_SIZE   512       /* Sector size */\r
+\r
+#define MDRIVER_RAM_VOLUME0_SIZE  (128 * 1024) /* defintion for size of ramdrive0 */\r
+\r
+#define MDRIVER_MEM_LONG_ACCESS   1         /* set this value to 1 if 32bit access available */\r
+\r
+#endif /* ifndef _CONFIG_MDRIVER_RAM_H_ */\r
+\r
diff --git a/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/File-Releated-CLI-commands.c b/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/File-Releated-CLI-commands.c
new file mode 100644 (file)
index 0000000..0e36e7a
--- /dev/null
@@ -0,0 +1,618 @@
+/*\r
+    FreeRTOS V7.4.0 - Copyright (C) 2013 Real Time Engineers Ltd.\r
+\r
+    FEATURES AND PORTS ARE ADDED TO FREERTOS ALL THE TIME.  PLEASE VISIT\r
+    http://www.FreeRTOS.org TO ENSURE YOU ARE USING THE LATEST VERSION.\r
+\r
+    ***************************************************************************\r
+     *                                                                       *\r
+     *    FreeRTOS tutorial books are available in pdf and paperback.        *\r
+     *    Complete, revised, and edited pdf reference manuals are also       *\r
+     *    available.                                                         *\r
+     *                                                                       *\r
+     *    Purchasing FreeRTOS documentation will not only help you, by       *\r
+     *    ensuring you get running as quickly as possible and with an        *\r
+     *    in-depth knowledge of how to use FreeRTOS, it will also help       *\r
+     *    the FreeRTOS project to continue with its mission of providing     *\r
+     *    professional grade, cross platform, de facto standard solutions    *\r
+     *    for microcontrollers - completely free of charge!                  *\r
+     *                                                                       *\r
+     *    >>> See http://www.FreeRTOS.org/Documentation for details. <<<     *\r
+     *                                                                       *\r
+     *    Thank you for using FreeRTOS, and thank you for your support!      *\r
+     *                                                                       *\r
+    ***************************************************************************\r
+\r
+\r
+    This file is part of the FreeRTOS distribution.\r
+\r
+    FreeRTOS is free software; you can redistribute it and/or modify it under\r
+    the terms of the GNU General Public License (version 2) as published by the\r
+    Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+\r
+    >>>>>>NOTE<<<<<< The modification to the GPL is included to allow you to\r
+    distribute a combined work that includes FreeRTOS without being obliged to\r
+    provide the source code for proprietary components outside of the FreeRTOS\r
+    kernel.\r
+\r
+    FreeRTOS is distributed in the hope that it will be useful, but WITHOUT ANY\r
+    WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS\r
+    FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more\r
+    details. You should have received a copy of the GNU General Public License\r
+    and the FreeRTOS license exception along with FreeRTOS; if not itcan be\r
+    viewed here: http://www.freertos.org/a00114.html and also obtained by\r
+    writing to Real Time Engineers Ltd., contact details for whom are available\r
+    on the FreeRTOS WEB site.\r
+\r
+    1 tab == 4 spaces!\r
+\r
+    ***************************************************************************\r
+     *                                                                       *\r
+     *    Having a problem?  Start by reading the FAQ "My application does   *\r
+     *    not run, what could be wrong?"                                     *\r
+     *                                                                       *\r
+     *    http://www.FreeRTOS.org/FAQHelp.html                               *\r
+     *                                                                       *\r
+    ***************************************************************************\r
+\r
+\r
+    http://www.FreeRTOS.org - Documentation, books, training, latest versions,\r
+    license and Real Time Engineers Ltd. contact details.\r
+\r
+    http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+    including FreeRTOS+Trace - an indispensable productivity tool, and our new\r
+    fully thread aware and reentrant UDP/IP stack.\r
+\r
+    http://www.OpenRTOS.com - Real Time Engineers ltd license FreeRTOS to High\r
+    Integrity Systems, who sell the code with commercial support,\r
+    indemnification and middleware, under the OpenRTOS brand.\r
+\r
+    http://www.SafeRTOS.com - High Integrity Systems also provide a safety\r
+    engineered and independently SIL3 certified version for use in safety and\r
+    mission critical applications that require provable dependability.\r
+*/\r
+\r
+/* FreeRTOS includes. */\r
+#include "FreeRTOS.h"\r
+#include "task.h"\r
+\r
+/* Standard includes. */\r
+#include <stdint.h>\r
+#include <stdio.h>\r
+#include <stdlib.h>\r
+\r
+/* FreeRTOS+CLI includes. */\r
+#include "FreeRTOS_CLI.h"\r
+\r
+/* File system includes. */\r
+#include "fat_sl.h"\r
+#include "api_mdriver_ram.h"\r
+#include "test.h"\r
+\r
+#ifdef _WINDOWS_\r
+       #define snprintf _snprintf\r
+#endif\r
+\r
+#define cliNEW_LINE            "\r\n"\r
+\r
+/*******************************************************************************\r
+ * See the URL in the comments within main.c for the location of the online\r
+ * documentation.\r
+ ******************************************************************************/\r
+\r
+/*\r
+ * Print out information on a single file.\r
+ */\r
+static void prvCreateFileInfoString( int8_t *pcBuffer, F_FIND *pxFindStruct );\r
+\r
+/*\r
+ * Copies an existing file into a newly created file.\r
+ */\r
+static portBASE_TYPE prvPerformCopy( int8_t *pcSourceFile,\r
+                                                       int32_t lSourceFileLength,\r
+                                                       int8_t *pcDestinationFile,\r
+                                                       int8_t *pxWriteBuffer,\r
+                                                       size_t xWriteBufferLen );\r
+\r
+/*\r
+ * Implements the DIR command.\r
+ */\r
+static portBASE_TYPE prvDIRCommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString );\r
+\r
+/*\r
+ * Implements the CD command.\r
+ */\r
+static portBASE_TYPE prvCDCommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString );\r
+\r
+/*\r
+ * Implements the DEL command.\r
+ */\r
+static portBASE_TYPE prvDELCommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString );\r
+\r
+/*\r
+ * Implements the TYPE command.\r
+ */\r
+static portBASE_TYPE prvTYPECommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString );\r
+\r
+/*\r
+ * Implements the COPY command.\r
+ */\r
+static portBASE_TYPE prvCOPYCommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString );\r
+\r
+/*\r
+ * Implements the TEST command.\r
+ */\r
+static portBASE_TYPE prvTESTFSCommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString );\r
+\r
+/* Structure that defines the DIR command line command, which lists all the\r
+files in the current directory. */\r
+static const CLI_Command_Definition_t xDIR =\r
+{\r
+       ( const int8_t * const ) "dir", /* The command string to type. */\r
+       ( const int8_t * const ) "\r\ndir:\r\n Lists the files in the current directory\r\n",\r
+       prvDIRCommand, /* The function to run. */\r
+       0 /* No parameters are expected. */\r
+};\r
+\r
+/* Structure that defines the CD command line command, which changes the\r
+working directory. */\r
+static const CLI_Command_Definition_t xCD =\r
+{\r
+       ( const int8_t * const ) "cd", /* The command string to type. */\r
+       ( const int8_t * const ) "\r\ncd <dir name>:\r\n Changes the working directory\r\n",\r
+       prvCDCommand, /* The function to run. */\r
+       1 /* One parameter is expected. */\r
+};\r
+\r
+/* Structure that defines the TYPE command line command, which prints the\r
+contents of a file to the console. */\r
+static const CLI_Command_Definition_t xTYPE =\r
+{\r
+       ( const int8_t * const ) "type", /* The command string to type. */\r
+       ( const int8_t * const ) "\r\ntype <filename>:\r\n Prints file contents to the terminal\r\n",\r
+       prvTYPECommand, /* The function to run. */\r
+       1 /* One parameter is expected. */\r
+};\r
+\r
+/* Structure that defines the DEL command line command, which deletes a file. */\r
+static const CLI_Command_Definition_t xDEL =\r
+{\r
+       ( const int8_t * const ) "del", /* The command string to type. */\r
+       ( const int8_t * const ) "\r\ndel <filename>:\r\n deletes a file or directory\r\n",\r
+       prvDELCommand, /* The function to run. */\r
+       1 /* One parameter is expected. */\r
+};\r
+\r
+/* Structure that defines the COPY command line command, which deletes a file. */\r
+static const CLI_Command_Definition_t xCOPY =\r
+{\r
+       ( const int8_t * const ) "copy", /* The command string to type. */\r
+       ( const int8_t * const ) "\r\ncopy <source file> <dest file>:\r\n Copies <source file> to <dest file>\r\n",\r
+       prvCOPYCommand, /* The function to run. */\r
+       2 /* Two parameters are expected. */\r
+};\r
+\r
+/* Structure that defines the TEST command line command, which executes some\r
+file system driver tests. */\r
+static const CLI_Command_Definition_t xTEST_FS =\r
+{\r
+       ( const int8_t * const ) "testfs", /* The command string to type. */\r
+       ( const int8_t * const ) "\r\ntest_fs:\r\n Executes some file system test.  ALL FILES WILL BE DELETED!!!\r\n",\r
+       prvTESTFSCommand, /* The function to run. */\r
+       0 /* No parameters are expected. */\r
+};\r
+\r
+/*-----------------------------------------------------------*/\r
+\r
+void vRegisterFileSystemCLICommands( void )\r
+{\r
+       /* Register all the command line commands defined immediately above. */\r
+       FreeRTOS_CLIRegisterCommand( &xDIR );\r
+       FreeRTOS_CLIRegisterCommand( &xCD );\r
+       FreeRTOS_CLIRegisterCommand( &xTYPE );\r
+       FreeRTOS_CLIRegisterCommand( &xDEL );\r
+       FreeRTOS_CLIRegisterCommand( &xCOPY );\r
+       FreeRTOS_CLIRegisterCommand( &xTEST_FS );\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static portBASE_TYPE prvTYPECommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString )\r
+{\r
+int8_t *pcParameter;\r
+portBASE_TYPE xParameterStringLength, xReturn = pdTRUE;\r
+static F_FILE *pxFile = NULL;\r
+int iChar;\r
+size_t xByte;\r
+size_t xColumns = 50U;\r
+\r
+       /* Ensure there is always a null terminator after each character written. */\r
+       memset( pcWriteBuffer, 0x00, xWriteBufferLen );\r
+\r
+       /* Ensure the buffer leaves space for the \r\n. */\r
+       configASSERT( xWriteBufferLen > ( strlen( cliNEW_LINE ) * 2 ) );\r
+       xWriteBufferLen -= strlen( cliNEW_LINE );\r
+\r
+       if( xWriteBufferLen < xColumns )\r
+       {\r
+               /* Ensure the loop that uses xColumns as an end condition does not\r
+               write off the end of the buffer. */\r
+               xColumns = xWriteBufferLen;\r
+       }\r
+\r
+       if( pxFile == NULL )\r
+       {\r
+               /* The file has not been opened yet.  Find the file name. */\r
+               pcParameter = ( int8_t * ) FreeRTOS_CLIGetParameter\r
+                                                                       (\r
+                                                                               pcCommandString,                /* The command string itself. */\r
+                                                                               1,                                              /* Return the first parameter. */\r
+                                                                               &xParameterStringLength /* Store the parameter string length. */\r
+                                                                       );\r
+\r
+               /* Sanity check something was returned. */\r
+               configASSERT( pcParameter );\r
+\r
+               /* Attempt to open the requested file. */\r
+               pxFile = f_open( ( const char * ) pcParameter, "r" );\r
+       }\r
+\r
+       if( pxFile != NULL )\r
+       {\r
+               /* Read the next chunk of data from the file. */\r
+               for( xByte = 0; xByte < xColumns; xByte++ )\r
+               {\r
+                       iChar = f_getc( pxFile );\r
+\r
+                       if( iChar == -1 )\r
+                       {\r
+                               /* No more characters to return. */\r
+                               f_close( pxFile );\r
+                               pxFile = NULL;\r
+                               break;\r
+                       }\r
+                       else\r
+                       {\r
+                               pcWriteBuffer[ xByte ] = ( int8_t ) iChar;\r
+                       }\r
+               }\r
+       }\r
+\r
+       if( pxFile == NULL )\r
+       {\r
+               /* Either the file was not opened, or all the data from the file has\r
+               been returned and the file is now closed. */\r
+               xReturn = pdFALSE;\r
+       }\r
+\r
+       strcat( ( char * ) pcWriteBuffer, cliNEW_LINE );\r
+\r
+       return xReturn;\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static portBASE_TYPE prvCDCommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString )\r
+{\r
+int8_t *pcParameter;\r
+portBASE_TYPE xParameterStringLength;\r
+unsigned char ucReturned;\r
+size_t xStringLength;\r
+\r
+       /* Obtain the parameter string. */\r
+       pcParameter = ( int8_t * ) FreeRTOS_CLIGetParameter\r
+                                                               (\r
+                                                                       pcCommandString,                /* The command string itself. */\r
+                                                                       1,                                              /* Return the first parameter. */\r
+                                                                       &xParameterStringLength /* Store the parameter string length. */\r
+                                                               );\r
+\r
+       /* Sanity check something was returned. */\r
+       configASSERT( pcParameter );\r
+\r
+       /* Attempt to move to the requested directory. */\r
+       ucReturned = f_chdir( ( char * ) pcParameter );\r
+\r
+       if( ucReturned == F_NO_ERROR )\r
+       {\r
+               sprintf( ( char * ) pcWriteBuffer, "In: " );\r
+               xStringLength = strlen( ( const char * ) pcWriteBuffer );\r
+               f_getcwd( ( char * ) &( pcWriteBuffer[ xStringLength ] ), ( unsigned char ) ( xWriteBufferLen - xStringLength ) );\r
+       }\r
+       else\r
+       {\r
+               sprintf( ( char * ) pcWriteBuffer, "Error" );\r
+       }\r
+\r
+       strcat( ( char * ) pcWriteBuffer, cliNEW_LINE );\r
+\r
+       return pdFALSE;\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static portBASE_TYPE prvDIRCommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString )\r
+{\r
+static F_FIND *pxFindStruct = NULL;\r
+unsigned char ucReturned;\r
+portBASE_TYPE xReturn = pdFALSE;\r
+\r
+       /* This assumes pcWriteBuffer is long enough. */\r
+       ( void ) pcCommandString;\r
+\r
+       /* Ensure the buffer leaves space for the \r\n. */\r
+       configASSERT( xWriteBufferLen > ( strlen( cliNEW_LINE ) * 2 ) );\r
+       xWriteBufferLen -= strlen( cliNEW_LINE );\r
+\r
+       if( pxFindStruct == NULL )\r
+       {\r
+               /* This is the first time this function has been executed since the Dir\r
+               command was run.  Create the find structure. */\r
+               pxFindStruct = ( F_FIND * ) pvPortMalloc( sizeof( F_FIND ) );\r
+\r
+               if( pxFindStruct != NULL )\r
+               {\r
+                       ucReturned = f_findfirst( "*.*", pxFindStruct );\r
+\r
+                       if( ucReturned == F_NO_ERROR )\r
+                       {\r
+                               prvCreateFileInfoString( pcWriteBuffer, pxFindStruct );\r
+                               xReturn = pdPASS;\r
+                       }\r
+                       else\r
+                       {\r
+                               snprintf( ( char * ) pcWriteBuffer, xWriteBufferLen, "Error: f_findfirst() failed." );\r
+                       }\r
+               }\r
+               else\r
+               {\r
+                       snprintf( ( char * ) pcWriteBuffer, xWriteBufferLen, "Failed to allocate RAM (using heap_4.c will prevent fragmentation)." );\r
+               }\r
+       }\r
+       else\r
+       {\r
+               /* The find struct has already been created.  Find the next file in\r
+               the directory. */\r
+               ucReturned = f_findnext( pxFindStruct );\r
+\r
+               if( ucReturned == F_NO_ERROR )\r
+               {\r
+                       prvCreateFileInfoString( pcWriteBuffer, pxFindStruct );\r
+                       xReturn = pdPASS;\r
+               }\r
+               else\r
+               {\r
+                       /* There are no more files.  Free the find structure. */\r
+                       vPortFree( pxFindStruct );\r
+                       pxFindStruct = NULL;\r
+\r
+                       /* No string to return. */\r
+                       pcWriteBuffer[ 0 ] = 0x00;\r
+               }\r
+       }\r
+\r
+       strcat( ( char * ) pcWriteBuffer, cliNEW_LINE );\r
+\r
+       return xReturn;\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static portBASE_TYPE prvDELCommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString )\r
+{\r
+int8_t *pcParameter;\r
+portBASE_TYPE xParameterStringLength;\r
+unsigned char ucReturned;\r
+\r
+       /* This function assumes xWriteBufferLen is large enough! */\r
+       ( void ) xWriteBufferLen;\r
+\r
+       /* Obtain the parameter string. */\r
+       pcParameter = ( int8_t * ) FreeRTOS_CLIGetParameter\r
+                                                               (\r
+                                                                       pcCommandString,                /* The command string itself. */\r
+                                                                       1,                                              /* Return the first parameter. */\r
+                                                                       &xParameterStringLength /* Store the parameter string length. */\r
+                                                               );\r
+\r
+       /* Sanity check something was returned. */\r
+       configASSERT( pcParameter );\r
+\r
+       /* Attempt to delete the file. */\r
+       ucReturned = f_delete( ( const char * ) pcParameter );\r
+\r
+       if( ucReturned == F_NO_ERROR )\r
+       {\r
+               sprintf( ( char * ) pcWriteBuffer, "%s was deleted", pcParameter );\r
+       }\r
+       else\r
+       {\r
+               sprintf( ( char * ) pcWriteBuffer, "Error" );\r
+       }\r
+\r
+       strcat( ( char * ) pcWriteBuffer, cliNEW_LINE );\r
+\r
+       return pdFALSE;\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static portBASE_TYPE prvTESTFSCommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString )\r
+{\r
+unsigned portBASE_TYPE uxOriginalPriority;\r
+\r
+       /* Avoid compiler warnings. */\r
+       ( void ) xWriteBufferLen;\r
+       ( void ) pcCommandString;\r
+\r
+       /* Limitations in the interaction with the Windows TCP/IP stack require\r
+       the command console to run at the idle priority.  Raise the priority for\r
+       the duration of the tests to ensure there are not multiple switches to the\r
+       idle task as in the simulated environment the idle task hook function may\r
+       include a (relatively) long delay. */\r
+       uxOriginalPriority = uxTaskPriorityGet( NULL );\r
+       vTaskPrioritySet( NULL, configMAX_PRIORITIES - 1 );\r
+\r
+       f_dotest( 0 );\r
+\r
+       /* Reset back to the original priority. */\r
+       vTaskPrioritySet( NULL, uxOriginalPriority );\r
+\r
+       sprintf( ( char * ) pcWriteBuffer, "%s", "Test results were sent to Windows console" );\r
+\r
+       return pdFALSE;\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static portBASE_TYPE prvCOPYCommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString )\r
+{\r
+int8_t *pcSourceFile, *pcDestinationFile;\r
+portBASE_TYPE xParameterStringLength;\r
+long lSourceLength, lDestinationLength = 0;\r
+\r
+       /* Obtain the name of the destination file. */\r
+       pcDestinationFile = ( int8_t * ) FreeRTOS_CLIGetParameter\r
+                                                               (\r
+                                                                       pcCommandString,                /* The command string itself. */\r
+                                                                       2,                                              /* Return the second parameter. */\r
+                                                                       &xParameterStringLength /* Store the parameter string length. */\r
+                                                               );\r
+\r
+       /* Sanity check something was returned. */\r
+       configASSERT( pcDestinationFile );\r
+\r
+       /* Obtain the name of the source file. */\r
+       pcSourceFile = ( int8_t * ) FreeRTOS_CLIGetParameter\r
+                                                               (\r
+                                                                       pcCommandString,                /* The command string itself. */\r
+                                                                       1,                                              /* Return the first parameter. */\r
+                                                                       &xParameterStringLength /* Store the parameter string length. */\r
+                                                               );\r
+\r
+       /* Sanity check something was returned. */\r
+       configASSERT( pcSourceFile );\r
+\r
+       /* Terminate the string. */\r
+       pcSourceFile[ xParameterStringLength ] = 0x00;\r
+\r
+       /* See if the source file exists, obtain its length if it does. */\r
+       lSourceLength = f_filelength( ( const char * ) pcSourceFile );\r
+\r
+       if( lSourceLength == 0 )\r
+       {\r
+               sprintf( ( char * ) pcWriteBuffer, "Source file does not exist" );\r
+       }\r
+       else\r
+       {\r
+               /* See if the destination file exists. */\r
+               lDestinationLength = f_filelength( ( const char * ) pcDestinationFile );\r
+\r
+               if( lDestinationLength != 0 )\r
+               {\r
+                       sprintf( ( char * ) pcWriteBuffer, "Error: Destination file already exists" );\r
+               }\r
+       }\r
+\r
+       /* Continue only if the source file exists and the destination file does\r
+       not exist. */\r
+       if( ( lSourceLength != 0 ) && ( lDestinationLength == 0 ) )\r
+       {\r
+               if( prvPerformCopy( pcSourceFile, lSourceLength, pcDestinationFile, pcWriteBuffer, xWriteBufferLen ) == pdPASS )\r
+               {\r
+                       sprintf( ( char * ) pcWriteBuffer, "Copy made" );\r
+               }\r
+               else\r
+               {\r
+                       sprintf( ( char * ) pcWriteBuffer, "Error during copy" );\r
+               }\r
+       }\r
+\r
+       strcat( ( char * ) pcWriteBuffer, cliNEW_LINE );\r
+\r
+       return pdFALSE;\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static portBASE_TYPE prvPerformCopy( int8_t *pcSourceFile,\r
+                                                       int32_t lSourceFileLength,\r
+                                                       int8_t *pcDestinationFile,\r
+                                                       int8_t *pxWriteBuffer,\r
+                                                       size_t xWriteBufferLen )\r
+{\r
+int32_t lBytesRead = 0, lBytesToRead, lBytesRemaining;\r
+F_FILE *pxFile;\r
+portBASE_TYPE xReturn = pdPASS;\r
+\r
+       /* NOTE:  Error handling has been omitted for clarity. */\r
+\r
+       while( lBytesRead < lSourceFileLength )\r
+       {\r
+               /* How many bytes are left? */\r
+               lBytesRemaining = lSourceFileLength - lBytesRead;\r
+\r
+               /* How many bytes should be read this time around the loop.  Can't\r
+               read more bytes than will fit into the buffer. */\r
+               if( lBytesRemaining > ( long ) xWriteBufferLen )\r
+               {\r
+                       lBytesToRead = ( long ) xWriteBufferLen;\r
+               }\r
+               else\r
+               {\r
+                       lBytesToRead = lBytesRemaining;\r
+               }\r
+\r
+               /* Open the source file, seek past the data that has already been\r
+               read from the file, read the next block of data, then close the\r
+               file again so the destination file can be opened. */\r
+               pxFile = f_open( ( const char * ) pcSourceFile, "r" );\r
+               if( pxFile != NULL )\r
+               {\r
+                       f_seek( pxFile, lBytesRead, F_SEEK_SET );\r
+                       f_read( pxWriteBuffer, lBytesToRead, 1, pxFile );\r
+                       f_close( pxFile );\r
+               }\r
+               else\r
+               {\r
+                       xReturn = pdFAIL;\r
+                       break;\r
+               }\r
+\r
+               /* Open the destination file and write the block of data to the end of\r
+               the file. */\r
+               pxFile = f_open( ( const char * ) pcDestinationFile, "a" );\r
+               if( pxFile != NULL )\r
+               {\r
+                       f_write( pxWriteBuffer, lBytesToRead, 1, pxFile );\r
+                       f_close( pxFile );\r
+               }\r
+               else\r
+               {\r
+                       xReturn = pdFAIL;\r
+                       break;\r
+               }\r
+\r
+               lBytesRead += lBytesToRead;\r
+       }\r
+\r
+       return xReturn;\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static void prvCreateFileInfoString( int8_t *pcBuffer, F_FIND *pxFindStruct )\r
+{\r
+const char *pcWritableFile = "writable file", *pcReadOnlyFile = "read only file", *pcDirectory = "directory";\r
+const char * pcAttrib;\r
+\r
+       /* Point pcAttrib to a string that describes the file. */\r
+       if( ( pxFindStruct->attr & F_ATTR_DIR ) != 0 )\r
+       {\r
+               pcAttrib = pcDirectory;\r
+       }\r
+       else if( pxFindStruct->attr & F_ATTR_READONLY )\r
+       {\r
+               pcAttrib = pcReadOnlyFile;\r
+       }\r
+       else\r
+       {\r
+               pcAttrib = pcWritableFile;\r
+       }\r
+\r
+       /* Create a string that includes the file name, the file size and the\r
+       attributes string. */\r
+       sprintf( ( char * ) pcBuffer, "%s [%s] [size=%d]", pxFindStruct->filename, pcAttrib, pxFindStruct->filesize );\r
+}\r
diff --git a/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/File-system-demo.c b/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/File-system-demo.c
new file mode 100644 (file)
index 0000000..8f3915b
--- /dev/null
@@ -0,0 +1,381 @@
+/*\r
+    FreeRTOS V7.4.0 - Copyright (C) 2013 Real Time Engineers Ltd.\r
+\r
+    FEATURES AND PORTS ARE ADDED TO FREERTOS ALL THE TIME.  PLEASE VISIT\r
+    http://www.FreeRTOS.org TO ENSURE YOU ARE USING THE LATEST VERSION.\r
+\r
+    ***************************************************************************\r
+     *                                                                       *\r
+     *    FreeRTOS tutorial books are available in pdf and paperback.        *\r
+     *    Complete, revised, and edited pdf reference manuals are also       *\r
+     *    available.                                                         *\r
+     *                                                                       *\r
+     *    Purchasing FreeRTOS documentation will not only help you, by       *\r
+     *    ensuring you get running as quickly as possible and with an        *\r
+     *    in-depth knowledge of how to use FreeRTOS, it will also help       *\r
+     *    the FreeRTOS project to continue with its mission of providing     *\r
+     *    professional grade, cross platform, de facto standard solutions    *\r
+     *    for microcontrollers - completely free of charge!                  *\r
+     *                                                                       *\r
+     *    >>> See http://www.FreeRTOS.org/Documentation for details. <<<     *\r
+     *                                                                       *\r
+     *    Thank you for using FreeRTOS, and thank you for your support!      *\r
+     *                                                                       *\r
+    ***************************************************************************\r
+\r
+\r
+    This file is part of the FreeRTOS distribution.\r
+\r
+    FreeRTOS is free software; you can redistribute it and/or modify it under\r
+    the terms of the GNU General Public License (version 2) as published by the\r
+    Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+\r
+    >>>>>>NOTE<<<<<< The modification to the GPL is included to allow you to\r
+    distribute a combined work that includes FreeRTOS without being obliged to\r
+    provide the source code for proprietary components outside of the FreeRTOS\r
+    kernel.\r
+\r
+    FreeRTOS is distributed in the hope that it will be useful, but WITHOUT ANY\r
+    WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS\r
+    FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more\r
+    details. You should have received a copy of the GNU General Public License\r
+    and the FreeRTOS license exception along with FreeRTOS; if not itcan be\r
+    viewed here: http://www.freertos.org/a00114.html and also obtained by\r
+    writing to Real Time Engineers Ltd., contact details for whom are available\r
+    on the FreeRTOS WEB site.\r
+\r
+    1 tab == 4 spaces!\r
+\r
+    ***************************************************************************\r
+     *                                                                       *\r
+     *    Having a problem?  Start by reading the FAQ "My application does   *\r
+     *    not run, what could be wrong?"                                     *\r
+     *                                                                       *\r
+     *    http://www.FreeRTOS.org/FAQHelp.html                               *\r
+     *                                                                       *\r
+    ***************************************************************************\r
+\r
+\r
+    http://www.FreeRTOS.org - Documentation, books, training, latest versions,\r
+    license and Real Time Engineers Ltd. contact details.\r
+\r
+    http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+    including FreeRTOS+Trace - an indispensable productivity tool, and our new\r
+    fully thread aware and reentrant UDP/IP stack.\r
+\r
+    http://www.OpenRTOS.com - Real Time Engineers ltd license FreeRTOS to High\r
+    Integrity Systems, who sell the code with commercial support,\r
+    indemnification and middleware, under the OpenRTOS brand.\r
+\r
+    http://www.SafeRTOS.com - High Integrity Systems also provide a safety\r
+    engineered and independently SIL3 certified version for use in safety and\r
+    mission critical applications that require provable dependability.\r
+*/\r
+\r
+/*******************************************************************************\r
+ * See the URL in the comments within main.c for the location of the online\r
+ * documentation.\r
+ ******************************************************************************/\r
+\r
+/* Standard includes. */\r
+#include <stdio.h>\r
+\r
+/* FreeRTOS includes. */\r
+#include "FreeRTOS.h"\r
+\r
+/* File system includes. */\r
+#include "fat_sl.h"\r
+#include "api_mdriver_ram.h"\r
+\r
+/* 8.3 format, plus null terminator. */\r
+#define fsMAX_FILE_NAME_LEN                            13\r
+\r
+/* The number of bytes read/written to the example files at a time. */\r
+#define fsRAM_BUFFER_SIZE                              200\r
+\r
+/* The number of bytes written to the file that uses f_putc() and f_getc(). */\r
+#define fsPUTC_FILE_SIZE                               100\r
+\r
+/*-----------------------------------------------------------*/\r
+\r
+/*\r
+ * Creates and verifies different files on the volume, demonstrating the use of\r
+ * various different API functions.\r
+ */\r
+void vCreateAndVerifySampleFiles( void );\r
+\r
+/*\r
+ * Create a set of example files in the root directory of the volume using\r
+ * f_write().\r
+ */\r
+static void prvCreateDemoFilesUsing_f_write( void );\r
+\r
+/*\r
+ * Use f_read() to read back and verify the files that were created by\r
+ * prvCreateDemoFilesUsing_f_write().\r
+ */\r
+static void prvVerifyDemoFileUsing_f_read( void );\r
+\r
+/*\r
+ * Create an example file in a sub-directory using f_putc().\r
+ */\r
+static void prvCreateDemoFileUsing_f_putc( void );\r
+\r
+/*\r
+ * Use f_getc() to read back and verify the file that was created by\r
+ * prvCreateDemoFileUsing_f_putc().\r
+ */\r
+static void prvVerifyDemoFileUsing_f_getc( void );\r
+\r
+/*-----------------------------------------------------------*/\r
+\r
+/* A buffer used to both create content to write to disk, and read content back\r
+from a disk.  Note there is no mutual exclusion on this buffer. */\r
+static char cRAMBuffer[ fsRAM_BUFFER_SIZE ];\r
+\r
+/* Names of directories that are created. */\r
+static const char *pcRoot = "/", *pcDirectory1 = "SUB1", *pcDirectory2 = "SUB2", *pcFullPath = "/SUB1/SUB2";\r
+\r
+/*-----------------------------------------------------------*/\r
+\r
+void vCreateAndVerifySampleFiles( void )\r
+{\r
+unsigned char ucStatus;\r
+\r
+       /* First create the volume. */\r
+       ucStatus = f_initvolume( ram_initfunc );\r
+\r
+       /* It is expected that the volume is not formatted. */\r
+       if( ucStatus == F_ERR_NOTFORMATTED )\r
+       {\r
+               /* Format the created volume. */\r
+               ucStatus = f_format( F_FAT12_MEDIA );\r
+       }\r
+\r
+       if( ucStatus == F_NO_ERROR )\r
+       {\r
+               /* Create a set of files using f_write(). */\r
+               prvCreateDemoFilesUsing_f_write();\r
+\r
+               /* Read back and verify the files that were created using f_write(). */\r
+               prvVerifyDemoFileUsing_f_read();\r
+\r
+               /* Create sub directories two deep then create a file using putc. */\r
+               prvCreateDemoFileUsing_f_putc();\r
+\r
+               /* Read back and verify the file created by\r
+               prvCreateDemoFileUsing_f_putc(). */\r
+               prvVerifyDemoFileUsing_f_getc();\r
+       }\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static void prvCreateDemoFilesUsing_f_write( void )\r
+{\r
+portBASE_TYPE xFileNumber, xWriteNumber;\r
+char cFileName[ fsMAX_FILE_NAME_LEN ];\r
+const portBASE_TYPE xMaxFiles = 5;\r
+long lItemsWritten;\r
+F_FILE *pxFile;\r
+\r
+       /* Create xMaxFiles files.  Each created file will be\r
+       ( xFileNumber * fsRAM_BUFFER_SIZE ) bytes in length, and filled\r
+       with a different repeating character. */\r
+       for( xFileNumber = 1; xFileNumber <= xMaxFiles; xFileNumber++ )\r
+       {\r
+               /* Generate a file name. */\r
+               sprintf( cFileName, "root%03d.txt", xFileNumber );\r
+\r
+               /* Obtain the current working directory and print out the file name and\r
+               the     directory into which the file is being written. */\r
+               f_getcwd( cRAMBuffer, fsRAM_BUFFER_SIZE );\r
+               printf( "Creating file %s in %s\r\n", cFileName, cRAMBuffer );\r
+\r
+               /* Open the file, creating the file if it does not already exist. */\r
+               pxFile = f_open( cFileName, "w" );\r
+               configASSERT( pxFile );\r
+\r
+               /* Fill the RAM buffer with data that will be written to the file.  This\r
+               is just a repeating ascii character that indicates the file number. */\r
+               memset( cRAMBuffer, ( int ) ( '0' + xFileNumber ), fsRAM_BUFFER_SIZE );\r
+\r
+               /* Write the RAM buffer to the opened file a number of times.  The\r
+               number of times the RAM buffer is written to the file depends on the\r
+               file number, so the length of each created file will be different. */\r
+               for( xWriteNumber = 0; xWriteNumber < xFileNumber; xWriteNumber++ )\r
+               {\r
+                       lItemsWritten = f_write( cRAMBuffer, fsRAM_BUFFER_SIZE, 1, pxFile );\r
+                       configASSERT( lItemsWritten == 1 );\r
+               }\r
+\r
+               /* Close the file so another file can be created. */\r
+               f_close( pxFile );\r
+       }\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static void prvVerifyDemoFileUsing_f_read( void )\r
+{\r
+portBASE_TYPE xFileNumber, xReadNumber;\r
+char cFileName[ fsMAX_FILE_NAME_LEN ];\r
+const portBASE_TYPE xMaxFiles = 5;\r
+long lItemsRead, lChar;\r
+F_FILE *pxFile;\r
+\r
+       /* Read back the files that were created by\r
+       prvCreateDemoFilesUsing_f_write(). */\r
+       for( xFileNumber = 1; xFileNumber <= xMaxFiles; xFileNumber++ )\r
+       {\r
+               /* Generate the file name. */\r
+               sprintf( cFileName, "root%03d.txt", xFileNumber );\r
+\r
+               /* Obtain the current working directory and print out the file name and\r
+               the     directory from which the file is being read. */\r
+               f_getcwd( cRAMBuffer, fsRAM_BUFFER_SIZE );\r
+               printf( "Reading file %s from %s\r\n", cFileName, cRAMBuffer );\r
+\r
+               /* Open the file for reading. */\r
+               pxFile = f_open( cFileName, "r" );\r
+               configASSERT( pxFile );\r
+\r
+               /* Read the file into the RAM buffer, checking the file contents are as\r
+               expected.  The size of the file depends on the file number. */\r
+               for( xReadNumber = 0; xReadNumber < xFileNumber; xReadNumber++ )\r
+               {\r
+                       /* Start with the RAM buffer clear. */\r
+                       memset( cRAMBuffer, 0x00, fsRAM_BUFFER_SIZE );\r
+\r
+                       lItemsRead = f_read( cRAMBuffer, fsRAM_BUFFER_SIZE, 1, pxFile );\r
+                       configASSERT( lItemsRead == 1 );\r
+\r
+                       /* Check the RAM buffer is filled with the expected data.  Each\r
+                       file contains a different repeating ascii character that indicates\r
+                       the number of the file. */\r
+                       for( lChar = 0; lChar < fsRAM_BUFFER_SIZE; lChar++ )\r
+                       {\r
+                               configASSERT( cRAMBuffer[ lChar ] == ( '0' + ( char ) xFileNumber ) );\r
+                       }\r
+               }\r
+\r
+               /* Close the file. */\r
+               f_close( pxFile );\r
+       }\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static void prvCreateDemoFileUsing_f_putc( void )\r
+{\r
+unsigned char ucReturn;\r
+int iByte, iReturned;\r
+F_FILE *pxFile;\r
+char cFileName[ fsMAX_FILE_NAME_LEN ];\r
+\r
+       /* Obtain and print out the working directory. */\r
+       f_getcwd( cRAMBuffer, fsRAM_BUFFER_SIZE );\r
+       printf( "In directory %s\r\n", cRAMBuffer );\r
+\r
+       /* Create a sub directory. */\r
+       ucReturn = f_mkdir( pcDirectory1 );\r
+       configASSERT( ucReturn == F_NO_ERROR );\r
+\r
+       /* Move into the created sub-directory. */\r
+       ucReturn = f_chdir( pcDirectory1 );\r
+       configASSERT( ucReturn == F_NO_ERROR );\r
+\r
+       /* Obtain and print out the working directory. */\r
+       f_getcwd( cRAMBuffer, fsRAM_BUFFER_SIZE );\r
+       printf( "In directory %s\r\n", cRAMBuffer );\r
+\r
+       /* Create a subdirectory in the new directory. */\r
+       ucReturn = f_mkdir( pcDirectory2 );\r
+       configASSERT( ucReturn == F_NO_ERROR );\r
+\r
+       /* Move into the directory just created - now two directories down from\r
+       the root. */\r
+       ucReturn = f_chdir( pcDirectory2 );\r
+       configASSERT( ucReturn == F_NO_ERROR );\r
+\r
+       /* Obtain and print out the working directory. */\r
+       f_getcwd( cRAMBuffer, fsRAM_BUFFER_SIZE );\r
+       printf( "In directory %s\r\n", cRAMBuffer );\r
+       configASSERT( strcmp( ( const char * ) cRAMBuffer, pcFullPath ) == 0 );\r
+\r
+       /* Generate the file name. */\r
+       sprintf( cFileName, "%s.txt", pcDirectory2 );\r
+\r
+       /* Print out the file name and the directory into which the file is being\r
+       written. */\r
+       printf( "Writing file %s in %s\r\n", cFileName, cRAMBuffer );\r
+\r
+       pxFile = f_open( cFileName, "w" );\r
+\r
+       /* Create a file 1 byte at a time.  The file is filled with incrementing\r
+       ascii characters starting from '0'. */\r
+       for( iByte = 0; iByte < fsPUTC_FILE_SIZE; iByte++ )\r
+       {\r
+               iReturned = f_putc( ( ( int ) '0' + iByte ), pxFile );\r
+               configASSERT( iReturned ==  ( ( int ) '0' + iByte ) );\r
+       }\r
+\r
+       /* Finished so close the file. */\r
+       f_close( pxFile );\r
+\r
+       /* Move back to the root directory. */\r
+       ucReturn = f_chdir( "../.." );\r
+       configASSERT( ucReturn == F_NO_ERROR );\r
+\r
+       /* Obtain and print out the working directory. */\r
+       f_getcwd( cRAMBuffer, fsRAM_BUFFER_SIZE );\r
+       printf( "Back in root directory %s\r\n", cRAMBuffer );\r
+       configASSERT( strcmp( ( const char * ) cRAMBuffer, pcRoot ) == 0 );\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static void prvVerifyDemoFileUsing_f_getc( void )\r
+{\r
+unsigned char ucReturn;\r
+int iByte, iReturned;\r
+F_FILE *pxFile;\r
+char cFileName[ fsMAX_FILE_NAME_LEN ];\r
+\r
+       /* Move into the directory in which the file was created. */\r
+       ucReturn = f_chdir( pcFullPath );\r
+       configASSERT( ucReturn == F_NO_ERROR );\r
+\r
+       /* Obtain and print out the working directory. */\r
+       f_getcwd( cRAMBuffer, fsRAM_BUFFER_SIZE );\r
+       printf( "Back in directory %s\r\n", cRAMBuffer );\r
+       configASSERT( strcmp( ( const char * ) cRAMBuffer, pcFullPath ) == 0 );\r
+\r
+       /* Generate the file name. */\r
+       sprintf( cFileName, "%s.txt", pcDirectory2 );\r
+\r
+       /* Print out the file name and the directory from which the file is being\r
+       read. */\r
+       printf( "Reading file %s in %s\r\n", cFileName, cRAMBuffer );\r
+\r
+       /* This time the file is opened for reading. */\r
+       pxFile = f_open( cFileName, "r" );\r
+\r
+       /* Read the file 1 byte at a time. */\r
+       for( iByte = 0; iByte < fsPUTC_FILE_SIZE; iByte++ )\r
+       {\r
+               iReturned = f_getc( pxFile );\r
+               configASSERT( iReturned ==  ( ( int ) '0' + iByte ) );\r
+       }\r
+\r
+       /* Finished so close the file. */\r
+       f_close( pxFile );\r
+\r
+       /* Move back to the root directory. */\r
+       ucReturn = f_chdir( "../.." );\r
+       configASSERT( ucReturn == F_NO_ERROR );\r
+\r
+       /* Obtain and print out the working directory. */\r
+       f_getcwd( cRAMBuffer, fsRAM_BUFFER_SIZE );\r
+       printf( "Back in root directory %s\r\n", cRAMBuffer );\r
+}\r
+\r
+\r
+\r
+\r
diff --git a/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/FreeRTOS_Plus_FAT_SL_with_CLI.sln b/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/FreeRTOS_Plus_FAT_SL_with_CLI.sln
new file mode 100644 (file)
index 0000000..3f819af
--- /dev/null
@@ -0,0 +1,20 @@
+\r
+Microsoft Visual Studio Solution File, Format Version 11.00\r
+# Visual C++ Express 2010\r
+Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "WIN32", "WIN32.vcxproj", "{C686325E-3261-42F7-AEB1-DDE5280E1CEB}"\r
+EndProject\r
+Global\r
+       GlobalSection(SolutionConfigurationPlatforms) = preSolution\r
+               Debug|Win32 = Debug|Win32\r
+               Release|Win32 = Release|Win32\r
+       EndGlobalSection\r
+       GlobalSection(ProjectConfigurationPlatforms) = postSolution\r
+               {C686325E-3261-42F7-AEB1-DDE5280E1CEB}.Debug|Win32.ActiveCfg = Debug|Win32\r
+               {C686325E-3261-42F7-AEB1-DDE5280E1CEB}.Debug|Win32.Build.0 = Debug|Win32\r
+               {C686325E-3261-42F7-AEB1-DDE5280E1CEB}.Release|Win32.ActiveCfg = Release|Win32\r
+               {C686325E-3261-42F7-AEB1-DDE5280E1CEB}.Release|Win32.Build.0 = Release|Win32\r
+       EndGlobalSection\r
+       GlobalSection(SolutionProperties) = preSolution\r
+               HideSolutionNode = FALSE\r
+       EndGlobalSection\r
+EndGlobal\r
diff --git a/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/READ_ME.url b/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/READ_ME.url
new file mode 100644 (file)
index 0000000..9c6b614
--- /dev/null
@@ -0,0 +1,5 @@
+[InternetShortcut]\r
+URL=http://www.freertos.org/FreeRTOS-Plus/FreeRTOS_Plus_FAT_SL/Demos/File_System_Win32_Simulator_demo.shtml\r
+IDList=\r
+[{000214A0-0000-0000-C000-000000000046}]\r
+Prop3=19,2\r
diff --git a/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/Run-time-stats-utils.c b/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/Run-time-stats-utils.c
new file mode 100644 (file)
index 0000000..40dca76
--- /dev/null
@@ -0,0 +1,137 @@
+/*\r
+    FreeRTOS V7.4.0 - Copyright (C) 2013 Real Time Engineers Ltd.\r
+\r
+    FEATURES AND PORTS ARE ADDED TO FREERTOS ALL THE TIME.  PLEASE VISIT\r
+    http://www.FreeRTOS.org TO ENSURE YOU ARE USING THE LATEST VERSION.\r
+\r
+    ***************************************************************************\r
+     *                                                                       *\r
+     *    FreeRTOS tutorial books are available in pdf and paperback.        *\r
+     *    Complete, revised, and edited pdf reference manuals are also       *\r
+     *    available.                                                         *\r
+     *                                                                       *\r
+     *    Purchasing FreeRTOS documentation will not only help you, by       *\r
+     *    ensuring you get running as quickly as possible and with an        *\r
+     *    in-depth knowledge of how to use FreeRTOS, it will also help       *\r
+     *    the FreeRTOS project to continue with its mission of providing     *\r
+     *    professional grade, cross platform, de facto standard solutions    *\r
+     *    for microcontrollers - completely free of charge!                  *\r
+     *                                                                       *\r
+     *    >>> See http://www.FreeRTOS.org/Documentation for details. <<<     *\r
+     *                                                                       *\r
+     *    Thank you for using FreeRTOS, and thank you for your support!      *\r
+     *                                                                       *\r
+    ***************************************************************************\r
+\r
+\r
+    This file is part of the FreeRTOS distribution.\r
+\r
+    FreeRTOS is free software; you can redistribute it and/or modify it under\r
+    the terms of the GNU General Public License (version 2) as published by the\r
+    Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+\r
+    >>>>>>NOTE<<<<<< The modification to the GPL is included to allow you to\r
+    distribute a combined work that includes FreeRTOS without being obliged to\r
+    provide the source code for proprietary components outside of the FreeRTOS\r
+    kernel.\r
+\r
+    FreeRTOS is distributed in the hope that it will be useful, but WITHOUT ANY\r
+    WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS\r
+    FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more\r
+    details. You should have received a copy of the GNU General Public License\r
+    and the FreeRTOS license exception along with FreeRTOS; if not itcan be\r
+    viewed here: http://www.freertos.org/a00114.html and also obtained by\r
+    writing to Real Time Engineers Ltd., contact details for whom are available\r
+    on the FreeRTOS WEB site.\r
+\r
+    1 tab == 4 spaces!\r
+\r
+    ***************************************************************************\r
+     *                                                                       *\r
+     *    Having a problem?  Start by reading the FAQ "My application does   *\r
+     *    not run, what could be wrong?"                                     *\r
+     *                                                                       *\r
+     *    http://www.FreeRTOS.org/FAQHelp.html                               *\r
+     *                                                                       *\r
+    ***************************************************************************\r
+\r
+\r
+    http://www.FreeRTOS.org - Documentation, books, training, latest versions, \r
+    license and Real Time Engineers Ltd. contact details.\r
+\r
+    http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+    including FreeRTOS+Trace - an indispensable productivity tool, and our new\r
+    fully thread aware and reentrant UDP/IP stack.\r
+\r
+    http://www.OpenRTOS.com - Real Time Engineers ltd license FreeRTOS to High \r
+    Integrity Systems, who sell the code with commercial support, \r
+    indemnification and middleware, under the OpenRTOS brand.\r
+    \r
+    http://www.SafeRTOS.com - High Integrity Systems also provide a safety \r
+    engineered and independently SIL3 certified version for use in safety and \r
+    mission critical applications that require provable dependability.\r
+*/\r
+\r
+/*\r
+ * Utility functions required to gather run time statistics.  See:\r
+ * http://www.freertos.org/rtos-run-time-stats.html\r
+ *\r
+ * Note that this is a simulated port, where simulated time is a lot slower than\r
+ * real time, therefore the run time counter values have no real meaningful\r
+ * units.\r
+ *\r
+ * Also note that it is assumed this demo is going to be used for short periods\r
+ * of time only, and therefore timer overflows are not handled.\r
+*/\r
+\r
+/* FreeRTOS includes. */\r
+#include <FreeRTOS.h>\r
+\r
+/* Variables used in the creation of the run time stats time base.  Run time \r
+stats record how much time each task spends in the Running state. */\r
+static long long llInitialRunTimeCounterValue = 0LL, llTicksPerHundedthMillisecond = 0LL;\r
+\r
+/*-----------------------------------------------------------*/\r
+\r
+void vConfigureTimerForRunTimeStats( void )\r
+{\r
+LARGE_INTEGER liPerformanceCounterFrequency, liInitialRunTimeValue;\r
+\r
+       /* Initialise the variables used to create the run time stats time base.\r
+       Run time stats record how much time each task spends in the Running \r
+       state. */\r
+\r
+       if( QueryPerformanceFrequency( &liPerformanceCounterFrequency ) == 0 )\r
+       {\r
+               llTicksPerHundedthMillisecond = 1;\r
+       }\r
+       else\r
+       {\r
+               /* How many times does the performance counter increment in 1/100th\r
+               millisecond. */\r
+               llTicksPerHundedthMillisecond = liPerformanceCounterFrequency.QuadPart / 100000LL;\r
+\r
+               /* What is the performance counter value now, this will be subtracted\r
+               from readings taken at run time. */\r
+               QueryPerformanceCounter( &liInitialRunTimeValue );\r
+               llInitialRunTimeCounterValue = liInitialRunTimeValue.QuadPart;\r
+       }\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+unsigned long ulGetRunTimeCounterValue( void )\r
+{\r
+LARGE_INTEGER liCurrentCount;\r
+unsigned long ulReturn;\r
+\r
+       /* What is the performance counter value now? */\r
+       QueryPerformanceCounter( &liCurrentCount );\r
+\r
+       /* Subtract the performance counter value reading taken when the \r
+       application started to get a count from that reference point, then\r
+       scale to (simulated) 1/100ths of a millisecond. */\r
+       ulReturn = ( unsigned long ) ( ( liCurrentCount.QuadPart - llInitialRunTimeCounterValue ) / llTicksPerHundedthMillisecond );\r
+\r
+       return ulReturn;\r
+}\r
+/*-----------------------------------------------------------*/\r
diff --git a/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/Sample-CLI-commands.c b/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/Sample-CLI-commands.c
new file mode 100644 (file)
index 0000000..1fccb84
--- /dev/null
@@ -0,0 +1,426 @@
+/*\r
+    FreeRTOS V7.4.0 - Copyright (C) 2013 Real Time Engineers Ltd.\r
+\r
+    FEATURES AND PORTS ARE ADDED TO FREERTOS ALL THE TIME.  PLEASE VISIT\r
+    http://www.FreeRTOS.org TO ENSURE YOU ARE USING THE LATEST VERSION.\r
+\r
+    ***************************************************************************\r
+     *                                                                       *\r
+     *    FreeRTOS tutorial books are available in pdf and paperback.        *\r
+     *    Complete, revised, and edited pdf reference manuals are also       *\r
+     *    available.                                                         *\r
+     *                                                                       *\r
+     *    Purchasing FreeRTOS documentation will not only help you, by       *\r
+     *    ensuring you get running as quickly as possible and with an        *\r
+     *    in-depth knowledge of how to use FreeRTOS, it will also help       *\r
+     *    the FreeRTOS project to continue with its mission of providing     *\r
+     *    professional grade, cross platform, de facto standard solutions    *\r
+     *    for microcontrollers - completely free of charge!                  *\r
+     *                                                                       *\r
+     *    >>> See http://www.FreeRTOS.org/Documentation for details. <<<     *\r
+     *                                                                       *\r
+     *    Thank you for using FreeRTOS, and thank you for your support!      *\r
+     *                                                                       *\r
+    ***************************************************************************\r
+\r
+\r
+    This file is part of the FreeRTOS distribution.\r
+\r
+    FreeRTOS is free software; you can redistribute it and/or modify it under\r
+    the terms of the GNU General Public License (version 2) as published by the\r
+    Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+\r
+    >>>>>>NOTE<<<<<< The modification to the GPL is included to allow you to\r
+    distribute a combined work that includes FreeRTOS without being obliged to\r
+    provide the source code for proprietary components outside of the FreeRTOS\r
+    kernel.\r
+\r
+    FreeRTOS is distributed in the hope that it will be useful, but WITHOUT ANY\r
+    WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS\r
+    FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more\r
+    details. You should have received a copy of the GNU General Public License\r
+    and the FreeRTOS license exception along with FreeRTOS; if not itcan be\r
+    viewed here: http://www.freertos.org/a00114.html and also obtained by\r
+    writing to Real Time Engineers Ltd., contact details for whom are available\r
+    on the FreeRTOS WEB site.\r
+\r
+    1 tab == 4 spaces!\r
+\r
+    ***************************************************************************\r
+     *                                                                       *\r
+     *    Having a problem?  Start by reading the FAQ "My application does   *\r
+     *    not run, what could be wrong?"                                     *\r
+     *                                                                       *\r
+     *    http://www.FreeRTOS.org/FAQHelp.html                               *\r
+     *                                                                       *\r
+    ***************************************************************************\r
+\r
+\r
+    http://www.FreeRTOS.org - Documentation, books, training, latest versions, \r
+    license and Real Time Engineers Ltd. contact details.\r
+\r
+    http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+    including FreeRTOS+Trace - an indispensable productivity tool, and our new\r
+    fully thread aware and reentrant UDP/IP stack.\r
+\r
+    http://www.OpenRTOS.com - Real Time Engineers ltd license FreeRTOS to High \r
+    Integrity Systems, who sell the code with commercial support, \r
+    indemnification and middleware, under the OpenRTOS brand.\r
+    \r
+    http://www.SafeRTOS.com - High Integrity Systems also provide a safety \r
+    engineered and independently SIL3 certified version for use in safety and \r
+    mission critical applications that require provable dependability.\r
+*/\r
+\r
+ /******************************************************************************\r
+ *\r
+ * See the following URL for information on the commands defined in this file:\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus/FreeRTOS_Plus_UDP/Embedded_Ethernet_Examples/Ethernet_Related_CLI_Commands.shtml\r
+ *\r
+ ******************************************************************************/\r
+\r
+\r
+/* FreeRTOS includes. */\r
+#include "FreeRTOS.h"\r
+#include "task.h"\r
+\r
+/* Standard includes. */\r
+#include <stdint.h>\r
+#include <stdio.h>\r
+#include <stdlib.h>\r
+\r
+/* FreeRTOS+CLI includes. */\r
+#include "FreeRTOS_CLI.h"\r
+\r
+#ifndef  configINCLUDE_TRACE_RELATED_CLI_COMMANDS\r
+       #define configINCLUDE_TRACE_RELATED_CLI_COMMANDS 0\r
+#endif\r
+\r
+\r
+/*\r
+ * Implements the run-time-stats command.\r
+ */\r
+static portBASE_TYPE prvTaskStatsCommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString );\r
+\r
+/*\r
+ * Implements the task-stats command.\r
+ */\r
+static portBASE_TYPE prvRunTimeStatsCommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString );\r
+\r
+/*\r
+ * Implements the echo-three-parameters command.\r
+ */\r
+static portBASE_TYPE prvThreeParameterEchoCommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString );\r
+\r
+/*\r
+ * Implements the echo-parameters command.\r
+ */\r
+static portBASE_TYPE prvParameterEchoCommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString );\r
+\r
+/*\r
+ * Implements the "trace start" and "trace stop" commands;\r
+ */\r
+#if configINCLUDE_TRACE_RELATED_CLI_COMMANDS == 1\r
+       static portBASE_TYPE prvStartStopTraceCommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString );\r
+#endif\r
+\r
+/* Structure that defines the "run-time-stats" command line command.   This\r
+generates a table that shows how much run time each task has */\r
+static const CLI_Command_Definition_t xRunTimeStats =\r
+{\r
+       ( const int8_t * const ) "run-time-stats", /* The command string to type. */\r
+       ( const int8_t * const ) "\r\nrun-time-stats:\r\n Displays a table showing how much processing time each FreeRTOS task has used\r\n",\r
+       prvRunTimeStatsCommand, /* The function to run. */\r
+       0 /* No parameters are expected. */\r
+};\r
+\r
+/* Structure that defines the "task-stats" command line command.  This generates\r
+a table that gives information on each task in the system. */\r
+static const CLI_Command_Definition_t xTaskStats =\r
+{\r
+       ( const int8_t * const ) "task-stats", /* The command string to type. */\r
+       ( const int8_t * const ) "\r\ntask-stats:\r\n Displays a table showing the state of each FreeRTOS task\r\n",\r
+       prvTaskStatsCommand, /* The function to run. */\r
+       0 /* No parameters are expected. */\r
+};\r
+\r
+/* Structure that defines the "echo_3_parameters" command line command.  This\r
+takes exactly three parameters that the command simply echos back one at a\r
+time. */\r
+static const CLI_Command_Definition_t xThreeParameterEcho =\r
+{\r
+       ( const int8_t * const ) "echo-3-parameters",\r
+       ( const int8_t * const ) "\r\necho-3-parameters <param1> <param2> <param3>:\r\n Expects three parameters, echos each in turn\r\n",\r
+       prvThreeParameterEchoCommand, /* The function to run. */\r
+       3 /* Three parameters are expected, which can take any value. */\r
+};\r
+\r
+/* Structure that defines the "echo_parameters" command line command.  This\r
+takes a variable number of parameters that the command simply echos back one at\r
+a time. */\r
+static const CLI_Command_Definition_t xParameterEcho =\r
+{\r
+       ( const int8_t * const ) "echo-parameters",\r
+       ( const int8_t * const ) "\r\necho-parameters <...>:\r\n Take variable number of parameters, echos each in turn\r\n",\r
+       prvParameterEchoCommand, /* The function to run. */\r
+       -1 /* The user can enter any number of commands. */\r
+};\r
+\r
+#if configINCLUDE_TRACE_RELATED_CLI_COMMANDS == 1\r
+       /* Structure that defines the "trace" command line command.  This takes a single\r
+       parameter, which can be either "start" or "stop". */\r
+       static const CLI_Command_Definition_t xStartStopTrace =\r
+       {\r
+               ( const int8_t * const ) "trace",\r
+               ( const int8_t * const ) "\r\ntrace [start | stop]:\r\n Starts or stops a trace recording for viewing in FreeRTOS+Trace\r\n",\r
+               prvStartStopTraceCommand, /* The function to run. */\r
+               1 /* One parameter is expected.  Valid values are "start" and "stop". */\r
+       };\r
+#endif /* configINCLUDE_TRACE_RELATED_CLI_COMMANDS */\r
+\r
+/*-----------------------------------------------------------*/\r
+\r
+void vRegisterSampleCLICommands( void )\r
+{\r
+       /* Register all the command line commands defined immediately above. */\r
+       FreeRTOS_CLIRegisterCommand( &xTaskStats );\r
+       FreeRTOS_CLIRegisterCommand( &xRunTimeStats );\r
+       FreeRTOS_CLIRegisterCommand( &xThreeParameterEcho );\r
+       FreeRTOS_CLIRegisterCommand( &xParameterEcho );\r
+\r
+       #if( configINCLUDE_TRACE_RELATED_CLI_COMMANDS == 1 )\r
+       {\r
+               FreeRTOS_CLIRegisterCommand( & xStartStopTrace );\r
+       }\r
+       #endif\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static portBASE_TYPE prvTaskStatsCommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString )\r
+{\r
+const int8_t *const pcHeader = ( int8_t * ) "Task          State  Priority  Stack      #\r\n************************************************\r\n";\r
+\r
+       /* Remove compile time warnings about unused parameters, and check the\r
+       write buffer is not NULL.  NOTE - for simplicity, this example assumes the\r
+       write buffer length is adequate, so does not check for buffer overflows. */\r
+       ( void ) pcCommandString;\r
+       ( void ) xWriteBufferLen;\r
+       configASSERT( pcWriteBuffer );\r
+\r
+       /* Generate a table of task stats. */\r
+       strcpy( ( char * ) pcWriteBuffer, ( char * ) pcHeader );\r
+       vTaskList( pcWriteBuffer + strlen( ( char * ) pcHeader ) );\r
+\r
+       /* There is no more data to return after this single string, so return\r
+       pdFALSE. */\r
+       return pdFALSE;\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static portBASE_TYPE prvRunTimeStatsCommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString )\r
+{\r
+const int8_t * const pcHeader = ( int8_t * ) "Task            Abs Time      % Time\r\n****************************************\r\n";\r
+\r
+       /* Remove compile time warnings about unused parameters, and check the\r
+       write buffer is not NULL.  NOTE - for simplicity, this example assumes the\r
+       write buffer length is adequate, so does not check for buffer overflows. */\r
+       ( void ) pcCommandString;\r
+       ( void ) xWriteBufferLen;\r
+       configASSERT( pcWriteBuffer );\r
+\r
+       /* Generate a table of task stats. */\r
+       strcpy( ( char * ) pcWriteBuffer, ( char * ) pcHeader );\r
+       vTaskGetRunTimeStats( pcWriteBuffer + strlen( ( char * ) pcHeader ) );\r
+\r
+       /* There is no more data to return after this single string, so return\r
+       pdFALSE. */\r
+       return pdFALSE;\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static portBASE_TYPE prvThreeParameterEchoCommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString )\r
+{\r
+int8_t *pcParameter;\r
+portBASE_TYPE xParameterStringLength, xReturn;\r
+static portBASE_TYPE lParameterNumber = 0;\r
+\r
+       /* Remove compile time warnings about unused parameters, and check the\r
+       write buffer is not NULL.  NOTE - for simplicity, this example assumes the\r
+       write buffer length is adequate, so does not check for buffer overflows. */\r
+       ( void ) pcCommandString;\r
+       ( void ) xWriteBufferLen;\r
+       configASSERT( pcWriteBuffer );\r
+\r
+       if( lParameterNumber == 0 )\r
+       {\r
+               /* The first time the function is called after the command has been\r
+               entered just a header string is returned. */\r
+               sprintf( ( char * ) pcWriteBuffer, "The three parameters were:\r\n" );\r
+\r
+               /* Next time the function is called the first parameter will be echoed\r
+               back. */\r
+               lParameterNumber = 1L;\r
+\r
+               /* There is more data to be returned as no parameters have been echoed\r
+               back yet. */\r
+               xReturn = pdPASS;\r
+       }\r
+       else\r
+       {\r
+               /* Obtain the parameter string. */\r
+               pcParameter = ( int8_t * ) FreeRTOS_CLIGetParameter\r
+                                                                       (\r
+                                                                               pcCommandString,                /* The command string itself. */\r
+                                                                               lParameterNumber,               /* Return the next parameter. */\r
+                                                                               &xParameterStringLength /* Store the parameter string length. */\r
+                                                                       );\r
+\r
+               /* Sanity check something was returned. */\r
+               configASSERT( pcParameter );\r
+\r
+               /* Return the parameter string. */\r
+               memset( pcWriteBuffer, 0x00, xWriteBufferLen );\r
+               sprintf( ( char * ) pcWriteBuffer, "%d: ", ( int ) lParameterNumber );\r
+               strncat( ( char * ) pcWriteBuffer, ( const char * ) pcParameter, xParameterStringLength );\r
+               strncat( ( char * ) pcWriteBuffer, "\r\n", strlen( "\r\n" ) );\r
+\r
+               /* If this is the last of the three parameters then there are no more\r
+               strings to return after this one. */\r
+               if( lParameterNumber == 3L )\r
+               {\r
+                       /* If this is the last of the three parameters then there are no more\r
+                       strings to return after this one. */\r
+                       xReturn = pdFALSE;\r
+                       lParameterNumber = 0L;\r
+               }\r
+               else\r
+               {\r
+                       /* There are more parameters to return after this one. */\r
+                       xReturn = pdTRUE;\r
+                       lParameterNumber++;\r
+               }\r
+       }\r
+\r
+       return xReturn;\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static portBASE_TYPE prvParameterEchoCommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString )\r
+{\r
+int8_t *pcParameter;\r
+portBASE_TYPE xParameterStringLength, xReturn;\r
+static portBASE_TYPE lParameterNumber = 0;\r
+\r
+       /* Remove compile time warnings about unused parameters, and check the\r
+       write buffer is not NULL.  NOTE - for simplicity, this example assumes the\r
+       write buffer length is adequate, so does not check for buffer overflows. */\r
+       ( void ) pcCommandString;\r
+       ( void ) xWriteBufferLen;\r
+       configASSERT( pcWriteBuffer );\r
+\r
+       if( lParameterNumber == 0 )\r
+       {\r
+               /* The first time the function is called after the command has been\r
+               entered just a header string is returned. */\r
+               sprintf( ( char * ) pcWriteBuffer, "The parameters were:\r\n" );\r
+\r
+               /* Next time the function is called the first parameter will be echoed\r
+               back. */\r
+               lParameterNumber = 1L;\r
+\r
+               /* There is more data to be returned as no parameters have been echoed\r
+               back yet. */\r
+               xReturn = pdPASS;\r
+       }\r
+       else\r
+       {\r
+               /* Obtain the parameter string. */\r
+               pcParameter = ( int8_t * ) FreeRTOS_CLIGetParameter\r
+                                                                       (\r
+                                                                               pcCommandString,                /* The command string itself. */\r
+                                                                               lParameterNumber,               /* Return the next parameter. */\r
+                                                                               &xParameterStringLength /* Store the parameter string length. */\r
+                                                                       );\r
+\r
+               if( pcParameter != NULL )\r
+               {\r
+                       /* Return the parameter string. */\r
+                       memset( pcWriteBuffer, 0x00, xWriteBufferLen );\r
+                       sprintf( ( char * ) pcWriteBuffer, "%d: ", ( int ) lParameterNumber );\r
+                       strncat( ( char * ) pcWriteBuffer, ( const char * ) pcParameter, xParameterStringLength );\r
+                       strncat( ( char * ) pcWriteBuffer, "\r\n", strlen( "\r\n" ) );\r
+\r
+                       /* There might be more parameters to return after this one. */\r
+                       xReturn = pdTRUE;\r
+                       lParameterNumber++;\r
+               }\r
+               else\r
+               {\r
+                       /* No more parameters were found.  Make sure the write buffer does\r
+                       not contain a valid string. */\r
+                       pcWriteBuffer[ 0 ] = 0x00;\r
+\r
+                       /* No more data to return. */\r
+                       xReturn = pdFALSE;\r
+\r
+                       /* Start over the next time this command is executed. */\r
+                       lParameterNumber = 0;\r
+               }\r
+       }\r
+\r
+       return xReturn;\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+#if configINCLUDE_TRACE_RELATED_CLI_COMMANDS == 1\r
+\r
+       static portBASE_TYPE prvStartStopTraceCommand( int8_t *pcWriteBuffer, size_t xWriteBufferLen, const int8_t *pcCommandString )\r
+       {\r
+       int8_t *pcParameter;\r
+       portBASE_TYPE lParameterStringLength;\r
+\r
+               /* Remove compile time warnings about unused parameters, and check the\r
+               write buffer is not NULL.  NOTE - for simplicity, this example assumes the\r
+               write buffer length is adequate, so does not check for buffer overflows. */\r
+               ( void ) pcCommandString;\r
+               ( void ) xWriteBufferLen;\r
+               configASSERT( pcWriteBuffer );\r
+\r
+               /* Obtain the parameter string. */\r
+               pcParameter = ( int8_t * ) FreeRTOS_CLIGetParameter\r
+                                                                       (\r
+                                                                               pcCommandString,                /* The command string itself. */\r
+                                                                               1,                                              /* Return the first parameter. */\r
+                                                                               &lParameterStringLength /* Store the parameter string length. */\r
+                                                                       );\r
+\r
+               /* Sanity check something was returned. */\r
+               configASSERT( pcParameter );\r
+\r
+               /* There are only two valid parameter values. */\r
+               if( strncmp( ( const char * ) pcParameter, "start", strlen( "start" ) ) == 0 )\r
+               {\r
+                       /* Start or restart the trace. */\r
+                       vTraceStop();\r
+                       vTraceClear();\r
+                       vTraceStart();\r
+\r
+                       sprintf( ( char * ) pcWriteBuffer, "Trace recording (re)started.\r\n" );\r
+               }\r
+               else if( strncmp( ( const char * ) pcParameter, "stop", strlen( "stop" ) ) == 0 )\r
+               {\r
+                       /* End the trace, if one is running. */\r
+                       vTraceStop();\r
+                       sprintf( ( char * ) pcWriteBuffer, "Stopping trace recording.\r\n" );\r
+               }\r
+               else\r
+               {\r
+                       sprintf( ( char * ) pcWriteBuffer, "Valid parameters are 'start' and 'stop'.\r\n" );\r
+               }\r
+\r
+               /* There is no more data to return after this single string, so return\r
+               pdFALSE. */\r
+               return pdFALSE;\r
+       }\r
+\r
+#endif /* configINCLUDE_TRACE_RELATED_CLI_COMMANDS */\r
diff --git a/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/UDPCommandServer.c b/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/UDPCommandServer.c
new file mode 100644 (file)
index 0000000..f5f65cf
--- /dev/null
@@ -0,0 +1,276 @@
+/*\r
+    FreeRTOS V7.4.0 - Copyright (C) 2013 Real Time Engineers Ltd.\r
+\r
+    FEATURES AND PORTS ARE ADDED TO FREERTOS ALL THE TIME.  PLEASE VISIT\r
+    http://www.FreeRTOS.org TO ENSURE YOU ARE USING THE LATEST VERSION.\r
+\r
+    ***************************************************************************\r
+     *                                                                       *\r
+     *    FreeRTOS tutorial books are available in pdf and paperback.        *\r
+     *    Complete, revised, and edited pdf reference manuals are also       *\r
+     *    available.                                                         *\r
+     *                                                                       *\r
+     *    Purchasing FreeRTOS documentation will not only help you, by       *\r
+     *    ensuring you get running as quickly as possible and with an        *\r
+     *    in-depth knowledge of how to use FreeRTOS, it will also help       *\r
+     *    the FreeRTOS project to continue with its mission of providing     *\r
+     *    professional grade, cross platform, de facto standard solutions    *\r
+     *    for microcontrollers - completely free of charge!                  *\r
+     *                                                                       *\r
+     *    >>> See http://www.FreeRTOS.org/Documentation for details. <<<     *\r
+     *                                                                       *\r
+     *    Thank you for using FreeRTOS, and thank you for your support!      *\r
+     *                                                                       *\r
+    ***************************************************************************\r
+\r
+\r
+    This file is part of the FreeRTOS distribution.\r
+\r
+    FreeRTOS is free software; you can redistribute it and/or modify it under\r
+    the terms of the GNU General Public License (version 2) as published by the\r
+    Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+\r
+    >>>>>>NOTE<<<<<< The modification to the GPL is included to allow you to\r
+    distribute a combined work that includes FreeRTOS without being obliged to\r
+    provide the source code for proprietary components outside of the FreeRTOS\r
+    kernel.\r
+\r
+    FreeRTOS is distributed in the hope that it will be useful, but WITHOUT ANY\r
+    WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS\r
+    FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more\r
+    details. You should have received a copy of the GNU General Public License\r
+    and the FreeRTOS license exception along with FreeRTOS; if not itcan be\r
+    viewed here: http://www.freertos.org/a00114.html and also obtained by\r
+    writing to Real Time Engineers Ltd., contact details for whom are available\r
+    on the FreeRTOS WEB site.\r
+\r
+    1 tab == 4 spaces!\r
+\r
+    ***************************************************************************\r
+     *                                                                       *\r
+     *    Having a problem?  Start by reading the FAQ "My application does   *\r
+     *    not run, what could be wrong?"                                     *\r
+     *                                                                       *\r
+     *    http://www.FreeRTOS.org/FAQHelp.html                               *\r
+     *                                                                       *\r
+    ***************************************************************************\r
+\r
+\r
+    http://www.FreeRTOS.org - Documentation, books, training, latest versions,\r
+    license and Real Time Engineers Ltd. contact details.\r
+\r
+    http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+    including FreeRTOS+Trace - an indispensable productivity tool, and our new\r
+    fully thread aware and reentrant UDP/IP stack.\r
+\r
+    http://www.OpenRTOS.com - Real Time Engineers ltd license FreeRTOS to High\r
+    Integrity Systems, who sell the code with commercial support,\r
+    indemnification and middleware, under the OpenRTOS brand.\r
+\r
+    http://www.SafeRTOS.com - High Integrity Systems also provide a safety\r
+    engineered and independently SIL3 certified version for use in safety and\r
+    mission critical applications that require provable dependability.\r
+*/\r
+\r
+\r
+#pragma comment( lib, "ws2_32.lib" )\r
+\r
+/* Win32 includes. */\r
+#include <WinSock2.h>\r
+\r
+/* FreeRTOS includes. */\r
+#include "FreeRTOS.h"\r
+#include "task.h"\r
+\r
+/* Standard includes. */\r
+#include <stdint.h>\r
+#include <stdio.h>\r
+\r
+/* FreeRTOS+CLI includes. */\r
+#include "FreeRTOS_CLI.h"\r
+\r
+/* Dimensions the buffer into which input characters are placed. */\r
+#define cmdMAX_INPUT_SIZE      60\r
+\r
+/* Dimensions the buffer into which string outputs can be placed. */\r
+#define cmdMAX_OUTPUT_SIZE     1024\r
+\r
+/* Dimensions the buffer passed to the recvfrom() call. */\r
+#define cmdSOCKET_INPUT_BUFFER_SIZE 60\r
+\r
+/* DEL acts as a backspace. */\r
+#define cmdASCII_DEL           ( 0x7F )\r
+\r
+/*\r
+ * Open and configure the UDP socket.\r
+ */\r
+static SOCKET prvOpenUDPSocket( void );\r
+\r
+/*-----------------------------------------------------------*/\r
+\r
+/*\r
+ * Task that provides the input and output for the FreeRTOS+CLI command\r
+ * interpreter.  In this case a WinSock UDP port is used for convenience as this\r
+ * demo runs in a simulated environment on a Windows PC.  See the URL in the\r
+ * comments within main.c for the location of the online documentation.\r
+ */\r
+void vUDPCommandInterpreterTask( void *pvParameters )\r
+{\r
+long lBytes, lByte;\r
+signed char cInChar, cInputIndex = 0;\r
+static signed char cInputString[ cmdMAX_INPUT_SIZE ], cOutputString[ cmdMAX_OUTPUT_SIZE ], cLocalBuffer[ cmdSOCKET_INPUT_BUFFER_SIZE ];\r
+portBASE_TYPE xMoreDataToFollow;\r
+volatile int iErrorCode = 0;\r
+struct sockaddr_in xClient;\r
+int xClientAddressLength = sizeof( struct sockaddr_in );\r
+SOCKET xSocket;\r
+\r
+       /* Just to prevent compiler warnings. */\r
+       ( void ) pvParameters;\r
+\r
+       /* Attempt to open the socket. */\r
+       xSocket = prvOpenUDPSocket();\r
+\r
+       if( xSocket != INVALID_SOCKET )\r
+       {\r
+               for( ;; )\r
+               {\r
+                       /* Wait for incoming data on the opened socket. */\r
+                       lBytes = recvfrom( xSocket, cLocalBuffer, sizeof( cLocalBuffer ), 0, ( struct sockaddr * ) &xClient, &xClientAddressLength );\r
+\r
+                       if( lBytes == SOCKET_ERROR )\r
+                       {\r
+                               /* Something went wrong, but it is not handled by this simple\r
+                               example. */\r
+                               iErrorCode = WSAGetLastError();\r
+                       }\r
+                       else\r
+                       {\r
+                               /* Process each received byte in turn. */\r
+                               lByte = 0;\r
+                               while( lByte < lBytes )\r
+                               {\r
+                                       /* The next character in the input buffer. */\r
+                                       cInChar = cLocalBuffer[ lByte ];\r
+                                       lByte++;\r
+\r
+                                       /* Newline characters are taken as the end of the command\r
+                                       string. */\r
+                                       if( cInChar == '\n' )\r
+                                       {\r
+                                               /* Process the input string received prior to the\r
+                                               newline. */\r
+                                               do\r
+                                               {\r
+                                                       /* Pass the string to FreeRTOS+CLI. */\r
+                                                       xMoreDataToFollow = FreeRTOS_CLIProcessCommand( cInputString, cOutputString, cmdMAX_OUTPUT_SIZE );\r
+\r
+                                                       /* Send the output generated by the command's\r
+                                                       implementation. */\r
+                                                       sendto( xSocket, cOutputString,  strlen( cOutputString ), 0, ( SOCKADDR * ) &xClient, xClientAddressLength );\r
+\r
+                                               } while( xMoreDataToFollow != pdFALSE ); /* Until the command does not generate any more output. */\r
+\r
+                                               /* All the strings generated by the command processing\r
+                                               have been sent.  Clear the input string ready to receive\r
+                                               the next command. */\r
+                                               cInputIndex = 0;\r
+                                               memset( cInputString, 0x00, cmdMAX_INPUT_SIZE );\r
+\r
+                                               /* Transmit a spacer, just to make the command console\r
+                                               easier to read. */\r
+                                               sendto( xSocket, "\r\n",  strlen( "\r\n" ), 0, ( SOCKADDR * ) &xClient, xClientAddressLength );\r
+                                       }\r
+                                       else\r
+                                       {\r
+                                               if( cInChar == '\r' )\r
+                                               {\r
+                                                       /* Ignore the character.  Newlines are used to\r
+                                                       detect the end of the input string. */\r
+                                               }\r
+                                               else if( ( cInChar == '\b' ) || ( cInChar == cmdASCII_DEL ) )\r
+                                               {\r
+                                                       /* Backspace was pressed.  Erase the last character\r
+                                                       in the string - if any. */\r
+                                                       if( cInputIndex > 0 )\r
+                                                       {\r
+                                                               cInputIndex--;\r
+                                                               cInputString[ cInputIndex ] = '\0';\r
+                                                       }\r
+                                               }\r
+                                               else\r
+                                               {\r
+                                                       /* A character was entered.  Add it to the string\r
+                                                       entered so far.  When a \n is entered the complete\r
+                                                       string will be passed to the command interpreter. */\r
+                                                       if( cInputIndex < cmdMAX_INPUT_SIZE )\r
+                                                       {\r
+                                                               cInputString[ cInputIndex ] = cInChar;\r
+                                                               cInputIndex++;\r
+                                                       }\r
+                                               }\r
+                                       }\r
+                               }\r
+                       }\r
+               }\r
+       }\r
+       else\r
+       {\r
+               /* The socket could not be opened. */\r
+               vTaskDelete( NULL );\r
+       }\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+static SOCKET prvOpenUDPSocket( void )\r
+{\r
+WSADATA xWSAData;\r
+WORD wVersionRequested;\r
+struct sockaddr_in xServer;\r
+SOCKET xSocket = INVALID_SOCKET;\r
+\r
+       wVersionRequested = MAKEWORD( 2, 2 );\r
+\r
+       /* Prepare to use WinSock. */\r
+       if( WSAStartup( wVersionRequested, &xWSAData ) != 0 )\r
+       {\r
+               fprintf( stderr, "Could not open Windows connection.\n" );\r
+       }\r
+       else\r
+       {\r
+               xSocket = socket( AF_INET, SOCK_DGRAM, 0 );\r
+               if( xSocket == INVALID_SOCKET)\r
+               {\r
+                       fprintf( stderr, "Could not create socket.\n" );\r
+                       WSACleanup();\r
+               }\r
+               else\r
+               {\r
+                       /* Zero out the server structure. */\r
+                       memset( ( void * ) &xServer, 0x00, sizeof( struct sockaddr_in ) );\r
+\r
+                       /* Set family and port. */\r
+                       xServer.sin_family = AF_INET;\r
+                       xServer.sin_port = htons( configUDP_CLI_PORT_NUMBER );\r
+\r
+                       /* Assign the loopback address */\r
+                       xServer.sin_addr.S_un.S_un_b.s_b1 = 127;\r
+                       xServer.sin_addr.S_un.S_un_b.s_b2 = 0;\r
+                       xServer.sin_addr.S_un.S_un_b.s_b3 = 0;\r
+                       xServer.sin_addr.S_un.S_un_b.s_b4 = 1;\r
+\r
+                       /* Bind the address to the socket. */\r
+                       if( bind( xSocket, ( struct sockaddr * ) &xServer, sizeof( struct sockaddr_in ) ) == -1 )\r
+                       {\r
+                               fprintf( stderr, "Could not socket to port %d.\n", configUDP_CLI_PORT_NUMBER );\r
+                               closesocket( xSocket );\r
+                               xSocket = INVALID_SOCKET;\r
+                               WSACleanup();\r
+                       }\r
+               }\r
+       }\r
+\r
+       return xSocket;\r
+}\r
+\r
+\r
diff --git a/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/WIN32.vcxproj b/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/WIN32.vcxproj
new file mode 100644 (file)
index 0000000..294c69b
--- /dev/null
@@ -0,0 +1,183 @@
+<?xml version="1.0" encoding="utf-8"?>\r
+<Project DefaultTargets="Build" ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">\r
+  <ItemGroup Label="ProjectConfigurations">\r
+    <ProjectConfiguration Include="Debug|Win32">\r
+      <Configuration>Debug</Configuration>\r
+      <Platform>Win32</Platform>\r
+    </ProjectConfiguration>\r
+    <ProjectConfiguration Include="Release|Win32">\r
+      <Configuration>Release</Configuration>\r
+      <Platform>Win32</Platform>\r
+    </ProjectConfiguration>\r
+  </ItemGroup>\r
+  <PropertyGroup Label="Globals">\r
+    <ProjectGuid>{C686325E-3261-42F7-AEB1-DDE5280E1CEB}</ProjectGuid>\r
+    <ProjectName>RTOSDemo</ProjectName>\r
+  </PropertyGroup>\r
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.Default.props" />\r
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="Configuration">\r
+    <ConfigurationType>Application</ConfigurationType>\r
+    <UseOfMfc>false</UseOfMfc>\r
+    <CharacterSet>MultiByte</CharacterSet>\r
+  </PropertyGroup>\r
+  <PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="Configuration">\r
+    <ConfigurationType>Application</ConfigurationType>\r
+    <UseOfMfc>false</UseOfMfc>\r
+    <CharacterSet>MultiByte</CharacterSet>\r
+  </PropertyGroup>\r
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.props" />\r
+  <ImportGroup Label="ExtensionSettings">\r
+  </ImportGroup>\r
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'" Label="PropertySheets">\r
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />\r
+    <Import Project="$(VCTargetsPath)Microsoft.CPP.UpgradeFromVC60.props" />\r
+  </ImportGroup>\r
+  <ImportGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'" Label="PropertySheets">\r
+    <Import Project="$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props" Condition="exists('$(UserRootDir)\Microsoft.Cpp.$(Platform).user.props')" Label="LocalAppDataPlatform" />\r
+    <Import Project="$(VCTargetsPath)Microsoft.CPP.UpgradeFromVC60.props" />\r
+  </ImportGroup>\r
+  <PropertyGroup Label="UserMacros" />\r
+  <PropertyGroup>\r
+    <_ProjectFileVersion>10.0.30319.1</_ProjectFileVersion>\r
+    <OutDir Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">.\Debug\</OutDir>\r
+    <IntDir Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">.\Debug\</IntDir>\r
+    <LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">true</LinkIncremental>\r
+    <OutDir Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">.\Release\</OutDir>\r
+    <IntDir Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">.\Release\</IntDir>\r
+    <LinkIncremental Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">false</LinkIncremental>\r
+  </PropertyGroup>\r
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">\r
+    <Midl>\r
+      <TypeLibraryName>.\Debug/WIN32.tlb</TypeLibraryName>\r
+      <HeaderFileName>\r
+      </HeaderFileName>\r
+    </Midl>\r
+    <ClCompile>\r
+      <Optimization>Disabled</Optimization>\r
+      <AdditionalIncludeDirectories>..\..\..\FreeRTOS\Source\include;..\..\..\FreeRTOS\Source\portable\MSVC-MingW;..\..\Source\FreeRTOS-Plus-CLI;.;.\..\..\Source\FreeRTOS-Plus-FAT-SL\api;.\..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\test;.\ConfigurationFiles;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>\r
+      <PreprocessorDefinitions>WIN32;_DEBUG;_CONSOLE;_WIN32_WINNT=0x0500;WINVER=0x400;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
+      <MinimalRebuild>true</MinimalRebuild>\r
+      <BasicRuntimeChecks>EnableFastChecks</BasicRuntimeChecks>\r
+      <RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>\r
+      <PrecompiledHeaderOutputFile>.\Debug/WIN32.pch</PrecompiledHeaderOutputFile>\r
+      <AssemblerListingLocation>.\Debug/</AssemblerListingLocation>\r
+      <ObjectFileName>.\Debug/</ObjectFileName>\r
+      <ProgramDataBaseFileName>.\Debug/</ProgramDataBaseFileName>\r
+      <WarningLevel>Level4</WarningLevel>\r
+      <SuppressStartupBanner>true</SuppressStartupBanner>\r
+      <DisableLanguageExtensions>false</DisableLanguageExtensions>\r
+      <DebugInformationFormat>EditAndContinue</DebugInformationFormat>\r
+    </ClCompile>\r
+    <ResourceCompile>\r
+      <PreprocessorDefinitions>_DEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
+      <Culture>0x0c09</Culture>\r
+    </ResourceCompile>\r
+    <Link>\r
+      <OutputFile>.\Debug/RTOSDemo.exe</OutputFile>\r
+      <SuppressStartupBanner>true</SuppressStartupBanner>\r
+      <GenerateDebugInformation>true</GenerateDebugInformation>\r
+      <ProgramDatabaseFile>.\Debug/WIN32.pdb</ProgramDatabaseFile>\r
+      <SubSystem>Console</SubSystem>\r
+      <TargetMachine>MachineX86</TargetMachine>\r
+      <AdditionalDependencies>%(AdditionalDependencies)</AdditionalDependencies>\r
+      <AdditionalLibraryDirectories>.\WinPCap</AdditionalLibraryDirectories>\r
+    </Link>\r
+    <Bscmake>\r
+      <SuppressStartupBanner>true</SuppressStartupBanner>\r
+      <OutputFile>.\Debug/WIN32.bsc</OutputFile>\r
+    </Bscmake>\r
+  </ItemDefinitionGroup>\r
+  <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">\r
+    <Midl>\r
+      <TypeLibraryName>.\Release/WIN32.tlb</TypeLibraryName>\r
+      <HeaderFileName>\r
+      </HeaderFileName>\r
+    </Midl>\r
+    <ClCompile>\r
+      <Optimization>MaxSpeed</Optimization>\r
+      <InlineFunctionExpansion>OnlyExplicitInline</InlineFunctionExpansion>\r
+      <PreprocessorDefinitions>_WINSOCKAPI_;WIN32;NDEBUG;_CONSOLE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
+      <StringPooling>true</StringPooling>\r
+      <RuntimeLibrary>MultiThreaded</RuntimeLibrary>\r
+      <FunctionLevelLinking>true</FunctionLevelLinking>\r
+      <PrecompiledHeaderOutputFile>.\Release/WIN32.pch</PrecompiledHeaderOutputFile>\r
+      <AssemblerListingLocation>.\Release/</AssemblerListingLocation>\r
+      <ObjectFileName>.\Release/</ObjectFileName>\r
+      <ProgramDataBaseFileName>.\Release/</ProgramDataBaseFileName>\r
+      <WarningLevel>Level3</WarningLevel>\r
+      <SuppressStartupBanner>true</SuppressStartupBanner>\r
+      <AdditionalIncludeDirectories>..\Common\Utils;..\Common\ethernet\lwip-1.4.0\ports\win32\WinPCap;..\Common\ethernet\lwip-1.4.0\src\include\ipv4;..\Common\ethernet\lwip-1.4.0\src\include;..\..\Source\include;..\..\Source\portable\MSVC-MingW;..\Common\ethernet\lwip-1.4.0\ports\win32\include;..\Common\Include;.\lwIP_Apps;.;%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>\r
+    </ClCompile>\r
+    <ResourceCompile>\r
+      <PreprocessorDefinitions>NDEBUG;%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
+      <Culture>0x0c09</Culture>\r
+    </ResourceCompile>\r
+    <Link>\r
+      <OutputFile>.\Release/RTOSDemo.exe</OutputFile>\r
+      <SuppressStartupBanner>true</SuppressStartupBanner>\r
+      <ProgramDatabaseFile>.\Release/WIN32.pdb</ProgramDatabaseFile>\r
+      <SubSystem>Console</SubSystem>\r
+      <TargetMachine>MachineX86</TargetMachine>\r
+      <AdditionalLibraryDirectories>..\Common\ethernet\lwip-1.4.0\ports\win32\WinPCap</AdditionalLibraryDirectories>\r
+      <AdditionalDependencies>wpcap.lib;%(AdditionalDependencies)</AdditionalDependencies>\r
+    </Link>\r
+    <Bscmake>\r
+      <SuppressStartupBanner>true</SuppressStartupBanner>\r
+      <OutputFile>.\Release/WIN32.bsc</OutputFile>\r
+    </Bscmake>\r
+  </ItemDefinitionGroup>\r
+  <ItemGroup>\r
+    <ClCompile Include="..\..\..\FreeRTOS\Source\portable\MemMang\heap_4.c" />\r
+    <ClCompile Include="..\..\..\FreeRTOS\Source\list.c" />\r
+    <ClCompile Include="..\..\..\FreeRTOS\Source\portable\MSVC-MingW\port.c" />\r
+    <ClCompile Include="..\..\..\FreeRTOS\Source\queue.c" />\r
+    <ClCompile Include="..\..\..\FreeRTOS\Source\tasks.c" />\r
+    <ClCompile Include="..\..\..\FreeRTOS\Source\timers.c" />\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-CLI\FreeRTOS_CLI.c" />\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\f_lock.c" />\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\test\test.c" />\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\psp\target\fat_sl\psp_test.c" />\r
+    <ClCompile Include="File-Releated-CLI-commands.c" />\r
+    <ClCompile Include="File-system-demo.c" />\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\dir.c" />\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\drv.c" />\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\fat.c" />\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\file.c" />\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\util.c" />\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\util_sfn.c" />\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\volume.c" />\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\media-drv\ram\ramdrv_f.c" />\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\psp\target\rtc\psp_rtc.c" />\r
+    <ClCompile Include="main.c">\r
+      <AdditionalIncludeDirectories Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>\r
+      <PreprocessorDefinitions Condition="'$(Configuration)|$(Platform)'=='Debug|Win32'">%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
+      <PreprocessorDefinitions Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">%(PreprocessorDefinitions)</PreprocessorDefinitions>\r
+    </ClCompile>\r
+    <ClCompile Include="Run-time-stats-utils.c" />\r
+    <ClCompile Include="Sample-CLI-commands.c" />\r
+    <ClCompile Include="UDPCommandServer.c" />\r
+  </ItemGroup>\r
+  <ItemGroup>\r
+    <ClInclude Include="..\..\..\FreeRTOS\Source\include\FreeRTOS.h" />\r
+    <ClInclude Include="..\..\..\FreeRTOS\Source\include\projdefs.h" />\r
+    <ClInclude Include="..\..\..\FreeRTOS\Source\include\queue.h" />\r
+    <ClInclude Include="..\..\..\FreeRTOS\Source\include\semphr.h" />\r
+    <ClInclude Include="..\..\..\FreeRTOS\Source\include\task.h" />\r
+    <ClInclude Include="..\..\..\FreeRTOS\Source\include\timers.h" />\r
+    <ClInclude Include="..\..\Source\FreeRTOS-Plus-CLI\FreeRTOS_CLI.h" />\r
+    <ClInclude Include="..\..\Source\FreeRTOS-Plus-FAT-SL\api\fat_sl.h" />\r
+    <ClInclude Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\f_lock.h" />\r
+    <ClInclude Include="ConfigurationFiles\config_fat_sl.h" />\r
+    <ClInclude Include="FreeRTOSConfig.h" />\r
+    <ClInclude Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\dir.h" />\r
+    <ClInclude Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\drv.h" />\r
+    <ClInclude Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\fat.h" />\r
+    <ClInclude Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\file.h" />\r
+    <ClInclude Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\util.h" />\r
+    <ClInclude Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\util_sfn.h" />\r
+    <ClInclude Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\volume.h" />\r
+  </ItemGroup>\r
+  <Import Project="$(VCTargetsPath)\Microsoft.Cpp.targets" />\r
+  <ImportGroup Label="ExtensionTargets">\r
+  </ImportGroup>\r
+</Project>
\ No newline at end of file
diff --git a/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/WIN32.vcxproj.filters b/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/WIN32.vcxproj.filters
new file mode 100644 (file)
index 0000000..e230fae
--- /dev/null
@@ -0,0 +1,177 @@
+<?xml version="1.0" encoding="utf-8"?>\r
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">\r
+  <ItemGroup>\r
+    <Filter Include="Resource Files">\r
+      <UniqueIdentifier>{38712199-cebf-4124-bf15-398f7c3419ea}</UniqueIdentifier>\r
+      <Extensions>ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe</Extensions>\r
+    </Filter>\r
+    <Filter Include="FreeRTOS">\r
+      <UniqueIdentifier>{af3445a1-4908-4170-89ed-39345d90d30c}</UniqueIdentifier>\r
+    </Filter>\r
+    <Filter Include="FreeRTOS\Source">\r
+      <UniqueIdentifier>{f32be356-4763-4cae-9020-974a2638cb08}</UniqueIdentifier>\r
+      <Extensions>*.c</Extensions>\r
+    </Filter>\r
+    <Filter Include="FreeRTOS\Source\Portable">\r
+      <UniqueIdentifier>{88f409e6-d396-4ac5-94bd-7a99c914be46}</UniqueIdentifier>\r
+    </Filter>\r
+    <Filter Include="FreeRTOS+">\r
+      <UniqueIdentifier>{e5ad4ec7-23dc-4295-8add-2acaee488f5a}</UniqueIdentifier>\r
+    </Filter>\r
+    <Filter Include="FreeRTOS+\FreeRTOS+CLI">\r
+      <UniqueIdentifier>{fd43c0ed-fdbc-437f-a5a3-c50399690bd7}</UniqueIdentifier>\r
+    </Filter>\r
+    <Filter Include="FreeRTOS+\FreeRTOS+CLI\include">\r
+      <UniqueIdentifier>{c5889fe2-af0f-4cea-927f-6a6935ec5e14}</UniqueIdentifier>\r
+    </Filter>\r
+    <Filter Include="FreeRTOS+\FreeRTOS+FAT SL">\r
+      <UniqueIdentifier>{d261611a-5416-4455-bb33-3bd84381ea40}</UniqueIdentifier>\r
+    </Filter>\r
+    <Filter Include="FreeRTOS+\FreeRTOS+FAT SL\Media_Driver">\r
+      <UniqueIdentifier>{17c1a794-a4a6-4358-850f-2a88bfe3bd33}</UniqueIdentifier>\r
+    </Filter>\r
+    <Filter Include="FreeRTOS+\FreeRTOS+FAT SL\psp">\r
+      <UniqueIdentifier>{fb7ccc1d-c4ad-475a-98d9-2e8ae2301c99}</UniqueIdentifier>\r
+    </Filter>\r
+    <Filter Include="FreeRTOS+\FreeRTOS+FAT SL\psp\target">\r
+      <UniqueIdentifier>{34bb4a98-fb88-41fc-81f2-4e3f1c50c528}</UniqueIdentifier>\r
+    </Filter>\r
+    <Filter Include="FreeRTOS+\FreeRTOS+FAT SL\psp\target\rtc">\r
+      <UniqueIdentifier>{286bf65c-93cd-4480-8363-0fb2c2bc7ce1}</UniqueIdentifier>\r
+    </Filter>\r
+    <Filter Include="Configuration Files">\r
+      <UniqueIdentifier>{19ff1a34-36de-4c48-9d10-3fb1fa0d1fa4}</UniqueIdentifier>\r
+      <Extensions>h;hpp;hxx;hm;inl</Extensions>\r
+    </Filter>\r
+    <Filter Include="FreeRTOS+\FreeRTOS+FAT SL\tests">\r
+      <UniqueIdentifier>{e4105d81-802a-4210-b40b-d5dd3cf6e643}</UniqueIdentifier>\r
+    </Filter>\r
+    <Filter Include="FreeRTOS\Source\include">\r
+      <UniqueIdentifier>{ab23827c-126c-4e5a-bc99-8efa44d8a8bd}</UniqueIdentifier>\r
+    </Filter>\r
+    <Filter Include="FreeRTOS+\FreeRTOS+FAT SL\api">\r
+      <UniqueIdentifier>{9e1c9cf5-c2c7-4f8d-b09d-0b7f329eac57}</UniqueIdentifier>\r
+    </Filter>\r
+  </ItemGroup>\r
+  <ItemGroup>\r
+    <ClCompile Include="..\..\..\FreeRTOS\Source\portable\MSVC-MingW\port.c">\r
+      <Filter>FreeRTOS\Source\Portable</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="..\..\..\FreeRTOS\Source\timers.c">\r
+      <Filter>FreeRTOS\Source</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="..\..\..\FreeRTOS\Source\list.c">\r
+      <Filter>FreeRTOS\Source</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="..\..\..\FreeRTOS\Source\queue.c">\r
+      <Filter>FreeRTOS\Source</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="..\..\..\FreeRTOS\Source\tasks.c">\r
+      <Filter>FreeRTOS\Source</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="..\..\..\FreeRTOS\Source\portable\MemMang\heap_4.c">\r
+      <Filter>FreeRTOS\Source\Portable</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-CLI\FreeRTOS_CLI.c">\r
+      <Filter>FreeRTOS+\FreeRTOS+CLI</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\media-drv\ram\ramdrv_f.c">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL\Media_Driver</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\psp\target\rtc\psp_rtc.c">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL\psp\target\rtc</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\dir.c">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\drv.c">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\fat.c">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\file.c">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\util.c">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\util_sfn.c">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\volume.c">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="UDPCommandServer.c" />\r
+    <ClCompile Include="File-Releated-CLI-commands.c" />\r
+    <ClCompile Include="File-system-demo.c" />\r
+    <ClCompile Include="main.c" />\r
+    <ClCompile Include="Run-time-stats-utils.c" />\r
+    <ClCompile Include="Sample-CLI-commands.c" />\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\psp\target\fat_sl\psp_test.c">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\test\test.c">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL\tests</Filter>\r
+    </ClCompile>\r
+    <ClCompile Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\f_lock.c">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL</Filter>\r
+    </ClCompile>\r
+  </ItemGroup>\r
+  <ItemGroup>\r
+    <ClInclude Include="FreeRTOSConfig.h">\r
+      <Filter>Configuration Files</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="..\..\Source\FreeRTOS-Plus-CLI\FreeRTOS_CLI.h">\r
+      <Filter>FreeRTOS+\FreeRTOS+CLI\include</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\volume.h">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\dir.h">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\drv.h">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\fat.h">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\file.h">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\util.h">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\util_sfn.h">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="ConfigurationFiles\config_fat_sl.h">\r
+      <Filter>Configuration Files</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="..\..\..\FreeRTOS\Source\include\timers.h">\r
+      <Filter>FreeRTOS\Source\include</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="..\..\..\FreeRTOS\Source\include\FreeRTOS.h">\r
+      <Filter>FreeRTOS\Source\include</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="..\..\..\FreeRTOS\Source\include\projdefs.h">\r
+      <Filter>FreeRTOS\Source\include</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="..\..\..\FreeRTOS\Source\include\queue.h">\r
+      <Filter>FreeRTOS\Source\include</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="..\..\..\FreeRTOS\Source\include\semphr.h">\r
+      <Filter>FreeRTOS\Source\include</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="..\..\..\FreeRTOS\Source\include\task.h">\r
+      <Filter>FreeRTOS\Source\include</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="..\..\Source\FreeRTOS-Plus-FAT-SL\api\fat_sl.h">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL\api</Filter>\r
+    </ClInclude>\r
+    <ClInclude Include="..\..\Source\FreeRTOS-Plus-FAT-SL\fat_sl\common\f_lock.h">\r
+      <Filter>FreeRTOS+\FreeRTOS+FAT SL</Filter>\r
+    </ClInclude>\r
+  </ItemGroup>\r
+</Project>
\ No newline at end of file
diff --git a/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/WIN32.vcxproj.user b/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/WIN32.vcxproj.user
new file mode 100644 (file)
index 0000000..695b5c7
--- /dev/null
@@ -0,0 +1,3 @@
+<?xml version="1.0" encoding="utf-8"?>\r
+<Project ToolsVersion="4.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">\r
+</Project>
\ No newline at end of file
diff --git a/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/main.c b/FreeRTOS-Plus/Demo/FreeRTOS_Plus_FAT_SL_and_CLI_Windows_Simulator/main.c
new file mode 100644 (file)
index 0000000..3925072
--- /dev/null
@@ -0,0 +1,237 @@
+/*\r
+    FreeRTOS V7.4.0 - Copyright (C) 2013 Real Time Engineers Ltd.\r
+\r
+    FEATURES AND PORTS ARE ADDED TO FREERTOS ALL THE TIME.  PLEASE VISIT\r
+    http://www.FreeRTOS.org TO ENSURE YOU ARE USING THE LATEST VERSION.\r
+\r
+    ***************************************************************************\r
+     *                                                                       *\r
+     *    FreeRTOS tutorial books are available in pdf and paperback.        *\r
+     *    Complete, revised, and edited pdf reference manuals are also       *\r
+     *    available.                                                         *\r
+     *                                                                       *\r
+     *    Purchasing FreeRTOS documentation will not only help you, by       *\r
+     *    ensuring you get running as quickly as possible and with an        *\r
+     *    in-depth knowledge of how to use FreeRTOS, it will also help       *\r
+     *    the FreeRTOS project to continue with its mission of providing     *\r
+     *    professional grade, cross platform, de facto standard solutions    *\r
+     *    for microcontrollers - completely free of charge!                  *\r
+     *                                                                       *\r
+     *    >>> See http://www.FreeRTOS.org/Documentation for details. <<<     *\r
+     *                                                                       *\r
+     *    Thank you for using FreeRTOS, and thank you for your support!      *\r
+     *                                                                       *\r
+    ***************************************************************************\r
+\r
+\r
+    This file is part of the FreeRTOS distribution.\r
+\r
+    FreeRTOS is free software; you can redistribute it and/or modify it under\r
+    the terms of the GNU General Public License (version 2) as published by the\r
+    Free Software Foundation AND MODIFIED BY the FreeRTOS exception.\r
+\r
+    >>>>>>NOTE<<<<<< The modification to the GPL is included to allow you to\r
+    distribute a combined work that includes FreeRTOS without being obliged to\r
+    provide the source code for proprietary components outside of the FreeRTOS\r
+    kernel.\r
+\r
+    FreeRTOS is distributed in the hope that it will be useful, but WITHOUT ANY\r
+    WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS\r
+    FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more\r
+    details. You should have received a copy of the GNU General Public License\r
+    and the FreeRTOS license exception along with FreeRTOS; if not itcan be\r
+    viewed here: http://www.freertos.org/a00114.html and also obtained by\r
+    writing to Real Time Engineers Ltd., contact details for whom are available\r
+    on the FreeRTOS WEB site.\r
+\r
+    1 tab == 4 spaces!\r
+\r
+    ***************************************************************************\r
+     *                                                                       *\r
+     *    Having a problem?  Start by reading the FAQ "My application does   *\r
+     *    not run, what could be wrong?"                                     *\r
+     *                                                                       *\r
+     *    http://www.FreeRTOS.org/FAQHelp.html                               *\r
+     *                                                                       *\r
+    ***************************************************************************\r
+\r
+\r
+    http://www.FreeRTOS.org - Documentation, books, training, latest versions,\r
+    license and Real Time Engineers Ltd. contact details.\r
+\r
+    http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products,\r
+    including FreeRTOS+Trace - an indispensable productivity tool, and our new\r
+    fully thread aware and reentrant UDP/IP stack.\r
+\r
+    http://www.OpenRTOS.com - Real Time Engineers ltd license FreeRTOS to High\r
+    Integrity Systems, who sell the code with commercial support,\r
+    indemnification and middleware, under the OpenRTOS brand.\r
+\r
+    http://www.SafeRTOS.com - High Integrity Systems also provide a safety\r
+    engineered and independently SIL3 certified version for use in safety and\r
+    mission critical applications that require provable dependability.\r
+*/\r
+\r
+/******************************************************************************\r
+ *\r
+ * This demo is described on the following web page:\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus/FreeRTOS_Plus_FAT_SL/Demos/File_System_Win32_Simulator_demo.shtml\r
+ *\r
+ ******************************************************************************/\r
+\r
+/* Standard includes. */\r
+#include <stdio.h>\r
+#include <stdint.h>\r
+\r
+/* FreeRTOS includes. */\r
+#include <FreeRTOS.h>\r
+#include "task.h"\r
+#include "queue.h"\r
+#include "semphr.h"\r
+\r
+/* File system includes. */\r
+#include "config_fat_sl.h"\r
+\r
+/* Priorities at which the tasks are created. */\r
+#define mainUDP_CLI_TASK_PRIORITY                      ( tskIDLE_PRIORITY )\r
+\r
+/*-----------------------------------------------------------*/\r
+\r
+/*\r
+ * Register the generic commands that can be used with FreeRTOS+CLI.\r
+ */\r
+extern void vRegisterSampleCLICommands( void );\r
+\r
+/*\r
+ * Register the file system commands that can be used with FreeRTOS+CLI.\r
+ */\r
+extern void vRegisterFileSystemCLICommands( void );\r
+\r
+/*\r
+ * The task that implements the UDP command interpreter using FreeRTOS+CLI.\r
+ */\r
+extern void vUDPCommandInterpreterTask( void *pvParameters );\r
+\r
+/*\r
+ * Creates and verifies different files on the volume, demonstrating the use of\r
+ * various different API functions.\r
+ */\r
+extern void vCreateAndVerifySampleFiles( void );\r
+\r
+/*-----------------------------------------------------------*/\r
+\r
+/******************************************************************************\r
+ *\r
+ * This demo is described on the following web page:\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus/FreeRTOS_Plus_FAT_SL/Demos/File_System_Win32_Simulator_demo.shtml\r
+ *\r
+ ******************************************************************************/\r
+\r
+int main( void )\r
+{\r
+const uint32_t ulLongTime_ms = 250UL;\r
+\r
+       /* If the file system is only going to be accessed from one task then\r
+       F_FS_THREAD_AWARE can be set to 0 and the set of example files are created\r
+       before the RTOS scheduler is started.  If the file system is going to be\r
+       access from more than one task then F_FS_THREAD_AWARE must be set to 1 and\r
+       the     set of sample files are created from the idle task hook function\r
+       vApplicationIdleHook() - which is defined in this file. */\r
+       #if F_FS_THREAD_AWARE == 0\r
+       {\r
+               /* Initialise the drive and file system, then create a few example\r
+               files.  The output from this function just goes to the stdout window,\r
+               allowing the output to be viewed when the UDP command console is not\r
+               connected. */\r
+               vCreateAndVerifySampleFiles();\r
+       }\r
+       #endif\r
+\r
+       /* Register generic commands with the FreeRTOS+CLI command interpreter. */\r
+       vRegisterSampleCLICommands();\r
+\r
+       /* Register file system related commands with the FreeRTOS+CLI command\r
+       interpreter. */\r
+       vRegisterFileSystemCLICommands();\r
+\r
+       /* Create the task that handles the CLI on a UDP port.  The port number\r
+       is set using the configUDP_CLI_PORT_NUMBER setting in FreeRTOSConfig.h. */\r
+       xTaskCreate( vUDPCommandInterpreterTask,        /* The function that implements the command interpreter IO handling. */\r
+                               ( signed char * ) "CLI",                /* The name of the task - just to assist debugging. */\r
+                               configMINIMAL_STACK_SIZE, NULL, /* The size of the stack allocated to the task. */\r
+                               mainUDP_CLI_TASK_PRIORITY,              /* The priority at which the task will run. */\r
+                               NULL );                                                 /* A handle to the task is not required, so NULL is passed. */\r
+\r
+       /* Start the RTOS scheduler. */\r
+       vTaskStartScheduler();\r
+\r
+       /* If all is well, the scheduler will now be running, and the following\r
+       line will never be reached.  If the following line does execute, then\r
+       there was insufficient FreeRTOS heap memory available for the idle and/or\r
+       timer tasks     to be created.  See the memory management section on the\r
+       FreeRTOS web site for more details (this is standard text that is not not\r
+       really applicable to the Win32 simulator port). */\r
+       for( ;; )\r
+       {\r
+               Sleep( ulLongTime_ms );\r
+       }\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+void vApplicationIdleHook( void )\r
+{\r
+const unsigned long ulMSToSleep = 5;\r
+\r
+       /* If the file system is only going to be accessed from one task then\r
+       F_FS_THREAD_AWARE can be set to 0 and the set of example files is created\r
+       before the RTOS scheduler is started.  If the file system is going to be\r
+       access from more than one task then F_FS_THREAD_AWARE must be set to 1 and\r
+       the     set of sample files are created from the idle task hook function. */\r
+       #if F_FS_THREAD_AWARE == 1\r
+       {\r
+               static portBASE_TYPE xCreatedSampleFiles = pdFALSE;\r
+\r
+               /* Initialise the drive and file system, then create a few example\r
+               files.  The output from this function just goes to the stdout window,\r
+               allowing the output to be viewed when the UDP command console is not\r
+               connected. */\r
+               if( xCreatedSampleFiles == pdFALSE )\r
+               {\r
+                       vCreateAndVerifySampleFiles();\r
+                       xCreatedSampleFiles = pdTRUE;\r
+               }\r
+       }\r
+       #endif\r
+\r
+       /* This function is called on each cycle of the idle task if\r
+       configUSE_IDLE_HOOK is set to 1 in FreeRTOSConfig.h.  Sleep to reduce CPU\r
+       load. */\r
+       Sleep( ulMSToSleep );\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+void vAssertCalled( const char *pcFile, unsigned long ulLine )\r
+{\r
+       printf( "ASSERT FAILED: File %s, line %u\r\n", pcFile, ulLine );\r
+}\r
+/*-----------------------------------------------------------*/\r
+\r
+void vApplicationMallocFailedHook( void )\r
+{\r
+       /* vApplicationMallocFailedHook() will only be called if\r
+       configUSE_MALLOC_FAILED_HOOK is set to 1 in FreeRTOSConfig.h.  It is a hook\r
+       function that will get called if a call to pvPortMalloc() fails.\r
+       pvPortMalloc() is called internally by the kernel whenever a task, queue,\r
+       timer or semaphore is created.  It is also called by various parts of the\r
+       demo application.  If heap_1.c, heap_2.c or heap_4.c are used, then the\r
+       size of the heap available to pvPortMalloc() is defined by\r
+       configTOTAL_HEAP_SIZE in FreeRTOSConfig.h, and the xPortGetFreeHeapSize()\r
+       API function can be used to query the size of free heap space that remains\r
+       (although it does not provide information on how the remaining heap might\r
+       be fragmented). */\r
+       taskDISABLE_INTERRUPTS();\r
+       for( ;; );\r
+}\r
+\r
+\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/ReadMe.url b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/ReadMe.url
new file mode 100644 (file)
index 0000000..c0924c3
--- /dev/null
@@ -0,0 +1,5 @@
+[InternetShortcut]\r
+URL=http://www.freertos.org/fat\r
+IDList=\r
+[{000214A0-0000-0000-C000-000000000046}]\r
+Prop3=19,2\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/api/api_mdriver.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/api/api_mdriver.h
new file mode 100644 (file)
index 0000000..c10ffec
--- /dev/null
@@ -0,0 +1,102 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef _API_MDRIVER_H_\r
+#define _API_MDRIVER_H_\r
+\r
+#include "../version/ver_mdriver.h"\r
+#if VER_MDRIVER_MAJOR != 1 || VER_MDRIVER_MINOR != 0\r
+ #error Incompatible MDRIVER version number!\r
+#endif\r
+\r
+#ifdef __cplusplus\r
+extern "C" {\r
+#endif\r
+\r
+\r
+typedef struct\r
+{\r
+  unsigned short  number_of_cylinders;\r
+  unsigned short  sector_per_track;\r
+  unsigned short  number_of_heads;\r
+  unsigned long   number_of_sectors;\r
+  unsigned char   media_descriptor;\r
+\r
+  unsigned short  bytes_per_sector;\r
+} F_PHY;\r
+\r
+/* media descriptor to be set in getphy function */\r
+#define F_MEDIADESC_REMOVABLE 0xf0\r
+#define F_MEDIADESC_FIX       0xf8\r
+\r
+/* return bitpattern for driver getphy function */\r
+#define F_ST_MISSING          0x00000001\r
+#define F_ST_CHANGED          0x00000002\r
+#define F_ST_WRPROTECT        0x00000004\r
+\r
+/* Driver definitions */\r
+typedef struct F_DRIVER  F_DRIVER;\r
+\r
+typedef int           ( *F_WRITESECTOR )( F_DRIVER * driver, void * data, unsigned long sector );\r
+typedef int           ( *F_READSECTOR )( F_DRIVER * driver, void * data, unsigned long sector );\r
+typedef int           ( *F_GETPHY )( F_DRIVER * driver, F_PHY * phy );\r
+typedef long          ( *F_GETSTATUS )( F_DRIVER * driver );\r
+typedef void          ( *F_RELEASE )( F_DRIVER * driver );\r
+\r
+typedef struct F_DRIVER\r
+{\r
+  unsigned long  user_data;     /* user defined data */\r
+  void         * user_ptr;      /* user define pointer */\r
+\r
+  /* driver functions */\r
+  F_WRITESECTOR          writesector;\r
+  F_READSECTOR           readsector;\r
+  F_GETPHY               getphy;\r
+  F_GETSTATUS            getstatus;\r
+  F_RELEASE              release;\r
+} _F_DRIVER;\r
+\r
+typedef F_DRIVER *( *F_DRIVERINIT )( unsigned long driver_param );\r
+\r
+#ifdef __cplusplus\r
+}\r
+#endif\r
+\r
+#endif /* _API_MDRIVER_H_ */\r
+\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/api/api_mdriver_ram.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/api/api_mdriver_ram.h
new file mode 100644 (file)
index 0000000..46dd1c6
--- /dev/null
@@ -0,0 +1,70 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef _API_MDRIVER_RAM_H_\r
+#define _API_MDRIVER_RAM_H_\r
+\r
+#include "api_mdriver.h"\r
+\r
+#include "../version/ver_mdriver_ram.h"\r
+#if VER_MDRIVER_RAM_MAJOR != 1 || VER_MDRIVER_RAM_MINOR != 2\r
+ #error Incompatible MDRIVER_RAM version number!\r
+#endif\r
+\r
+#ifdef __cplusplus\r
+extern "C" {\r
+#endif\r
+\r
+#define F_RAM_DRIVE0 0\r
+\r
+enum\r
+{\r
+  MDRIVER_RAM_NO_ERROR\r
+  , MDRIVER_RAM_ERR_SECTOR = 101\r
+  , MDRIVER_RAM_ERR_NOTAVAILABLE\r
+};\r
+\r
+F_DRIVER * ram_initfunc ( unsigned long driver_param );\r
+\r
+#ifdef __cplusplus\r
+}\r
+#endif\r
+\r
+\r
+#endif /* _API_MDRIVER_RAM_H_ */\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/api/fat_sl.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/api/fat_sl.h
new file mode 100644 (file)
index 0000000..f80ef27
--- /dev/null
@@ -0,0 +1,479 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef _API_FAT_SL_H_\r
+#define _API_FAT_SL_H_\r
+\r
+#include "config_fat_sl.h"\r
+\r
+#include "../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+#ifdef __cplusplus\r
+extern "C" {\r
+#endif\r
+\r
+#define F_MAXNAME 8                  /* 8 byte name */\r
+#define F_MAXEXT  3                  /* 3 byte extension */\r
+\r
+typedef struct\r
+{\r
+  char  path[F_MAXPATH];        /*  /directory1/dir2/  */\r
+  char  filename[F_MAXNAME];    /* filename */\r
+  char  fileext[F_MAXEXT];      /* extension */\r
+} F_NAME;\r
+\r
+typedef struct\r
+{\r
+  unsigned long  cluster;\r
+  unsigned long  sector;\r
+  unsigned long  sectorend;\r
+  unsigned long  pos;\r
+} F_POS;\r
+\r
+typedef struct\r
+{\r
+  char            filename[F_MAXPATH]; /*file name+ext*/\r
+  char            name[F_MAXNAME];     /*file name*/\r
+  char            ext[F_MAXEXT];       /*file extension*/\r
+  unsigned char   attr;                /*attribute of the file*/\r
+\r
+  unsigned short  ctime;        /*creation time*/\r
+  unsigned short  cdate;        /*creation date*/\r
+  unsigned long   cluster;\r
+\r
+  long            filesize;         /*length of file*/\r
+\r
+  F_NAME          findfsname;   /*find properties*/\r
+  F_POS           pos;\r
+} F_FIND;\r
+\r
+/* definitions for ctime */\r
+#define F_CTIME_SEC_SHIFT   0\r
+#define F_CTIME_SEC_MASK    0x001f  /*0-30 in 2seconds*/\r
+#define F_CTIME_MIN_SHIFT   5\r
+#define F_CTIME_MIN_MASK    0x07e0  /*0-59 */\r
+#define F_CTIME_HOUR_SHIFT  11\r
+#define F_CTIME_HOUR_MASK   0xf800  /*0-23*/\r
+\r
+\r
+/* definitions for cdate */\r
+#define F_CDATE_DAY_SHIFT   0\r
+#define F_CDATE_DAY_MASK    0x001f  /*0-31*/\r
+#define F_CDATE_MONTH_SHIFT 5\r
+#define F_CDATE_MONTH_MASK  0x01e0  /*1-12*/\r
+#define F_CDATE_YEAR_SHIFT  9\r
+#define F_CDATE_YEAR_MASK   0xfe00  /*0-119 (1980+value)*/\r
+\r
+#define F_ATTR_ARC         0x20\r
+#define F_ATTR_DIR         0x10\r
+#define F_ATTR_VOLUME      0x08\r
+#define F_ATTR_SYSTEM      0x04\r
+#define F_ATTR_HIDDEN      0x02\r
+#define F_ATTR_READONLY    0x01\r
+\r
+#define F_CLUSTER_FREE     ( (unsigned long)0x00000000 )\r
+#define F_CLUSTER_RESERVED ( (unsigned long)0x0ffffff0 )\r
+#define F_CLUSTER_BAD      ( (unsigned long)0x0ffffff7 )\r
+#define F_CLUSTER_LAST     ( (unsigned long)0x0ffffff8 )\r
+#define F_CLUSTER_LASTF32R ( (unsigned long)0x0fffffff )\r
+\r
+#define F_ST_MISSING       0x00000001\r
+#define F_ST_CHANGED       0x00000002\r
+#define F_ST_WRPROTECT     0x00000004\r
+\r
+typedef struct\r
+{\r
+  unsigned long  abspos;\r
+  unsigned long  filesize;\r
+  unsigned long  startcluster;\r
+  unsigned long  prevcluster;\r
+  unsigned long  relpos;\r
+  unsigned char  modified;\r
+  unsigned char  mode;\r
+  unsigned char  _tdata[F_SECTOR_SIZE];\r
+  F_POS          pos;\r
+  F_POS          dirpos;\r
+#if F_FILE_CHANGED_EVENT\r
+  char           filename[F_MAXPATH];   /* filename with full path */\r
+#endif\r
+} F_FILE;\r
+\r
+enum\r
+{\r
+  F_UNKNOWN_MEDIA\r
+  , F_FAT12_MEDIA\r
+  , F_FAT16_MEDIA\r
+  , F_FAT32_MEDIA\r
+};\r
+\r
+enum\r
+{\r
+/*  0 */\r
+  F_NO_ERROR,\r
+\r
+/*  1 */ F_ERR_RESERVED_1,\r
+\r
+/*  2 */ F_ERR_NOTFORMATTED,\r
+\r
+/*  3 */ F_ERR_INVALIDDIR,\r
+\r
+/*  4 */ F_ERR_INVALIDNAME,\r
+\r
+/*  5 */ F_ERR_NOTFOUND,\r
+\r
+/*  6 */ F_ERR_DUPLICATED,\r
+\r
+/*  7 */ F_ERR_NOMOREENTRY,\r
+\r
+/*  8 */ F_ERR_NOTOPEN,\r
+\r
+/*  9 */ F_ERR_EOF,\r
+\r
+/* 10 */ F_ERR_RESERVED_2,\r
+\r
+/* 11 */ F_ERR_NOTUSEABLE,\r
+\r
+/* 12 */ F_ERR_LOCKED,\r
+\r
+/* 13 */ F_ERR_ACCESSDENIED,\r
+\r
+/* 14 */ F_ERR_NOTEMPTY,\r
+\r
+/* 15 */ F_ERR_INITFUNC,\r
+\r
+/* 16 */ F_ERR_CARDREMOVED,\r
+\r
+/* 17 */ F_ERR_ONDRIVE,\r
+\r
+/* 18 */ F_ERR_INVALIDSECTOR,\r
+\r
+/* 19 */ F_ERR_READ,\r
+\r
+/* 20 */ F_ERR_WRITE,\r
+\r
+/* 21 */ F_ERR_INVALIDMEDIA,\r
+\r
+/* 22 */ F_ERR_BUSY,\r
+\r
+/* 23 */ F_ERR_WRITEPROTECT,\r
+\r
+/* 24 */ F_ERR_INVFATTYPE,\r
+\r
+/* 25 */ F_ERR_MEDIATOOSMALL,\r
+\r
+/* 26 */ F_ERR_MEDIATOOLARGE,\r
+\r
+/* 27 */ F_ERR_NOTSUPPSECTORSIZE\r
+\r
+/* 28 */, F_ERR_ALLOCATION\r
+\r
+#if F_FS_THREAD_AWARE == 1\r
+/* 29 */, F_ERR_OS = 29\r
+#endif /* F_FS_THREAD_AWARE */\r
+};\r
+\r
+typedef struct\r
+{\r
+  unsigned long  total;\r
+  unsigned long  free;\r
+  unsigned long  used;\r
+  unsigned long  bad;\r
+\r
+  unsigned long  total_high;\r
+  unsigned long  free_high;\r
+  unsigned long  used_high;\r
+  unsigned long  bad_high;\r
+} F_SPACE;\r
+\r
+enum\r
+{\r
+  F_SEEK_SET   /*Beginning of file*/\r
+  , F_SEEK_CUR /*Current position of file pointer*/\r
+  , F_SEEK_END /*End of file*/\r
+};\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * for file changed events\r
+ *\r
+ ***************************************************************************/\r
+#ifndef F_FILE_CHANGED_EVENT\r
+       #define F_FILE_CHANGED_EVENT 0\r
+#endif\r
+\r
+#if F_FILE_CHANGED_EVENT\r
+\r
+typedef struct\r
+{\r
+  unsigned char   action;\r
+  unsigned char   flags;\r
+  unsigned char   attr;\r
+  unsigned short  ctime;\r
+  unsigned short  cdate;\r
+  unsigned long   filesize;\r
+  char            filename[F_MAXPATH];\r
+} ST_FILE_CHANGED;\r
+\r
+typedef void ( *F_FILE_CHANGED_EVENTFUNC )( ST_FILE_CHANGED * fc );\r
+\r
+extern F_FILE_CHANGED_EVENTFUNC  f_filechangedevent;\r
+\r
+ #define f_setfilechangedevent( filechangeevent ) f_filechangedevent = filechangeevent\r
+\r
+/* flags */\r
+\r
+ #define FFLAGS_NONE              0x00000000\r
+\r
+ #define FFLAGS_FILE_NAME         0x00000001\r
+ #define FFLAGS_DIR_NAME          0x00000002\r
+ #define FFLAGS_NAME              0x00000003\r
+ #define FFLAGS_ATTRIBUTES        0x00000004\r
+ #define FFLAGS_SIZE              0x00000008\r
+ #define FFLAGS_LAST_WRITE        0x00000010\r
+\r
+/* actions */\r
+\r
+ #define FACTION_ADDED            0x00000001\r
+ #define FACTION_REMOVED          0x00000002\r
+ #define FACTION_MODIFIED         0x00000003\r
+\r
+#endif /* if F_FILE_CHANGED_EVENT */\r
+\r
+unsigned char fn_initvolume ( F_DRIVERINIT initfunc );\r
+unsigned char fn_delvolume ( void );\r
+\r
+unsigned char fn_getfreespace ( F_SPACE * pspace );\r
+\r
+unsigned char fn_chdir ( const char * dirname );\r
+unsigned char fn_mkdir ( const char * dirname );\r
+unsigned char fn_rmdir ( const char * dirname );\r
+\r
+unsigned char fn_findfirst ( const char * filename, F_FIND * find );\r
+unsigned char fn_findnext ( F_FIND * find );\r
+\r
+long fn_filelength ( const char * filename );\r
+\r
+unsigned char fn_close ( F_FILE * filehandle );\r
+F_FILE * fn_open ( const char * filename, const char * mode );\r
+\r
+long fn_read ( void * buf, long size, long _size_t, F_FILE * filehandle );\r
+\r
+long fn_write ( const void * buf, long size, long _size_t, F_FILE * filehandle );\r
+\r
+unsigned char fn_seek ( F_FILE * filehandle, long offset, unsigned char whence );\r
+\r
+long fn_tell ( F_FILE * filehandle );\r
+int fn_getc ( F_FILE * filehandle );\r
+int fn_putc ( int ch, F_FILE * filehandle );\r
+unsigned char fn_rewind ( F_FILE * filehandle );\r
+unsigned char fn_eof ( F_FILE * filehandle );\r
+\r
+unsigned char fn_delete ( const char * filename );\r
+\r
+unsigned char fn_seteof ( F_FILE * );\r
+\r
+F_FILE * fn_truncate ( const char *, long );\r
+\r
+unsigned char fn_getcwd ( char * buffer, unsigned char maxlen, char root );\r
+\r
+unsigned char fn_hardformat ( unsigned char fattype );\r
+unsigned char fn_format ( unsigned char fattype );\r
+\r
+unsigned char fn_getserial ( unsigned long * );\r
+\r
+\r
+#if F_FS_THREAD_AWARE == 1\r
+\r
+#include "FreeRTOS.h"\r
+#include "semphr.h"\r
+#ifndef FS_MUTEX_DEFINED\r
+       extern xSemaphoreHandle fs_lock_semaphore;\r
+#endif /* FS_MUTEX_DEFINED */\r
+\r
+unsigned char fn_init ( void );\r
+#define f_init fn_init\r
+#define f_initvolume fn_initvolume\r
+#define f_delvolume  fn_delvolume\r
+\r
+unsigned char fr_hardformat ( unsigned char fattype );\r
+#define f_hardformat( fattype ) fr_hardformat( fattype )\r
+#define f_format( fattype )    fr_hardformat( fattype )\r
+\r
+unsigned char fr_getcwd ( char * buffer, unsigned char maxlen, char root );\r
+#define f_getcwd( buffer, maxlen ) fr_getcwd( buffer, maxlen, 1 )\r
+\r
+unsigned char fr_getfreespace ( F_SPACE * pspace );\r
+#define f_getfreespace fr_getfreespace\r
+\r
+\r
+unsigned char fr_chdir ( const char * dirname );\r
+#define f_chdir( dirname ) fr_chdir( dirname )\r
+unsigned char fr_mkdir ( const char * dirname );\r
+#define f_mkdir( dirname ) fr_mkdir( dirname )\r
+unsigned char fr_rmdir ( const char * dirname );\r
+#define f_rmdir( dirname ) fr_rmdir( dirname )\r
+\r
+unsigned char fr_findfirst ( const char * filename, F_FIND * find );\r
+unsigned char fr_findnext ( F_FIND * find );\r
+#define f_findfirst( filename, find ) fr_findfirst( filename, find )\r
+#define f_findnext( find )            fr_findnext( find )\r
+\r
+long fr_filelength ( const char * filename );\r
+#define f_filelength( filename ) fr_filelength( filename )\r
+\r
+unsigned char fr_close ( F_FILE * filehandle );\r
+F_FILE * fr_open ( const char * filename, const char * mode );\r
+\r
+long fr_read ( void * buf, long size, long _size_t, F_FILE * filehandle );\r
+\r
+unsigned char fr_getserial ( unsigned long * );\r
+#define f_getserial( serial )  fr_getserial( serial )\r
+\r
+unsigned char fr_flush ( F_FILE * f );\r
+#define f_flush( filehandle ) fr_flush( filehandle )\r
+\r
+long fr_write ( const void * buf, long size, long _size_t, F_FILE * filehandle );\r
+#define f_write( buf, size, _size_t, filehandle ) fr_write( buf, size, _size_t, filehandle )\r
+\r
+unsigned char fr_seek ( F_FILE * filehandle, long offset, unsigned char whence );\r
+#define f_seek( filehandle, offset, whence ) fr_seek( filehandle, offset, whence )\r
+\r
+long fr_tell ( F_FILE * filehandle );\r
+#define f_tell( filehandle )     fr_tell( filehandle )\r
+int fr_getc ( F_FILE * filehandle );\r
+#define f_getc( filehandle )     fr_getc( filehandle )\r
+int fr_putc ( int ch, F_FILE * filehandle );\r
+#define f_putc( ch, filehandle ) fr_putc( ch, filehandle )\r
+unsigned char fr_rewind ( F_FILE * filehandle );\r
+#define f_rewind( filehandle )   fr_rewind( filehandle )\r
+unsigned char fr_eof ( F_FILE * filehandle );\r
+#define f_eof( filehandle )      fr_eof( filehandle )\r
+\r
+unsigned char fr_delete ( const char * filename );\r
+#define f_delete( filename ) fr_delete( filename )\r
+\r
+unsigned char fr_seteof ( F_FILE * );\r
+#define f_seteof( file ) fr_seteof( file )\r
+\r
+F_FILE * fr_truncate ( const char *, long );\r
+#define f_truncate( filename, filesize ) fr_truncate( filename, filesize )\r
+\r
+#define f_close( filehandle )                    fr_close( filehandle )\r
+#define f_open( filename, mode )                 fr_open( filename, mode )\r
+#define f_read( buf, size, _size_t, filehandle ) fr_read( buf, size, _size_t, filehandle )\r
+\r
+#else /* F_FS_THREAD_AWARE */\r
+\r
+unsigned char fn_init ( void );\r
+#define f_init fn_init\r
+#define f_initvolume fn_initvolume\r
+#define f_delvolume  fn_delvolume\r
+\r
+#define f_hardformat( fattype ) fn_hardformat( fattype )\r
+#define f_format( fattype )    fn_hardformat( fattype )\r
+\r
+#define f_getcwd( buffer, maxlen ) fn_getcwd( buffer, maxlen, 1 )\r
+\r
+unsigned char fn_getfreespace ( F_SPACE * pspace );\r
+#define f_getfreespace fn_getfreespace\r
+\r
+\r
+unsigned char fn_chdir ( const char * dirname );\r
+#define f_chdir( dirname ) fn_chdir( dirname )\r
+unsigned char fn_mkdir ( const char * dirname );\r
+#define f_mkdir( dirname ) fn_mkdir( dirname )\r
+unsigned char fn_rmdir ( const char * dirname );\r
+#define f_rmdir( dirname ) fn_rmdir( dirname )\r
+\r
+unsigned char fn_findfirst ( const char * filename, F_FIND * find );\r
+unsigned char fn_findnext ( F_FIND * find );\r
+#define f_findfirst( filename, find ) fn_findfirst( filename, find )\r
+#define f_findnext( find )            fn_findnext( find )\r
+\r
+#define f_filelength( filename ) fn_filelength( filename )\r
+\r
+#define f_getserial( serial )  fn_getserial( serial )\r
+\r
+unsigned char fn_flush ( F_FILE * f );\r
+#define f_flush( filehandle ) fn_flush( filehandle )\r
+\r
+#define f_write( buf, size, _size_t, filehandle ) fn_write( buf, size, _size_t, filehandle )\r
+\r
+#define f_seek( filehandle, offset, whence ) fn_seek( filehandle, offset, whence )\r
+\r
+long fn_tell ( F_FILE * filehandle );\r
+#define f_tell( filehandle )     fn_tell( filehandle )\r
+int fn_getc ( F_FILE * filehandle );\r
+#define f_getc( filehandle )     fn_getc( filehandle )\r
+int fn_putc ( int ch, F_FILE * filehandle );\r
+#define f_putc( ch, filehandle ) fn_putc( ch, filehandle )\r
+unsigned char fn_rewind ( F_FILE * filehandle );\r
+#define f_rewind( filehandle )   fn_rewind( filehandle )\r
+unsigned char fn_eof ( F_FILE * filehandle );\r
+#define f_eof( filehandle )      fn_eof( filehandle )\r
+\r
+unsigned char fn_delete ( const char * filename );\r
+#define f_delete( filename ) fn_delete( filename )\r
+\r
+unsigned char fn_seteof ( F_FILE * );\r
+#define f_seteof( file ) fn_seteof( file )\r
+\r
+F_FILE * fn_truncate ( const char *, long );\r
+#define f_truncate( filename, filesize ) fn_truncate( filename, filesize )\r
+\r
+#define f_close( filehandle )                    fn_close( filehandle )\r
+#define f_open( filename, mode )                 fn_open( filename, mode )\r
+#define f_read( buf, size, _size_t, filehandle ) fn_read( buf, size, _size_t, filehandle )\r
+\r
+#endif /* F_FS_THREAD_AWARE */\r
+\r
+/****************************************************************************\r
+ *\r
+ * end of fat_sl.h\r
+ *\r
+ ***************************************************************************/\r
+#ifdef __cplusplus\r
+}\r
+#endif\r
+\r
+#endif /*_API_FAT_SL_H_*/\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/config/config_fat_sl_template.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/config/config_fat_sl_template.h
new file mode 100644 (file)
index 0000000..2ecf569
--- /dev/null
@@ -0,0 +1,69 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef _CONFIG_FAT_SL_H\r
+#define _CONFIG_FAT_SL_H\r
+\r
+#include "../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+#include "../api/api_mdriver.h"\r
+\r
+#ifdef __cplusplus\r
+extern "C" {\r
+#endif\r
+\r
+\r
+/**************************************************************************\r
+**\r
+**  FAT SL user settings\r
+**\r
+**************************************************************************/\r
+#define F_SECTOR_SIZE           512u  /* Disk sector size. */\r
+#define F_FS_THREAD_AWARE       1     /* Set to one if the file system will be access from more than one task. */\r
+#define F_MAXPATH               64    /* Maximum length a file name (including its full path) can be. */\r
+#define F_MAX_LOCK_WAIT_TICKS   20    /* The maximum number of RTOS ticks to wait when attempting to obtain a lock on the file system when F_FS_THREAD_AWARE is set to 1. */\r
+\r
+#ifdef __cplusplus\r
+}\r
+#endif\r
+\r
+#endif /* _CONFIG_FAT_SL_H */\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/config/config_mdriver_ram_template.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/config/config_mdriver_ram_template.h
new file mode 100644 (file)
index 0000000..5912ed0
--- /dev/null
@@ -0,0 +1,54 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef _CONFIG_MDRIVER_RAM_H_\r
+#define _CONFIG_MDRIVER_RAM_H_\r
+\r
+#include "../version/ver_mdriver_ram.h"\r
+#if VER_MDRIVER_RAM_MAJOR != 1 || VER_MDRIVER_RAM_MINOR != 2\r
+ #error Incompatible MDRIVER_RAM version number!\r
+#endif\r
+\r
+#define MDRIVER_RAM_SECTOR_SIZE   512       /* Sector size */\r
+\r
+#define MDRIVER_RAM_VOLUME0_SIZE  (128 * 1024) /* defintion for size of ramdrive0 */\r
+\r
+#define MDRIVER_MEM_LONG_ACCESS   1         /* set this value to 1 if 32bit access available */\r
+\r
+#endif /* ifndef _CONFIG_MDRIVER_RAM_H_ */\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/dir.c b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/dir.c
new file mode 100644 (file)
index 0000000..815db86
--- /dev/null
@@ -0,0 +1,1219 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#include "../../api/fat_sl.h"\r
+#include "../../psp/include/psp_string.h"\r
+\r
+#include "dir.h"\r
+#include "util.h"\r
+#include "volume.h"\r
+#include "drv.h"\r
+#include "fat.h"\r
+#include "file.h"\r
+\r
+#include "../../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_findfilewc\r
+ *\r
+ * internal function to finding file in directory entry with or without\r
+ * wildcard\r
+ *\r
+ * INPUTS\r
+ *\r
+ * name - filename\r
+ * ext - fileextension\r
+ * pos - where to start searching, and contains current position\r
+ * pde - store back the directory entry pointer\r
+ * wc - wildcard checking?\r
+ *\r
+ * RETURNS\r
+ *\r
+ * 0 - if file was not found\r
+ * 1 - if file was found\r
+ *\r
+ ***************************************************************************/\r
+unsigned char _f_findfilewc ( char * name, char * ext, F_POS * pos, F_DIRENTRY * * pde, unsigned char wc )\r
+{\r
+  while ( pos->cluster < F_CLUSTER_RESERVED )\r
+  {\r
+    for ( ; pos->sector < pos->sectorend ; pos->sector++ )\r
+    {\r
+      F_DIRENTRY * de = (F_DIRENTRY *)( gl_sector + sizeof( F_DIRENTRY ) * pos->pos );\r
+\r
+      if ( _f_readglsector( pos->sector ) )\r
+      {\r
+        return 0;                                         /*not found*/\r
+      }\r
+\r
+      for ( ; pos->pos < F_SECTOR_SIZE / sizeof( F_DIRENTRY ) ; de++, pos->pos++ )\r
+      {\r
+        unsigned char  b, ok;\r
+\r
+        if ( !de->name[0] )\r
+        {\r
+          return 0;                                                /*empty*/\r
+        }\r
+\r
+        if ( (unsigned char)( de->name[0] ) == 0xe5 )\r
+        {\r
+          continue;                                                 /*deleted*/\r
+        }\r
+\r
+        if ( de->attr & F_ATTR_VOLUME )\r
+        {\r
+          continue;\r
+        }\r
+\r
+        if ( wc )\r
+        {\r
+          for ( b = 0, ok = 1 ; b < sizeof( de->name ) ; b++ )\r
+          {\r
+            if ( name[b] == '*' )\r
+            {\r
+              break;\r
+            }\r
+\r
+            if ( name[b] != '?' )\r
+            {\r
+              if ( de->name[b] != name[b] )\r
+              {\r
+                ok = 0;\r
+                break;\r
+              }\r
+            }\r
+          }\r
+\r
+          if ( ok )\r
+          {\r
+            for ( b = 0, ok = 1 ; b < sizeof( de->ext ) ; b++ )\r
+            {\r
+              if ( ext[b] == '*' )\r
+              {\r
+                if ( pde )\r
+                {\r
+                  *pde = de;\r
+                }\r
+\r
+                return 1;\r
+              }\r
+\r
+              if ( ext[b] != '?' )\r
+              {\r
+                if ( de->ext[b] != ext[b] )\r
+                {\r
+                  ok = 0;\r
+                  break;\r
+                }\r
+              }\r
+            }\r
+\r
+            if ( ok )\r
+            {\r
+              if ( pde )\r
+              {\r
+                *pde = de;\r
+              }\r
+\r
+              return 1;\r
+            }\r
+          }\r
+        }\r
+        else\r
+        {\r
+          for ( b = 0, ok = 1 ; b < sizeof( de->name ) ; b++ )\r
+          {\r
+            if ( de->name[b] != name[b] )\r
+            {\r
+              ok = 0;\r
+              break;\r
+            }\r
+          }\r
+\r
+          if ( ok )\r
+          {\r
+            for ( b = 0, ok = 1 ; b < sizeof( de->ext ) ; b++ )\r
+            {\r
+              if ( de->ext[b] != ext[b] )\r
+              {\r
+                ok = 0;\r
+                break;\r
+              }\r
+            }\r
+\r
+            if ( ok )\r
+            {\r
+              if ( pde )\r
+              {\r
+                *pde = de;\r
+              }\r
+\r
+              return 1;\r
+            }\r
+          }\r
+        }\r
+      }\r
+\r
+      pos->pos = 0;\r
+    }\r
+\r
+    if ( !pos->cluster )\r
+    {\r
+      if ( gl_volume.mediatype == F_FAT32_MEDIA )\r
+      {\r
+        pos->cluster = gl_volume.bootrecord.rootcluster;\r
+      }\r
+      else\r
+        return 0;\r
+    }\r
+\r
+    {\r
+      unsigned long  nextcluster;\r
+      gl_volume.fatsector = (unsigned long)-1;\r
+      if ( _f_getclustervalue( pos->cluster, &nextcluster ) )\r
+      {\r
+        return 0;                                                          /*not found*/\r
+      }\r
+\r
+      if ( nextcluster >= F_CLUSTER_RESERVED )\r
+      {\r
+        return 0;                                            /*eof*/\r
+      }\r
+\r
+      _f_clustertopos( nextcluster, pos );\r
+    }\r
+  } /* _f_findfilewc */\r
+\r
+  return 0;\r
+}\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_getfilename\r
+ *\r
+ * create a complete filename from name and extension\r
+ *\r
+ * INPUTS\r
+ *\r
+ * dest - where to store filename\r
+ * name - name of the file\r
+ * ext - extension of the file\r
+ *\r
+ ***************************************************************************/\r
+static void _f_getfilename ( char * dest, char * name, char * ext )\r
+{\r
+  unsigned char  a, len;\r
+\r
+  for ( len = a = F_MAXNAME ; a ; a--, len-- )\r
+  {\r
+    if ( name[a - 1] != ' ' )\r
+    {\r
+      break;\r
+    }\r
+  }\r
+\r
+  for ( a = 0 ; a < len ; a++ )\r
+  {\r
+    *dest++ = *name++;\r
+  }\r
+\r
+\r
+  for ( len = a = F_MAXEXT ; a ; a--, len-- )\r
+  {\r
+    if ( ext[a - 1] != ' ' )\r
+    {\r
+      break;\r
+    }\r
+  }\r
+\r
+  if ( len )\r
+  {\r
+    *dest++ = '.';\r
+  }\r
+\r
+  for ( a = 0 ; a < len ; a++ )\r
+  {\r
+    *dest++ = *ext++;\r
+  }\r
+\r
+  *dest = 0; /*terminateit*/\r
+} /* _f_getfilename */\r
+\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_getdecluster\r
+ *\r
+ * get a directory entry structure start cluster value\r
+ *\r
+ * INPUTS\r
+ *\r
+ * de - directory entry\r
+ *\r
+ * RETURNS\r
+ *\r
+ * directory entry cluster value\r
+ *\r
+ ***************************************************************************/\r
+unsigned long _f_getdecluster ( F_DIRENTRY * de )\r
+{\r
+  unsigned long  cluster;\r
+  if ( gl_volume.mediatype == F_FAT32_MEDIA )\r
+  {\r
+    cluster = _f_getword( &de->clusterhi );\r
+    cluster <<= 16;\r
+    cluster |= _f_getword( &de->clusterlo );\r
+    return cluster;\r
+  }\r
+\r
+  return _f_getword( &de->clusterlo );\r
+}\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_setdecluster\r
+ *\r
+ * set a directory entry structure start cluster value\r
+ *\r
+ * INPUTS\r
+ *\r
+ * de - directory entry\r
+ * cluster - value of the start cluster\r
+ *\r
+ ***************************************************************************/\r
+void _f_setdecluster ( F_DIRENTRY * de, unsigned long cluster )\r
+{\r
+  _f_setword( &de->clusterlo, (unsigned short)( cluster & 0xffff ) );\r
+  if ( gl_volume.mediatype == F_FAT32_MEDIA )\r
+  {\r
+    _f_setword( &de->clusterhi, (unsigned short)( cluster >> 16 ) );\r
+  }\r
+  else\r
+  {\r
+    _f_setword( &de->clusterhi, (unsigned short)0 );\r
+  }\r
+}\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_findpath\r
+ *\r
+ * finding out if path is valid in F_NAME and\r
+ * correct path info with absolute path (removes relatives)\r
+ *\r
+ * INPUTS\r
+ *\r
+ * fsname - filled structure with path,drive\r
+ * pos - where to start searching, and contains current position\r
+ *\r
+ * RETURNS\r
+ *\r
+ * 0 - if path was not found or invalid\r
+ * 1 - if path was found\r
+ *\r
+ ***************************************************************************/\r
+unsigned char _f_findpath ( F_NAME * fsname, F_POS * pos )\r
+{\r
+  char       * path = fsname->path;\r
+  char       * mpath = path;\r
+  F_DIRENTRY * de;\r
+\r
+  _f_clustertopos( 0, pos );\r
+\r
+  for ( ; *path ; )\r
+  {\r
+    char           name[F_MAXNAME];\r
+    char           ext[F_MAXEXT];\r
+\r
+    unsigned char  len = _f_setnameext( path, name, ext );\r
+\r
+    if ( ( pos->cluster == 0 ) && ( len == 1 ) && ( name[0] == '.' ) )\r
+    {\r
+      _f_clustertopos( 0, pos );\r
+    }\r
+    else\r
+    {\r
+      if ( !_f_findfilewc( name, ext, pos, &de, 0 ) )\r
+      {\r
+        return 0;\r
+      }\r
+      if ( !( de->attr & F_ATTR_DIR ) )\r
+      {\r
+        return 0;\r
+      }\r
+\r
+      _f_clustertopos( _f_getdecluster( de ), pos );\r
+    }\r
+\r
+\r
+    if ( name[0] == '.' )\r
+    {\r
+      if ( len == 1 )\r
+      {\r
+        path += len;\r
+\r
+        if ( !( *path ) )\r
+        {\r
+          if ( mpath != fsname->path )\r
+          {\r
+            mpath--;                                  /*if we are now at the top*/\r
+          }\r
+\r
+          break;\r
+        }\r
+\r
+        path++;\r
+        continue;\r
+      }\r
+\r
+      if ( name[1] != '.' )\r
+      {\r
+        return 0;                       /*invalid name*/\r
+      }\r
+\r
+      if ( len != 2 )\r
+      {\r
+        return 0;                 /*invalid name !*/\r
+      }\r
+\r
+      path += len;\r
+\r
+      if ( mpath == fsname->path )\r
+      {\r
+        return 0;                              /*we are in the top*/\r
+      }\r
+\r
+      mpath--;       /*no on separator*/\r
+      for ( ; ; )\r
+      {\r
+        if ( mpath == fsname->path )\r
+        {\r
+          break;                                /*we are now at the top*/\r
+        }\r
+\r
+        mpath--;\r
+        if ( *mpath == '/' )\r
+        {\r
+          mpath++;\r
+          break;\r
+        }\r
+      }\r
+\r
+      if ( !( *path ) )\r
+      {\r
+        if ( mpath != fsname->path )\r
+        {\r
+          mpath--;                                /*if we are now at the top*/\r
+        }\r
+\r
+        break;\r
+      }\r
+\r
+      path++;\r
+      continue;\r
+    }\r
+    else\r
+    {\r
+      if ( path == mpath )                              /*if no was dots just step*/\r
+      {\r
+        path += len;\r
+        mpath += len;\r
+      }\r
+      else\r
+      {\r
+        unsigned char  a;\r
+        for ( a = 0 ; a < len ; a++ )\r
+        {\r
+          *mpath++ = *path++;                            /*copy if in different pos*/\r
+        }\r
+      }\r
+    }\r
+\r
+    if ( !( *path ) )\r
+    {\r
+      break;\r
+    }\r
+\r
+    path++;\r
+    *mpath++ = '/';   /*add separator*/\r
+  }\r
+\r
+  *mpath = 0; /*terminate it*/\r
+  return 1;\r
+} /* _f_findpath */\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_getcwd\r
+ *\r
+ * getting a current working directory of current drive\r
+ *\r
+ * INPUTS\r
+ *\r
+ * buffer - where to store current working folder\r
+ * maxlen - buffer length (possible size is F_MAXPATH)\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+\r
+\r
+unsigned char fn_getcwd ( char * buffer, unsigned char maxlen, char root )\r
+{\r
+  unsigned char  a;\r
+\r
+  if ( !maxlen )\r
+  {\r
+    return F_NO_ERROR;\r
+  }\r
+\r
+  maxlen--;     /*need for termination*/\r
+  if ( root && maxlen )\r
+  {\r
+    *buffer++ = '/';\r
+    maxlen--;\r
+  }\r
+\r
+  for ( a = 0 ; a < maxlen ; a++ )\r
+  {\r
+    char  ch = gl_volume.cwd[a];\r
+    buffer[a] = ch;\r
+    if ( !ch )\r
+    {\r
+      break;\r
+    }\r
+  }\r
+\r
+  buffer[a] = 0;    /*add terminator at the end*/\r
+\r
+  return F_NO_ERROR;\r
+} /* fn_getcwd */\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_findfirst\r
+ *\r
+ * find a file(s) or directory(s) in directory\r
+ *\r
+ * INPUTS\r
+ *\r
+ * filename - filename (with or without wildcards)\r
+ * find - where to store found file information\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+\r
+\r
+unsigned char fn_findfirst ( const char * filename, F_FIND * find )\r
+{\r
+  unsigned char  ret;\r
+\r
+  if ( _f_setfsname( filename, &find->findfsname ) )\r
+  {\r
+    return F_ERR_INVALIDNAME;  /*invalid name*/\r
+  }\r
+\r
+  if ( _f_checkname( find->findfsname.filename, find->findfsname.fileext ) )\r
+  {\r
+    return F_ERR_INVALIDNAME;  /*invalid name, wildcard is ok*/\r
+  }\r
+\r
+\r
+  ret = _f_getvolume();\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  if ( !_f_findpath( &find->findfsname, &find->pos ) )\r
+  {\r
+    return F_ERR_INVALIDDIR;   /*search for path*/\r
+  }\r
+\r
+  return fn_findnext( find );\r
+} /* fn_findfirst */\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_findnext\r
+ *\r
+ * find further file(s) or directory(s) in directory\r
+ *\r
+ * INPUTS\r
+ *\r
+ * find - where to store found file information (findfirst should call 1st)\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+\r
+\r
+unsigned char fn_findnext ( F_FIND * find )\r
+{\r
+  F_DIRENTRY   * de;\r
+  unsigned char  a;\r
+  unsigned char  ret;\r
+\r
+  ret = _f_getvolume();\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  if ( !_f_findfilewc( find->findfsname.filename, find->findfsname.fileext, &find->pos, &de, 1 ) )\r
+  {\r
+    return F_ERR_NOTFOUND;\r
+  }\r
+\r
+  for ( a = 0 ; a < F_MAXNAME ; a++ )\r
+  {\r
+    find->name[a] = de->name[a];\r
+  }\r
+\r
+  for ( a = 0 ; a < F_MAXEXT ; a++ )\r
+  {\r
+    find->ext[a] = de->ext[a];\r
+  }\r
+\r
+  _f_getfilename( find->filename, (char *)de->name, (char *)de->ext );\r
+\r
+  find->attr = de->attr;\r
+  find->cdate = _f_getword( &de->cdate );\r
+  find->ctime = _f_getword( &de->ctime );\r
+  find->filesize = (long)_f_getlong( &de->filesize );\r
+  find->cluster = _f_getdecluster( de );\r
+  find->pos.pos++;   /*goto next position*/\r
+\r
+  return 0;\r
+} /* fn_findnext */\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_chdir\r
+ *\r
+ * change current working directory\r
+ *\r
+ * INPUTS\r
+ *\r
+ * dirname - new working directory name\r
+ *\r
+ * RETURNS\r
+ *\r
+ * 0 - if successfully\r
+ * other - if any error\r
+ *\r
+ ***************************************************************************/\r
+unsigned char fn_chdir ( const char * dirname )\r
+{\r
+  F_POS          pos;\r
+  F_NAME         fsname;\r
+  unsigned char  len;\r
+  unsigned char  a;\r
+  unsigned char  ret;\r
+\r
+  ret = _f_setfsname( dirname, &fsname );\r
+\r
+  if ( ret == 1 )\r
+  {\r
+    return F_ERR_INVALIDNAME;             /*invalid name*/\r
+  }\r
+\r
+  if ( _f_checknamewc( fsname.filename, fsname.fileext ) )\r
+  {\r
+    return F_ERR_INVALIDNAME;                                                    /*invalid name*/\r
+  }\r
+\r
+  ret = _f_getvolume();\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  for ( len = 0 ; fsname.path[len] ; )\r
+  {\r
+    len++;\r
+  }\r
+\r
+  if ( len && ( ( fsname.filename[0] != 32 ) || ( fsname.fileext[0] != 32 ) ) )\r
+  {\r
+    fsname.path[len++] = '/';\r
+  }\r
+\r
+  _f_getfilename( fsname.path + len, fsname.filename, fsname.fileext );\r
+\r
+  if ( !( _f_findpath( &fsname, &pos ) ) )\r
+  {\r
+    return F_ERR_NOTFOUND;\r
+  }\r
+\r
+  for ( a = 0 ; a < F_MAXPATH ; a++ )\r
+  {\r
+    gl_volume.cwd[a] = fsname.path[a];\r
+  }\r
+\r
+  return F_NO_ERROR;\r
+} /* fn_chdir */\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_initentry\r
+ *\r
+ * init directory entry, this function is called if a new entry is coming\r
+ *\r
+ * INPUTS\r
+ *\r
+ * de - directory entry which needs to be initialized\r
+ * name - fil ename  (8)\r
+ * ext - file extension (3)\r
+ *\r
+ ***************************************************************************/\r
+static void _f_initentry ( F_DIRENTRY * de, char * name, char * ext )\r
+{\r
+  unsigned short  date;\r
+  unsigned short  time;\r
+\r
+  psp_memset( de, 0, sizeof( F_DIRENTRY ) ); /*reset all entries*/\r
+\r
+  psp_memcpy( de->name, name, sizeof( de->name ) );\r
+  psp_memcpy( de->ext, ext, sizeof( de->ext ) );\r
+\r
+  f_igettimedate( &time, &date );\r
+  _f_setword( &de->cdate, date ); /*if there is realtime clock then creation date could be set from*/\r
+  _f_setword( &de->ctime, time ); /*if there is realtime clock then creation time could be set from*/\r
+}\r
+\r
+\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_addentry\r
+ *\r
+ * Add a new directory entry into driectory list\r
+ *\r
+ * INPUTS\r
+ *\r
+ * fs_name - filled structure what to add into directory list\r
+ * pos - where directory cluster chains starts\r
+ * pde - F_DIRENTRY pointer where to store the entry where it was added\r
+ *\r
+ * RETURNS\r
+ *\r
+ * 0 - if successfully added\r
+ * other - if any error (see FS_xxx errorcodes)\r
+ *\r
+ ***************************************************************************/\r
+unsigned char _f_addentry ( F_NAME * fsname, F_POS * pos, F_DIRENTRY * * pde )\r
+{\r
+  unsigned char   ret;\r
+  unsigned short  date;\r
+  unsigned short  time;\r
+\r
+  if ( !fsname->filename[0] )\r
+  {\r
+    return F_ERR_INVALIDNAME;\r
+  }\r
+\r
+  if ( fsname->filename[0] == '.' )\r
+  {\r
+    return F_ERR_INVALIDNAME;\r
+  }\r
+\r
+  while ( pos->cluster < F_CLUSTER_RESERVED )\r
+  {\r
+    for ( ; pos->sector < pos->sectorend ; pos->sector++ )\r
+    {\r
+      F_DIRENTRY * de = (F_DIRENTRY *)( gl_sector + sizeof( F_DIRENTRY ) * pos->pos );\r
+\r
+      ret = _f_readglsector( pos->sector );\r
+      if ( ret )\r
+      {\r
+        return ret;\r
+      }\r
+\r
+      for ( ; pos->pos < F_SECTOR_SIZE / sizeof( F_DIRENTRY ) ; de++, pos->pos++ )\r
+      {\r
+        if ( ( !de->name[0] ) || ( (unsigned char)( de->name[0] ) == 0xe5 ) )\r
+        {\r
+          _f_initentry( de, fsname->filename, fsname->fileext );\r
+          if ( gl_volume.mediatype == F_FAT32_MEDIA )\r
+          {\r
+            f_igettimedate( &time, &date );\r
+            _f_setword( &de->crtdate, date );             /*if there is realtime clock then creation date could be set from*/\r
+            _f_setword( &de->crttime, time );             /*if there is realtime clock then creation time could be set from*/\r
+            _f_setword( &de->lastaccessdate, date );      /*if there is realtime clock then creation date could be set from*/\r
+          }\r
+\r
+          if ( pde )\r
+          {\r
+            *pde = de;\r
+          }\r
+\r
+          return F_NO_ERROR;\r
+        }\r
+      }\r
+\r
+      pos->pos = 0;\r
+    }\r
+\r
+    if ( !pos->cluster )\r
+    {\r
+      if ( gl_volume.mediatype == F_FAT32_MEDIA )\r
+      {\r
+        pos->cluster = gl_volume.bootrecord.rootcluster;\r
+      }\r
+      else\r
+        return F_ERR_NOMOREENTRY;\r
+    }\r
+\r
+    {\r
+      unsigned long  cluster;\r
+\r
+      gl_volume.fatsector = (unsigned long)-1;\r
+      ret = _f_getclustervalue( pos->cluster, &cluster );    /*try to get next cluster*/\r
+      if ( ret )\r
+      {\r
+        return ret;\r
+      }\r
+\r
+      if ( cluster < F_CLUSTER_RESERVED )\r
+      {\r
+        _f_clustertopos( cluster, pos );\r
+      }\r
+      else\r
+      {\r
+        ret = _f_alloccluster( &cluster );        /*get a new one*/\r
+        if ( ret )\r
+        {\r
+          return ret;\r
+        }\r
+\r
+        if ( cluster < F_CLUSTER_RESERVED )\r
+        {\r
+          if ( gl_file.mode != F_FILE_CLOSE )\r
+          {\r
+            return F_ERR_NOMOREENTRY;\r
+          }\r
+\r
+          _f_clustertopos( cluster, &gl_file.pos );\r
+\r
+          ret = _f_setclustervalue( gl_file.pos.cluster, F_CLUSTER_LAST );\r
+          if ( ret )\r
+          {\r
+            return ret;\r
+          }\r
+\r
+          ret = _f_setclustervalue( pos->cluster, gl_file.pos.cluster );\r
+          if ( ret )\r
+          {\r
+            return ret;\r
+          }\r
+\r
+          ret = _f_writefatsector();\r
+          if ( ret )\r
+          {\r
+            return ret;\r
+          }\r
+\r
+          gl_volume.fatsector = (unsigned long)-1;\r
+          psp_memset( gl_sector, 0, F_SECTOR_SIZE );\r
+          while ( gl_file.pos.sector < gl_file.pos.sectorend )\r
+          {\r
+            ret = _f_writeglsector( gl_file.pos.sector );\r
+            if ( ret )\r
+            {\r
+              return ret;\r
+            }\r
+\r
+            gl_file.pos.sector++;\r
+          }\r
+\r
+          _f_clustertopos( gl_file.pos.cluster, pos );\r
+        }\r
+        else\r
+        {\r
+          return F_ERR_NOMOREENTRY;\r
+        }\r
+      }\r
+    }\r
+  } /* _f_addentry */\r
+\r
+  return F_ERR_NOMOREENTRY;\r
+}\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_mkdir\r
+ *\r
+ * making a new directory\r
+ *\r
+ * INPUTS\r
+ *\r
+ * dirname - new directory name\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+unsigned char fn_mkdir ( const char * dirname )\r
+{\r
+  F_POS          posdir;\r
+  F_POS          pos;\r
+  F_DIRENTRY   * de;\r
+  F_NAME         fsname;\r
+  unsigned long  cluster;\r
+  unsigned char  ret;\r
+\r
+ #if F_FILE_CHANGED_EVENT\r
+  ST_FILE_CHANGED  fc;\r
+ #endif\r
+\r
+  if ( _f_setfsname( dirname, &fsname ) )\r
+  {\r
+    return F_ERR_INVALIDNAME;                                    /*invalid name*/\r
+  }\r
+\r
+  if ( _f_checknamewc( fsname.filename, fsname.fileext ) )\r
+  {\r
+    return F_ERR_INVALIDNAME;                                                    /*invalid name*/\r
+  }\r
+\r
+  ret = _f_getvolume();\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  if ( !_f_findpath( &fsname, &posdir ) )\r
+  {\r
+    return F_ERR_INVALIDDIR;\r
+  }\r
+\r
+  pos = posdir;\r
+\r
+  if ( fsname.filename[0] == '.' )\r
+  {\r
+    return F_ERR_NOTFOUND;\r
+  }\r
+\r
+  if ( _f_findfilewc( fsname.filename, fsname.fileext, &pos, &de, 0 ) )\r
+  {\r
+    return F_ERR_DUPLICATED;\r
+  }\r
+\r
+  pos = posdir;\r
+\r
+  gl_volume.fatsector = (unsigned long)-1;\r
+  ret = _f_alloccluster( &cluster );\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  ret = _f_addentry( &fsname, &pos, &de );\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  de->attr |= F_ATTR_DIR;       /*set as directory*/\r
+\r
+ #if F_FILE_CHANGED_EVENT\r
+  if ( f_filechangedevent )\r
+  {\r
+    fc.action = FACTION_ADDED;\r
+    fc.flags = FFLAGS_DIR_NAME | FFLAGS_ATTRIBUTES | FFLAGS_SIZE | FFLAGS_LAST_WRITE;\r
+    fc.attr = de->attr;\r
+    fc.ctime = _f_getword( de->ctime );\r
+    fc.cdate = _f_getword( de->cdate );\r
+    fc.filesize = _f_getlong( de->filesize );\r
+  }\r
+\r
+ #endif\r
+\r
+  if ( gl_file.mode != F_FILE_CLOSE )\r
+  {\r
+    return F_ERR_LOCKED;\r
+  }\r
+\r
+  _f_clustertopos( cluster, &gl_file.pos );\r
+  _f_setdecluster( de, cluster ); /*new dir*/\r
+\r
+  (void)_f_writeglsector( (unsigned long)-1 );  /*write actual directory sector*/\r
+\r
+\r
+  de = (F_DIRENTRY *)gl_sector;\r
+\r
+  _f_initentry( de, ".       ", "   " );\r
+  de->attr = F_ATTR_DIR;          /*set as directory*/\r
+  _f_setdecluster( de, cluster ); /*current*/\r
+  de++;\r
+\r
+  _f_initentry( de, "..      ", "   " );\r
+  de->attr = F_ATTR_DIR;                 /*set as directory*/\r
+  _f_setdecluster( de, posdir.cluster ); /*parent*/\r
+  de++;\r
+\r
+  psp_memset( de, 0, ( F_SECTOR_SIZE - 2 * sizeof( F_DIRENTRY ) ) );\r
+\r
+\r
+  ret = _f_writeglsector( gl_file.pos.sector );\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  gl_file.pos.sector++;\r
+  psp_memset( gl_sector, 0, ( 2 * sizeof( F_DIRENTRY ) ) );\r
+  while ( gl_file.pos.sector < gl_file.pos.sectorend )\r
+  {\r
+    ret = _f_writeglsector( gl_file.pos.sector );\r
+    if ( ret )\r
+    {\r
+      return ret;\r
+    }\r
+\r
+    gl_file.pos.sector++;\r
+  }\r
+\r
+  gl_volume.fatsector = (unsigned long)-1;\r
+  ret = _f_setclustervalue( gl_file.pos.cluster, F_CLUSTER_LAST );\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  ret = _f_writefatsector();\r
+ #if F_FILE_CHANGED_EVENT\r
+  if ( f_filechangedevent && !ret )\r
+  {\r
+    fc.action = FACTION_ADDED;\r
+    fc.flags = FFLAGS_DIR_NAME;\r
+\r
+    if ( !_f_createfullname( fc.filename, sizeof( fc.filename ), fsname.path, fsname.filename, fsname.fileext ) )\r
+    {\r
+      f_filechangedevent( &fc );\r
+    }\r
+  }\r
+\r
+ #endif\r
+\r
+  return ret;\r
+} /* fn_mkdir */\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_rmdir\r
+ *\r
+ * Remove directory, only could be removed if empty\r
+ *\r
+ * INPUTS\r
+ *\r
+ * dirname - which directory needed to be removed\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+unsigned char fn_rmdir ( const char * dirname )\r
+{\r
+  unsigned char  ret;\r
+  F_POS          pos;\r
+  F_DIRENTRY   * de;\r
+  F_NAME         fsname;\r
+  unsigned long  dirsector;\r
+  unsigned char  a;\r
+\r
+  if ( _f_setfsname( dirname, &fsname ) )\r
+  {\r
+    return F_ERR_INVALIDNAME;                                    /*invalid name*/\r
+  }\r
+\r
+  if ( _f_checknamewc( fsname.filename, fsname.fileext ) )\r
+  {\r
+    return F_ERR_INVALIDNAME;                                                    /*invalid name*/\r
+  }\r
+\r
+  if ( fsname.filename[0] == '.' )\r
+  {\r
+    return F_ERR_NOTFOUND;\r
+  }\r
+\r
+  ret = _f_getvolume();\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  if ( !( _f_findpath( &fsname, &pos ) ) )\r
+  {\r
+    return F_ERR_INVALIDDIR;\r
+  }\r
+\r
+  if ( !_f_findfilewc( fsname.filename, fsname.fileext, &pos, &de, 0 ) )\r
+  {\r
+    return F_ERR_NOTFOUND;\r
+  }\r
+\r
+  if ( !( de->attr & F_ATTR_DIR ) )\r
+  {\r
+    return F_ERR_INVALIDDIR;                                       /*not a directory*/\r
+  }\r
+\r
+  dirsector = gl_volume.actsector;\r
+\r
+  if ( gl_file.mode != F_FILE_CLOSE )\r
+  {\r
+    return F_ERR_LOCKED;\r
+  }\r
+\r
+  _f_clustertopos( _f_getdecluster( de ), &gl_file.pos );\r
+\r
+  for ( ; ; )\r
+  {\r
+    F_DIRENTRY * de2;\r
+    char         ch = 0;\r
+\r
+    ret = _f_getcurrsector();\r
+    if ( ret == F_ERR_EOF )\r
+    {\r
+      break;\r
+    }\r
+\r
+    if ( ret )\r
+    {\r
+      return ret;\r
+    }\r
+\r
+    de2 = (F_DIRENTRY *)gl_sector;\r
+    for ( a = 0 ; a < ( F_SECTOR_SIZE / sizeof( F_DIRENTRY ) ) ; a++, de2++ )\r
+    {\r
+      ch = de2->name[0];\r
+      if ( !ch )\r
+      {\r
+        break;\r
+      }\r
+\r
+      if ( (unsigned char)ch == 0xe5 )\r
+      {\r
+        continue;\r
+      }\r
+\r
+      if ( ch == '.' )\r
+      {\r
+        continue;\r
+      }\r
+\r
+      return F_ERR_NOTEMPTY;       /*something is there*/\r
+    }\r
+\r
+    if ( !ch )\r
+    {\r
+      break;\r
+    }\r
+\r
+    gl_file.pos.sector++;\r
+  }\r
+\r
+  ret = _f_readglsector( dirsector );\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  de->name[0] = (unsigned char)0xe5;\r
+\r
+  ret = _f_writeglsector( dirsector );\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  gl_volume.fatsector = (unsigned long)-1;\r
+  ret = _f_removechain( _f_getdecluster( de ) );\r
+ #if F_FILE_CHANGED_EVENT\r
+  if ( f_filechangedevent && !ret )\r
+  {\r
+    ST_FILE_CHANGED  fc;\r
+    fc.action = FACTION_REMOVED;\r
+    fc.flags = FFLAGS_DIR_NAME;\r
+\r
+    if ( !_f_createfullname( fc.filename, sizeof( fc.filename ), fsname.path, fsname.filename, fsname.fileext ) )\r
+    {\r
+      f_filechangedevent( &fc );\r
+    }\r
+  }\r
+\r
+ #endif\r
+  return ret;\r
+} /* fn_rmdir */\r
+\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/dir.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/dir.h
new file mode 100644 (file)
index 0000000..467973c
--- /dev/null
@@ -0,0 +1,90 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef __DIR_H\r
+#define __DIR_H\r
+\r
+#include "../../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+#ifdef __cplusplus\r
+extern "C" {\r
+#endif\r
+\r
+\r
+\r
+\r
+#define NTRES_LOW           0x08 /*lower case name*/\r
+\r
+\r
+typedef struct\r
+{\r
+  unsigned char  name[F_MAXNAME];   /* 8+3 */\r
+  unsigned char  ext[F_MAXEXT];\r
+  unsigned char  attr;                  /* 00ADVSHR */\r
+\r
+  unsigned char  ntres;             /* FAT32 only  */\r
+  unsigned char  crttimetenth;      /* FAT32 only  */\r
+  unsigned char  crttime[2];        /* FAT32 only  */\r
+  unsigned char  crtdate[2];        /* FAT32 only */\r
+  unsigned char  lastaccessdate[2]; /* FAT32 only */\r
+\r
+  unsigned char  clusterhi[2]; /* FAT32 only */\r
+  unsigned char  ctime[2];\r
+  unsigned char  cdate[2];\r
+  unsigned char  clusterlo[2]; /* fat12,fat16,fat32 */\r
+  unsigned char  filesize[4];\r
+} F_DIRENTRY;\r
+\r
+\r
+unsigned char _f_getdirsector ( unsigned long );\r
+unsigned char _f_findfilewc ( char *, char *, F_POS *, F_DIRENTRY * *, unsigned char );\r
+unsigned char _f_findpath ( F_NAME *, F_POS * );\r
+unsigned long _f_getdecluster ( F_DIRENTRY * );\r
+\r
+unsigned char _f_writedirsector ( void );\r
+void _f_setdecluster ( F_DIRENTRY *, unsigned long );\r
+unsigned char _f_addentry ( F_NAME *, F_POS *, F_DIRENTRY * * );\r
+\r
+#ifdef __cplusplus\r
+}\r
+#endif\r
+\r
+#endif /* ifndef __DIR_H */\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/drv.c b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/drv.c
new file mode 100644 (file)
index 0000000..82f19bd
--- /dev/null
@@ -0,0 +1,216 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#include "../../api/fat_sl.h"\r
+#include "../../psp/include/psp_string.h"\r
+\r
+#include "drv.h"\r
+#include "util.h"\r
+#include "volume.h"\r
+\r
+#include "../../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+F_DRIVER * mdrv = NULL;  /* driver structure */\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_checkstatus\r
+ *\r
+ * checking a volume driver status, if media is removed or has been changed\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+unsigned char _f_checkstatus ( void )\r
+{\r
+  if ( mdrv->getstatus != NULL )\r
+  {\r
+    if ( mdrv->getstatus( mdrv ) & ( F_ST_MISSING | F_ST_CHANGED ) )\r
+    {\r
+      gl_volume.state = F_STATE_NEEDMOUNT; /*card has been removed;*/\r
+      return F_ERR_CARDREMOVED;\r
+    }\r
+  }\r
+\r
+  return F_NO_ERROR;\r
+}\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_writesector\r
+ *\r
+ * write sector data on a volume, it calls low level driver function, it\r
+ * writes a complete sector\r
+ *\r
+ * INPUTS\r
+ * sector - which physical sector\r
+ *\r
+ * RETURNS\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+unsigned char _f_writeglsector ( unsigned long sector )\r
+{\r
+  unsigned char  retry;\r
+\r
+  if ( mdrv->writesector == NULL )\r
+  {\r
+    gl_volume.state = F_STATE_NEEDMOUNT; /*no write function*/\r
+    return F_ERR_ACCESSDENIED;\r
+  }\r
+\r
+  if ( sector == (unsigned long)-1 )\r
+  {\r
+    if ( gl_file.modified )\r
+    {\r
+      sector = gl_file.pos.sector;\r
+    }\r
+    else\r
+    {\r
+      sector = gl_volume.actsector;\r
+    }\r
+  }\r
+\r
+  if ( sector != (unsigned long)-1 )\r
+  {\r
+    if ( mdrv->getstatus != NULL )\r
+    {\r
+      unsigned int  status;\r
+\r
+      status = mdrv->getstatus( mdrv );\r
+\r
+      if ( status & ( F_ST_MISSING | F_ST_CHANGED ) )\r
+      {\r
+        gl_volume.state = F_STATE_NEEDMOUNT; /*card has been removed;*/\r
+        return F_ERR_CARDREMOVED;\r
+      }\r
+\r
+      if ( status & ( F_ST_WRPROTECT ) )\r
+      {\r
+        gl_volume.state = F_STATE_NEEDMOUNT;  /*card has been removed;*/\r
+        return F_ERR_WRITEPROTECT;\r
+      }\r
+    }\r
+\r
+    gl_volume.modified = 0;\r
+    gl_file.modified = 0;\r
+    gl_volume.actsector = sector;\r
+    for ( retry = 3 ; retry ; retry-- )\r
+    {\r
+      int mdrv_ret;\r
+      mdrv_ret = mdrv->writesector( mdrv, (unsigned char *)gl_sector, sector );\r
+      if ( !mdrv_ret )\r
+      {\r
+        return F_NO_ERROR;\r
+      }\r
+\r
+      if ( mdrv_ret == -1 )\r
+      {\r
+        gl_volume.state = F_STATE_NEEDMOUNT; /*card has been removed;*/\r
+        return F_ERR_CARDREMOVED;\r
+      }\r
+    }\r
+  }\r
+\r
+\r
+  return F_ERR_ONDRIVE;\r
+} /* _f_writeglsector */\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_readsector\r
+ *\r
+ * read sector data from a volume, it calls low level driver function, it\r
+ * reads a complete sector\r
+ *\r
+ * INPUTS\r
+ * sector - which physical sector is read\r
+ *\r
+ * RETURNS\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+unsigned char _f_readglsector ( unsigned long sector )\r
+{\r
+  unsigned char  retry;\r
+  unsigned char  ret;\r
+\r
+  if ( sector == gl_volume.actsector )\r
+  {\r
+    return F_NO_ERROR;\r
+  }\r
+\r
+  if ( gl_volume.modified || gl_file.modified )\r
+  {\r
+    ret = _f_writeglsector( (unsigned long)-1 );\r
+    if ( ret )\r
+    {\r
+      return ret;\r
+    }\r
+  }\r
+\r
+\r
+  for ( retry = 3 ; retry ; retry-- )\r
+  {\r
+    int mdrv_ret;\r
+    mdrv_ret = mdrv->readsector( mdrv, (unsigned char *)gl_sector, sector );\r
+    if ( !mdrv_ret )\r
+    {\r
+      gl_volume.actsector = sector;\r
+      return F_NO_ERROR;\r
+    }\r
+\r
+    if ( mdrv_ret == -1 )\r
+    {\r
+      gl_volume.state = F_STATE_NEEDMOUNT; /*card has been removed;*/\r
+      return F_ERR_CARDREMOVED;\r
+    }\r
+  }\r
+\r
+  gl_volume.actsector = (unsigned long)-1;\r
+  return F_ERR_ONDRIVE;\r
+} /* _f_readglsector */\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/drv.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/drv.h
new file mode 100644 (file)
index 0000000..10827a2
--- /dev/null
@@ -0,0 +1,61 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef __DRV_H\r
+#define __DRV_H\r
+\r
+#include "../../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+#ifdef __cplusplus\r
+extern "C" {\r
+#endif\r
+\r
+extern F_DRIVER * mdrv;  /* driver structure */\r
+\r
+unsigned char _f_checkstatus ( void );\r
+unsigned char _f_readglsector ( unsigned long );\r
+unsigned char _f_writeglsector ( unsigned long );\r
+\r
+#ifdef __cplusplus\r
+}\r
+#endif\r
+\r
+#endif /* ifndef __DRV_H */\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/f_lock.c b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/f_lock.c
new file mode 100644 (file)
index 0000000..23ebbf2
--- /dev/null
@@ -0,0 +1,642 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#define FS_MUTEX_DEFINED\r
+\r
+#include "../../api/fat_sl.h"\r
+#include "../../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+#if F_FS_THREAD_AWARE == 1\r
+\r
+xSemaphoreHandle fs_lock_semaphore;\r
+\r
+\r
+/*\r
+** fr_findfirst\r
+**\r
+** find first time a file using wildcards\r
+**\r
+** INPUT : filename - name of the file\r
+**         *find - pointer to a pre-define F_FIND structure\r
+** RETURN: F_NOERR - on success\r
+**         F_ERR_NOTFOUND - if not found\r
+*/\r
+unsigned char fr_findfirst ( const char * filename, F_FIND * find )\r
+{\r
+  unsigned char  rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_findfirst( filename, find );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = F_ERR_OS;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+\r
+/*\r
+** fr_findnext\r
+**\r
+** find next time a file using wildcards\r
+**\r
+** INPUT : *find - pointer to a pre-define F_FIND structure\r
+** RETURN: F_NOERR - on success\r
+**         F_ERR_NOTFOUND - if not found\r
+*/\r
+unsigned char fr_findnext ( F_FIND * find )\r
+{\r
+  unsigned char  rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_findnext( find );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = F_ERR_OS;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+\r
+/*\r
+** fr_filelength\r
+**\r
+** Get the length of a file\r
+**\r
+** INPUT : filename - name of the file\r
+** RETURN: size of the file or F_ERR_INVALID if not exists or volume not working\r
+*/\r
+long fr_filelength ( const char * filename )\r
+{\r
+  unsigned long  rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_filelength( filename );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = 0;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+\r
+/*\r
+** fr_open\r
+**\r
+** open a file\r
+**\r
+** INPUT : filename - file to be opened\r
+**         mode - open method (r,w,a,r+,w+,a+)\r
+** RETURN: pointer to a file descriptor or 0 on error\r
+*/\r
+F_FILE * fr_open ( const char * filename, const char * mode )\r
+{\r
+  F_FILE * rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_open( filename, mode );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = NULL;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+\r
+/*\r
+** fr_close\r
+**\r
+** Close a previously opened file.\r
+**\r
+** INPUT : *filehandle - pointer to the file descriptor\r
+** RETURN: F_NOERR on success, other if error\r
+*/\r
+unsigned char fr_close ( F_FILE * filehandle )\r
+{\r
+  unsigned char  rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_close( filehandle );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = F_ERR_OS;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+\r
+/*\r
+** fr_read\r
+**\r
+** Read from a file.\r
+**\r
+** INPUT : buf - buffer to read data\r
+**         size - number of unique\r
+**         size_st - size of unique\r
+**         *filehandle - pointer to file descriptor\r
+** OUTPUT: number of read bytes\r
+*/\r
+long fr_read ( void * bbuf, long size, long size_st, F_FILE * filehandle )\r
+{\r
+  long  rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_read( bbuf, size, size_st, filehandle );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = 0;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+\r
+/*\r
+** fr_write\r
+**\r
+** INPUT : bbuf - buffer to write from\r
+**         size - number of unique\r
+**         size_st - size of unique\r
+**         *filehandle - pointer to the file descriptor\r
+** RETURN: number of written bytes\r
+*/\r
+long fr_write ( const void * bbuf, long size, long size_st, F_FILE * filehandle )\r
+{\r
+  long  rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_write( bbuf, size, size_st, filehandle );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = 0;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+/*\r
+** fr_seek\r
+**\r
+** Seek in a file.\r
+**\r
+** INPUT : *filehandle - pointer to a file descriptor\r
+**         offset - offset\r
+**         whence - F_SEEK_SET: position = offset\r
+**                  F_SEEK_CUR: position = position + offset\r
+**                  F_SEEK_END: position = end of file (offset=0)\r
+** RETURN: F_NOERR on succes, other if error.\r
+*/\r
+unsigned char fr_seek ( F_FILE * filehandle, long offset, unsigned char whence )\r
+{\r
+  unsigned char  rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_seek( filehandle, offset, whence );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = F_ERR_OS;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+/*\r
+** fr_tell\r
+**\r
+** get current position in the file\r
+**\r
+** INPUT : *filehandle - pointer to a file descriptor\r
+** RETURN: -1 on error or current position.\r
+*/\r
+long fr_tell ( F_FILE * filehandle )\r
+{\r
+  long  rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_tell( filehandle );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = -1;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+/*\r
+** fr_getc\r
+**\r
+** read one byte from a file\r
+**\r
+** INPUT : *filehandle - pointer to a file descriptor\r
+** RETURN: -1 if error, otherwise the read character.\r
+*/\r
+int fr_getc ( F_FILE * filehandle )\r
+{\r
+  int  rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_getc( filehandle );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = -1;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+/*\r
+** fr_putc\r
+**\r
+** write one byte to a file\r
+**\r
+** INPUT : ch - character to write\r
+**         *filehandle - pointer to a file handler\r
+** RETURN: ch on success, -1 on error\r
+*/\r
+int fr_putc ( int ch, F_FILE * filehandle )\r
+{\r
+  int  rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_putc( ch, filehandle );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = -1;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+/*\r
+** fr_rewind\r
+**\r
+** set current position in the file to the beginning\r
+**\r
+** INPUT : *filehandle - pointer to a file descriptor\r
+** RETURN: F_NOERR on succes, other if error.\r
+*/\r
+unsigned char fr_rewind ( F_FILE * filehandle )\r
+{\r
+  unsigned char rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_rewind( filehandle );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = F_ERR_OS;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+/*\r
+** fr_eof\r
+**\r
+** check if current position is at the end of the file.\r
+**\r
+** INPUT : *filehandle - pointer to a file descriptor\r
+** RETURN: F_ERR_EOF - at the end of the file\r
+**         F_NOERR - no error, end of the file not reached\r
+**         other - on error\r
+*/\r
+unsigned char fr_eof ( F_FILE * filehandle )\r
+{\r
+  unsigned char  rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_eof( filehandle );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = F_ERR_OS;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+/*\r
+** Format the device\r
+*/\r
+unsigned char fr_hardformat ( unsigned char fattype )\r
+{\r
+  unsigned char  rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_hardformat( fattype );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = F_ERR_OS;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+/*\r
+** fr_get_serial\r
+**\r
+** Get serial number\r
+**\r
+** OUTPUT: serial - where to write the serial number\r
+** RETURN: error code\r
+*/\r
+unsigned char fr_getserial ( unsigned long * serial )\r
+{\r
+  unsigned char  rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_getserial( serial );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = F_ERR_OS;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+\r
+/*\r
+** fr_delete\r
+**\r
+** Delete a file. Removes the chain that belongs to the file and inserts a new descriptor\r
+** to the directory with first_cluster set to 0.\r
+**\r
+** INPUT : filename - name of the file to delete\r
+** RETURN: F_NOERR on success, other if error.\r
+*/\r
+unsigned char fr_delete ( const char * filename )\r
+{\r
+  unsigned char  rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_delete( filename );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = F_ERR_OS;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+/*\r
+** fr_truncate\r
+**\r
+** Open a file and set end of file\r
+**\r
+** INPUT:      filename - name of the file\r
+**             filesize - required new size\r
+** RETURN:     NULL on error, otherwise file pointer\r
+*/\r
+F_FILE * fr_truncate ( const char * filename, long filesize )\r
+{\r
+  F_FILE * f;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    f = fn_truncate( filename, filesize );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    f = NULL;\r
+  }\r
+\r
+  return f;\r
+}\r
+\r
+\r
+/*\r
+** fr_getfreespace\r
+**\r
+** Get free space on the volume\r
+**\r
+** OUTPUT: *sp - pre-defined F_SPACE structure, where information will be stored\r
+** RETURN: F_NOERR - on success\r
+**         F_ERR_NOTFORMATTED - if volume is not formatted\r
+*/\r
+unsigned char fr_getfreespace ( F_SPACE * sp )\r
+{\r
+  unsigned char  rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_getfreespace( sp );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = F_ERR_OS;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+\r
+/*\r
+** fr_chdir\r
+**\r
+** Change to a directory\r
+**\r
+** INPUT:  path - path to the dircetory\r
+** RETURN: 0 - on success, other if error\r
+*/\r
+unsigned char fr_chdir ( const char * path )\r
+{\r
+  unsigned char  rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_chdir( path );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = F_ERR_OS;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+\r
+/*\r
+** fr_mkdir\r
+**\r
+** Create a directory\r
+**\r
+** INPUT:  path - new directory path\r
+** RETURN: 0 - on success, other if error\r
+*/\r
+unsigned char fr_mkdir ( const char * path )\r
+{\r
+  unsigned char  rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_mkdir( path );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = F_ERR_OS;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+\r
+/*\r
+** fr_rmdir\r
+**\r
+** Removes a directory\r
+**\r
+** INPUT:  path - path to remove\r
+** RETURN: 0 - on success, other if error\r
+*/\r
+unsigned char fr_rmdir ( const char * path )\r
+{\r
+  unsigned char  rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_rmdir( path );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = F_ERR_OS;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+\r
+/*\r
+** fr_getcwd\r
+**\r
+** Get current working directory\r
+**\r
+** INPUT:  maxlen - maximum length allowed\r
+** OUTPUT: path - current working directory\r
+** RETURN: 0 - on success, other if error\r
+*/\r
+unsigned char fr_getcwd ( char * path, unsigned char maxlen, char root )\r
+{\r
+  unsigned char  rc;\r
+\r
+  if( xSemaphoreTake( fs_lock_semaphore, F_MAX_LOCK_WAIT_TICKS ) == pdPASS )\r
+  {\r
+    rc = fn_getcwd( path, maxlen, root );\r
+    xSemaphoreGive( fs_lock_semaphore );\r
+  }\r
+  else\r
+  {\r
+    rc = F_ERR_OS;\r
+  }\r
+\r
+  return rc;\r
+}\r
+\r
+\r
+/*\r
+** fr_init\r
+**\r
+** Initialize FAT_SL OS module\r
+**\r
+** RETURN: F_NO_ERROR or F_ERR_OS\r
+*/\r
+unsigned char fr_init ( void )\r
+{\r
+  return F_NO_ERROR;\r
+}\r
+\r
+#endif /* F_FS_THREAD_AWARE */\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/f_lock.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/f_lock.h
new file mode 100644 (file)
index 0000000..c050559
--- /dev/null
@@ -0,0 +1,59 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef _F_RTOS_H\r
+#define _F_RTOS_H\r
+\r
+#include "../../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+\r
+#ifdef __cplusplus\r
+extern "C" {\r
+#endif\r
+\r
+unsigned char fr_init ( void );\r
+\r
+#ifdef __cplusplus\r
+}\r
+#endif\r
+\r
+#endif /* ifndef _F_RTOS_H */\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/fat.c b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/fat.c
new file mode 100644 (file)
index 0000000..771d1ff
--- /dev/null
@@ -0,0 +1,598 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+#include "../../api/fat_sl.h"\r
+\r
+#include "fat.h"\r
+#include "util.h"\r
+#include "volume.h"\r
+#include "drv.h"\r
+\r
+#include "../../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_writefatsector\r
+ *\r
+ * writing fat sector into volume, this function check if fat was modified\r
+ * and writes data\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+unsigned char _f_writefatsector ( void )\r
+{\r
+  unsigned char  a;\r
+\r
+  if ( gl_volume.modified )\r
+  {\r
+    unsigned long  fatsector = gl_volume.firstfat.sector + gl_volume.fatsector;\r
+\r
+    if ( gl_volume.fatsector >= gl_volume.firstfat.num )\r
+    {\r
+      return F_ERR_INVALIDSECTOR;\r
+    }\r
+\r
+    for ( a = 0 ; a < gl_volume.bootrecord.number_of_FATs ; a++ )\r
+    {\r
+      unsigned char  ret;\r
+      ret = _f_writeglsector( fatsector );\r
+      if ( ret )\r
+      {\r
+        return ret;\r
+      }\r
+\r
+      fatsector += gl_volume.firstfat.num;\r
+    }\r
+\r
+    gl_volume.modified = 0;\r
+  }\r
+\r
+  return F_NO_ERROR;\r
+} /* _f_writefatsector */\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_getfatsector\r
+ *\r
+ * read a fat sector from media\r
+ *\r
+ * INPUTS\r
+ *\r
+ * sector - which fat sector is needed, this sector number is zero based\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+unsigned char _f_getfatsector ( unsigned long sector )\r
+{\r
+  unsigned char  a;\r
+\r
+  if ( gl_volume.fatsector != sector )\r
+  {\r
+    unsigned long  fatsector;\r
+\r
+    gl_volume.fatsector = sector;\r
+\r
+    if ( gl_volume.fatsector >= gl_volume.firstfat.num )\r
+    {\r
+      return F_ERR_INVALIDSECTOR;\r
+    }\r
+\r
+    fatsector = gl_volume.firstfat.sector + gl_volume.fatsector;\r
+\r
+    for ( a = 0 ; a < gl_volume.bootrecord.number_of_FATs ; a++ )\r
+    {\r
+      if ( !_f_readglsector( fatsector ) )\r
+      {\r
+        return F_NO_ERROR;\r
+      }\r
+\r
+      fatsector += gl_volume.firstfat.num;\r
+    }\r
+\r
+    return F_ERR_READ;\r
+  }\r
+\r
+  return F_NO_ERROR;\r
+} /* _f_getfatsector */\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_setclustervalue\r
+ *\r
+ * set a cluster value in the FAT\r
+ *\r
+ * INPUTS\r
+ *\r
+ * cluster - which cluster's value need to be modified\r
+ * data - new value of the cluster\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+unsigned char _f_setclustervalue ( unsigned long cluster, unsigned long _tdata )\r
+{\r
+  unsigned char  ret;\r
+\r
+  switch ( gl_volume.mediatype )\r
+  {\r
+    case F_FAT16_MEDIA:\r
+    {\r
+      unsigned long   sector = cluster;\r
+      unsigned short  s_data = (unsigned short)( _tdata & 0xffff ); /*keep 16 bit only*/\r
+\r
+      sector /= ( F_SECTOR_SIZE / 2 );\r
+      cluster -= sector * ( F_SECTOR_SIZE / 2 );\r
+\r
+      ret = _f_getfatsector( sector );\r
+      if ( ret )\r
+      {\r
+        return ret;\r
+      }\r
+\r
+      if ( _f_getword( &gl_sector[cluster << 1] ) != s_data )\r
+      {\r
+        _f_setword( &gl_sector[cluster << 1], s_data );\r
+        gl_volume.modified = 1;\r
+      }\r
+    }\r
+    break;\r
+\r
+    case F_FAT12_MEDIA:\r
+    {\r
+      unsigned char   f12new[2];\r
+      unsigned long   sector = cluster;\r
+      unsigned short  pos;\r
+      unsigned short  s_data = (unsigned short)( _tdata & 0x0fff ); /*keep 12 bit only*/\r
+\r
+      if ( cluster & 1 )\r
+      {\r
+        s_data <<= 4;\r
+      }\r
+\r
+      _f_setword( f12new, s_data ); /*create new data*/\r
+\r
+      sector += sector / 2;       /*1.5 bytes*/\r
+      pos = (unsigned short)( sector % F_SECTOR_SIZE );\r
+      sector /= F_SECTOR_SIZE;\r
+\r
+      ret = _f_getfatsector( sector );\r
+      if ( ret )\r
+      {\r
+        return ret;\r
+      }\r
+\r
+      if ( cluster & 1 )\r
+      {\r
+        f12new[0] |= gl_sector[pos] & 0x0f;\r
+      }\r
+\r
+      if ( gl_sector[pos] != f12new[0] )\r
+      {\r
+        gl_sector[pos] = f12new[0];\r
+        gl_volume.modified = 1;\r
+      }\r
+\r
+      pos++;\r
+      if ( pos >= 512 )\r
+      {\r
+        ret = _f_getfatsector( sector + 1 );\r
+        if ( ret )\r
+        {\r
+          return ret;\r
+        }\r
+\r
+        pos = 0;\r
+      }\r
+\r
+      if ( !( cluster & 1 ) )\r
+      {\r
+        f12new[1] |= gl_sector[pos] & 0xf0;\r
+      }\r
+\r
+      if ( gl_sector[pos] != f12new[1] )\r
+      {\r
+        gl_sector[pos] = f12new[1];\r
+        gl_volume.modified = 1;\r
+      }\r
+    }\r
+    break;\r
+\r
+    case F_FAT32_MEDIA:\r
+    {\r
+      unsigned long  sector = cluster;\r
+      unsigned long  oldv;\r
+\r
+      sector /= ( F_SECTOR_SIZE / 4 );\r
+      cluster -= sector * ( F_SECTOR_SIZE / 4 );\r
+\r
+      ret = _f_getfatsector( sector );\r
+      if ( ret )\r
+      {\r
+        return ret;\r
+      }\r
+\r
+      oldv = _f_getlong( &gl_sector[cluster << 2] );\r
+\r
+      _tdata &= 0x0fffffff;\r
+      _tdata |= oldv & 0xf0000000; /*keep 4 top bits*/\r
+\r
+      if ( _tdata != oldv )\r
+      {\r
+        _f_setlong( &gl_sector[cluster << 2], _tdata );\r
+        gl_volume.modified = 1;\r
+      }\r
+    }\r
+    break;\r
+\r
+    default:\r
+      return F_ERR_INVALIDMEDIA;\r
+  } /* switch */\r
+\r
+  return F_NO_ERROR;\r
+} /* _f_setclustervalue */\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_getclustervalue\r
+ *\r
+ * get a cluster value from FAT\r
+ *\r
+ * INPUTS\r
+ *\r
+ * cluster - which cluster value is requested\r
+ * pvalue - where to store data\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+unsigned char _f_getclustervalue ( unsigned long cluster, unsigned long * pvalue )\r
+{\r
+  unsigned long  val;\r
+  unsigned char  ret;\r
+\r
+  switch ( gl_volume.mediatype )\r
+  {\r
+    case F_FAT16_MEDIA:\r
+    {\r
+      unsigned long  sector = cluster;\r
+      sector /= ( F_SECTOR_SIZE / 2 );\r
+      cluster -= sector * ( F_SECTOR_SIZE / 2 );\r
+\r
+      ret = _f_getfatsector( sector );\r
+      if ( ret )\r
+      {\r
+        return ret;\r
+      }\r
+\r
+      val = _f_getword( &gl_sector[cluster << 1] );\r
+      if ( val >= ( F_CLUSTER_RESERVED & 0xffff ) )\r
+      {\r
+        val |= 0x0ffff000;                                       /*extends it*/\r
+      }\r
+\r
+      if ( pvalue )\r
+      {\r
+        *pvalue = val;\r
+      }\r
+    }\r
+    break;\r
+\r
+    case F_FAT12_MEDIA:\r
+    {\r
+      unsigned char   dataf12[2];\r
+      unsigned long   sector = cluster;\r
+      unsigned short  pos;\r
+\r
+      sector += sector / 2;       /*1.5 bytes*/\r
+      pos = (unsigned short)( sector % F_SECTOR_SIZE );\r
+      sector /= F_SECTOR_SIZE;\r
+\r
+      ret = _f_getfatsector( sector );\r
+      if ( ret )\r
+      {\r
+        return ret;\r
+      }\r
+\r
+      dataf12[0] = gl_sector[pos++];\r
+\r
+      if ( pos >= 512 )\r
+      {\r
+        ret = _f_getfatsector( sector + 1 );\r
+        if ( ret )\r
+        {\r
+          return ret;\r
+        }\r
+\r
+        pos = 0;\r
+      }\r
+\r
+      dataf12[1] = gl_sector[pos];\r
+\r
+      val = _f_getword( dataf12 );\r
+\r
+      if ( cluster & 1 )\r
+      {\r
+        val = val >> 4;\r
+      }\r
+      else\r
+      {\r
+        val = val & 0xfff;\r
+      }\r
+\r
+      if ( val >= ( F_CLUSTER_RESERVED & 0xfff ) )\r
+      {\r
+        val |= 0x0ffff000;                                      /*extends it*/\r
+      }\r
+\r
+      if ( pvalue )\r
+      {\r
+        *pvalue = val;\r
+      }\r
+    }\r
+    break;\r
+\r
+    case F_FAT32_MEDIA:\r
+    {\r
+      unsigned long  sector = cluster;\r
+      sector /= ( F_SECTOR_SIZE / 4 );\r
+      cluster -= sector * ( F_SECTOR_SIZE / 4 );\r
+\r
+      ret = _f_getfatsector( sector );\r
+      if ( ret )\r
+      {\r
+        return ret;\r
+      }\r
+\r
+      if ( pvalue )\r
+      {\r
+        *pvalue = _f_getlong( &gl_sector[cluster << 2] ) & 0x0fffffff;       /*28bit*/\r
+      }\r
+    }\r
+    break;\r
+\r
+    default:\r
+      return F_ERR_INVALIDMEDIA;\r
+  } /* switch */\r
+\r
+  return F_NO_ERROR;\r
+} /* _f_getclustervalue */\r
+\r
+\r
+\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_clustertopos\r
+ *\r
+ * convert a cluster position into physical sector position\r
+ *\r
+ * INPUTS\r
+ *\r
+ * cluster - original cluster position\r
+ * pos - position structure to fills the position\r
+ *\r
+ ***************************************************************************/\r
+void _f_clustertopos ( unsigned long cluster, F_POS * pos )\r
+{\r
+  pos->cluster = cluster;\r
+\r
+  if ( !cluster )\r
+  {\r
+    pos->sector = gl_volume.root.sector;\r
+    pos->sectorend = pos->sector + gl_volume.root.num;\r
+  }\r
+  else\r
+  {\r
+    unsigned long  sectorcou = gl_volume.bootrecord.sector_per_cluster;\r
+    pos->sector = ( pos->cluster - 2 ) * sectorcou + gl_volume._tdata.sector;\r
+    pos->sectorend = pos->sector + sectorcou;\r
+  }\r
+\r
+  if ( cluster >= F_CLUSTER_RESERVED )\r
+  {\r
+    pos->sectorend = 0;\r
+  }\r
+\r
+  pos->pos = 0;\r
+} /* _f_clustertopos */\r
+\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_getcurrsector\r
+ *\r
+ * read current sector according in file structure\r
+ *\r
+ * INPUTS\r
+ * f - internal file pointer\r
+ *\r
+ * RETURNS\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+unsigned char _f_getcurrsector ( void )\r
+{\r
+  unsigned char  ret;\r
+  unsigned long  cluster;\r
+\r
+  if ( gl_file.pos.sector == gl_file.pos.sectorend )\r
+  {\r
+    gl_volume.fatsector = (unsigned long)-1;\r
+    ret = _f_getclustervalue( gl_file.pos.cluster, &cluster );\r
+    if ( ret )\r
+    {\r
+      return ret;\r
+    }\r
+\r
+    if ( cluster >= F_CLUSTER_RESERVED )\r
+    {\r
+      return F_ERR_EOF;\r
+    }\r
+\r
+    gl_file.prevcluster = gl_file.pos.cluster;\r
+    _f_clustertopos( cluster, &gl_file.pos );\r
+  }\r
+\r
+  return _f_readglsector( gl_file.pos.sector );\r
+} /* _f_getcurrsector */\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_alloccluster\r
+ *\r
+ * allocate cluster from FAT\r
+ *\r
+ * INPUTS\r
+ * pcluster - where to store the allocated cluster number\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+\r
+unsigned char _f_alloccluster ( unsigned long * pcluster )\r
+{\r
+  unsigned long  maxcluster = gl_volume.maxcluster;\r
+  unsigned long  cou;\r
+  unsigned long  cluster = gl_volume.lastalloccluster;\r
+  unsigned long  value;\r
+  unsigned char  ret;\r
+\r
+  for ( cou = 0 ; cou < maxcluster ; cou++ )\r
+  {\r
+    if ( cluster >= maxcluster )\r
+    {\r
+      cluster = 0;\r
+    }\r
+\r
+    ret = _f_getclustervalue( cluster, &value );\r
+    if ( ret )\r
+    {\r
+      return ret;\r
+    }\r
+\r
+    if ( !value )\r
+    {\r
+      gl_volume.lastalloccluster = cluster + 1;   /*set next one*/\r
+      *pcluster = cluster;\r
+\r
+      return F_NO_ERROR;\r
+    }\r
+\r
+    cluster++;\r
+  }\r
+\r
+  return F_ERR_NOMOREENTRY;\r
+} /* _f_alloccluster */\r
+\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_removechain\r
+ *\r
+ * remove cluster chain from fat\r
+ *\r
+ * INPUTS\r
+ * cluster - first cluster in the cluster chain\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+\r
+unsigned char _f_removechain ( unsigned long cluster )\r
+{\r
+  gl_volume.fatsector = (unsigned long)-1;\r
+\r
+  if ( cluster < gl_volume.lastalloccluster ) /*this could be the begining of alloc*/\r
+  {\r
+    gl_volume.lastalloccluster = cluster;\r
+  }\r
+\r
+  while ( cluster < F_CLUSTER_RESERVED && cluster >= 2 )\r
+  {\r
+    unsigned long  nextcluster;\r
+\r
+    unsigned char  ret = _f_getclustervalue( cluster, &nextcluster );\r
+    if ( ret )\r
+    {\r
+      return ret;\r
+    }\r
+\r
+    ret = _f_setclustervalue( cluster, F_CLUSTER_FREE );\r
+    if ( ret )\r
+    {\r
+      return ret;\r
+    }\r
+\r
+    cluster = nextcluster;\r
+  }\r
+\r
+  return _f_writefatsector();\r
+} /* _f_removechain */\r
+\r
+\r
+\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/fat.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/fat.h
new file mode 100644 (file)
index 0000000..bb8c727
--- /dev/null
@@ -0,0 +1,65 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef __FAT_H\r
+#define __FAT_H\r
+\r
+#include "../../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+#ifdef __cplusplus\r
+extern "C" {\r
+#endif\r
+\r
+unsigned char _f_getfatsector ( unsigned long );\r
+unsigned char _f_getclustervalue ( unsigned long, unsigned long * );\r
+void _f_clustertopos ( unsigned long, F_POS * );\r
+unsigned char _f_getcurrsector ( void );\r
+\r
+unsigned char _f_writefatsector ( void );\r
+unsigned char _f_setclustervalue ( unsigned long, unsigned long );\r
+unsigned char _f_alloccluster ( unsigned long * );\r
+unsigned char _f_removechain ( unsigned long );\r
+\r
+#ifdef __cplusplus\r
+}\r
+#endif\r
+\r
+#endif /* ifndef __FAT_H */\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/file.c b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/file.c
new file mode 100644 (file)
index 0000000..ae08990
--- /dev/null
@@ -0,0 +1,1492 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#include "../../api/fat_sl.h"\r
+#include "../../psp/include/psp_string.h"\r
+\r
+#include "util.h"\r
+#include "volume.h"\r
+#include "drv.h"\r
+#include "fat.h"\r
+#include "dir.h"\r
+#include "file.h"\r
+\r
+#include "../../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+static unsigned char _f_emptywritebuffer ( void );\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_filelength\r
+ *\r
+ * Get a file length\r
+ *\r
+ * INPUTS\r
+ *\r
+ * filename - file whose length is needed\r
+ *\r
+ * RETURNS\r
+ *\r
+ * length of the file\r
+ *\r
+ ***************************************************************************/\r
+\r
+long fn_filelength ( const char * filename )\r
+{\r
+  F_POS        pos;\r
+  F_DIRENTRY * de;\r
+  F_NAME       fsname;\r
+\r
+  if ( _f_setfsname( filename, &fsname ) )\r
+  {\r
+    return 0;                                     /*invalid name*/\r
+  }\r
+\r
+  if ( _f_checknamewc( fsname.filename, fsname.fileext ) )\r
+  {\r
+    return 0;                                                    /*invalid name*/\r
+  }\r
+\r
+  if ( _f_getvolume() )\r
+  {\r
+    return 0;                     /*can't get the size*/\r
+  }\r
+\r
+  if ( !_f_findpath( &fsname, &pos ) )\r
+  {\r
+    return 0;\r
+  }\r
+\r
+  if ( !_f_findfilewc( fsname.filename, fsname.fileext, &pos, &de, 0 ) )\r
+  {\r
+    return 0;\r
+  }\r
+\r
+  if ( de->attr & F_ATTR_DIR )\r
+  {\r
+    return 0;                                           /*directory*/\r
+  }\r
+\r
+  return (long)_f_getlong( &de->filesize );\r
+} /* fn_filelength */\r
+\r
+\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_emptywritebuffer\r
+ *\r
+ * empty write buffer if it contains unwritten data\r
+ *\r
+ * RETURNS\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+\r
+\r
+static unsigned char _f_emptywritebuffer ( void )\r
+{\r
+  unsigned char  ret;\r
+\r
+  ret = _f_writeglsector( gl_file.pos.sector );\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  gl_file.modified = 0;\r
+\r
+  gl_file.pos.sector++;\r
+\r
+  if ( gl_file.pos.sector >= gl_file.pos.sectorend )\r
+  {\r
+    unsigned long  value;\r
+\r
+    gl_volume.fatsector = (unsigned long)-1;\r
+    ret = _f_getclustervalue( gl_file.pos.cluster, &value );\r
+    if ( ret )\r
+    {\r
+      return ret;\r
+    }\r
+\r
+    if ( ( value >= 2 ) && ( value < F_CLUSTER_RESERVED ) ) /*we are in chain*/\r
+    {\r
+      gl_file.prevcluster = gl_file.pos.cluster;\r
+      _f_clustertopos( value, &gl_file.pos );    /*go to next cluster*/\r
+    }\r
+    else\r
+    {\r
+      unsigned long  nextcluster;\r
+\r
+      ret = _f_alloccluster( &nextcluster );\r
+      if ( ret )\r
+      {\r
+        return ret;\r
+      }\r
+\r
+      ret = _f_setclustervalue( nextcluster, F_CLUSTER_LAST );\r
+      if ( ret )\r
+      {\r
+        return ret;\r
+      }\r
+\r
+      ret = _f_setclustervalue( gl_file.pos.cluster, nextcluster );\r
+      if ( ret )\r
+      {\r
+        return ret;\r
+      }\r
+\r
+      gl_file.prevcluster = gl_file.pos.cluster;\r
+\r
+      _f_clustertopos( nextcluster, &gl_file.pos );\r
+\r
+      return _f_writefatsector();\r
+    }\r
+  }\r
+\r
+\r
+  return F_NO_ERROR;\r
+} /* _f_emptywritebuffer */\r
+\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_extend\r
+ *\r
+ * Extend file to a certain size\r
+ *\r
+ ***************************************************************************/\r
+static unsigned char _f_extend ( long size )\r
+{\r
+  unsigned long  _size;\r
+  unsigned char  rc;\r
+\r
+  size -= gl_file.filesize;\r
+  _size = (unsigned long)size;\r
+\r
+  rc = _f_getcurrsector();\r
+  if ( rc )\r
+  {\r
+    return rc;\r
+  }\r
+\r
+  psp_memset( gl_sector + gl_file.relpos, 0, ( F_SECTOR_SIZE - gl_file.relpos ) );\r
+\r
+  if ( gl_file.relpos + _size > F_SECTOR_SIZE )\r
+  {\r
+    _size -= ( F_SECTOR_SIZE - gl_file.relpos );\r
+    while ( _size )\r
+    {\r
+      if ( _f_emptywritebuffer() )\r
+      {\r
+        return F_ERR_WRITE;\r
+      }\r
+\r
+      psp_memset( gl_sector, 0, F_SECTOR_SIZE );\r
+      _size -= ( _size > F_SECTOR_SIZE ? F_SECTOR_SIZE : _size );\r
+    }\r
+  }\r
+  else\r
+  {\r
+    _size += gl_file.relpos;\r
+  }\r
+\r
+  gl_file.modified = 1;\r
+  gl_file.filesize += size;\r
+  gl_file.abspos = gl_file.filesize & ( ~( F_SECTOR_SIZE - 1 ) );\r
+  gl_file.relpos = _size;\r
+\r
+  return F_NO_ERROR;\r
+} /* _f_extend */\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_fseek\r
+ *\r
+ * subfunction for f_seek it moves position into given offset and read\r
+ * the current sector\r
+ *\r
+ * INPUTS\r
+ * offset - position from start\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+static unsigned char _f_fseek ( long offset )\r
+{\r
+  unsigned long  cluster;\r
+  unsigned long  tmp;\r
+  unsigned char  ret = F_NO_ERROR;\r
+  long           remain;\r
+\r
+  if ( offset < 0 )\r
+  {\r
+    offset = 0;\r
+  }\r
+\r
+  if ( ( (unsigned long) offset <= gl_file.filesize )\r
+       && ( (unsigned long) offset >= gl_file.abspos )\r
+       && ( (unsigned long) offset < gl_file.abspos + F_SECTOR_SIZE ) )\r
+  {\r
+    gl_file.relpos = (unsigned short)( offset - gl_file.abspos );\r
+  }\r
+  else\r
+  {\r
+    if ( gl_file.modified )\r
+    {\r
+      ret = _f_writeglsector( (unsigned long)-1 );\r
+      if ( ret )\r
+      {\r
+        gl_file.mode = F_FILE_CLOSE; /*cant accessed any more*/\r
+        return ret;\r
+      }\r
+    }\r
+\r
+    if ( gl_file.startcluster )\r
+    {\r
+      gl_file.abspos = 0;\r
+      gl_file.relpos = 0;\r
+      gl_file.prevcluster = 0;\r
+      gl_file.pos.cluster = gl_file.startcluster;\r
+      remain = gl_file.filesize;\r
+\r
+      tmp = gl_volume.bootrecord.sector_per_cluster;\r
+      tmp *= F_SECTOR_SIZE;   /* set to cluster size */\r
+\r
+      /*calc cluster*/\r
+      gl_volume.fatsector = (unsigned long)-1;\r
+      while ( (unsigned long)offset >= tmp )\r
+      {\r
+        ret = _f_getclustervalue( gl_file.pos.cluster, &cluster );\r
+        if ( ret )\r
+        {\r
+          gl_file.mode = F_FILE_CLOSE;\r
+          return ret;\r
+        }\r
+\r
+        if ( (long) tmp >= remain )\r
+        {\r
+          break;\r
+        }\r
+\r
+        remain -= tmp;\r
+        offset -= tmp;\r
+        gl_file.abspos += tmp;\r
+        if ( cluster >= F_CLUSTER_RESERVED )\r
+        {\r
+          break;\r
+        }\r
+\r
+        gl_file.prevcluster = gl_file.pos.cluster;\r
+        gl_file.pos.cluster = cluster;\r
+      }\r
+\r
+      _f_clustertopos( gl_file.pos.cluster, &gl_file.pos );\r
+      if ( remain && offset )\r
+      {\r
+        while ( ( offset > (long) F_SECTOR_SIZE )\r
+               && ( remain > (long) F_SECTOR_SIZE ) )\r
+        {\r
+          gl_file.pos.sector++;\r
+          offset -= F_SECTOR_SIZE;\r
+          remain -= F_SECTOR_SIZE;\r
+          gl_file.abspos += F_SECTOR_SIZE;\r
+        }\r
+      }\r
+\r
+      if ( remain < offset )\r
+      {\r
+        gl_file.relpos = (unsigned short)remain;\r
+        ret = _f_extend( gl_file.filesize + offset - remain );\r
+      }\r
+      else\r
+      {\r
+        gl_file.relpos = (unsigned short)offset;\r
+      }\r
+    }\r
+  }\r
+\r
+  return ret;\r
+} /* _f_fseek */\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_open\r
+ *\r
+ * open a file for reading/writing/appending\r
+ *\r
+ * INPUTS\r
+ *\r
+ * filename - which file need to be opened\r
+ * mode - string how to open ("r"-read, "w"-write, "w+"-overwrite, "a"-append\r
+ *\r
+ * RETURNS\r
+ *\r
+ * F_FILE pointer if successfully\r
+ * 0 - if any error\r
+ *\r
+ ***************************************************************************/\r
+F_FILE * fn_open ( const char * filename, const char * mode )\r
+{\r
+  F_DIRENTRY    * de;\r
+  F_NAME          fsname;\r
+  unsigned short  date;\r
+  unsigned short  time;\r
+  unsigned char   m_mode = F_FILE_CLOSE;\r
+\r
+  if ( mode[1] == 0 )\r
+  {\r
+    if ( mode[0] == 'r' )\r
+    {\r
+      m_mode = F_FILE_RD;\r
+    }\r
+\r
+    if ( mode[0] == 'w' )\r
+    {\r
+      m_mode = F_FILE_WR;\r
+    }\r
+\r
+    if ( mode[0] == 'a' )\r
+    {\r
+      m_mode = F_FILE_A;\r
+    }\r
+  }\r
+\r
+  if ( ( mode[1] == '+' ) && ( mode[2] == 0 ) )\r
+  {\r
+    if ( mode[0] == 'r' )\r
+    {\r
+      m_mode = F_FILE_RDP;\r
+    }\r
+\r
+    if ( mode[0] == 'w' )\r
+    {\r
+      m_mode = F_FILE_WRP;\r
+    }\r
+\r
+    if ( mode[0] == 'a' )\r
+    {\r
+      m_mode = F_FILE_AP;\r
+    }\r
+\r
+  }\r
+\r
+  if ( m_mode == F_FILE_CLOSE )\r
+  {\r
+    return 0;                                       /*invalid mode*/\r
+  }\r
+\r
+  if ( _f_setfsname( filename, &fsname ) )\r
+  {\r
+    return 0;                                     /*invalid name*/\r
+  }\r
+\r
+  if ( _f_checknamewc( fsname.filename, fsname.fileext ) )\r
+  {\r
+    return 0;                                                    /*invalid name*/\r
+  }\r
+\r
+  if ( fsname.filename[0] == '.' )\r
+  {\r
+    return 0;\r
+  }\r
+\r
+  if ( _f_getvolume() )\r
+  {\r
+    return 0;                     /*cant open any*/\r
+  }\r
+\r
+  if ( gl_file.mode != F_FILE_CLOSE )\r
+  {\r
+    return 0;\r
+  }\r
+\r
+  psp_memset( &gl_file, 0, 21 );\r
+\r
+  if ( !_f_findpath( &fsname, &gl_file.dirpos ) )\r
+  {\r
+    return 0;\r
+  }\r
+\r
+  switch ( m_mode )\r
+  {\r
+    case F_FILE_RDP:   /*r*/\r
+    case F_FILE_RD:   /*r*/\r
+      if ( !_f_findfilewc( fsname.filename, fsname.fileext, &gl_file.dirpos, &de, 0 ) )\r
+      {\r
+        return 0;\r
+      }\r
+\r
+      if ( de->attr & F_ATTR_DIR )\r
+      {\r
+        return 0;                                      /*directory*/\r
+      }\r
+\r
+      gl_file.startcluster = _f_getdecluster( de );\r
+\r
+      if ( gl_file.startcluster )\r
+      {\r
+        _f_clustertopos( gl_file.startcluster, &gl_file.pos );\r
+        gl_file.filesize = _f_getlong( &de->filesize );\r
+        gl_file.abspos = (unsigned long) (-1 * (long) F_SECTOR_SIZE);\r
+        if ( _f_fseek( 0 ) )\r
+        {\r
+          return 0;\r
+        }\r
+      }\r
+\r
+#if F_FILE_CHANGED_EVENT\r
+      if ( m_mode == F_FILE_RDP )\r
+      {\r
+        _f_createfullname( gl_file.filename, sizeof( gl_file.filename ), fsname.path, fsname.filename, fsname.fileext );\r
+      }\r
+\r
+#endif\r
+\r
+      break;\r
+\r
+    case F_FILE_AP:\r
+    case F_FILE_A: /*a*/\r
+      psp_memcpy( &( gl_file.pos ), &( gl_file.dirpos ), sizeof( F_POS ) );\r
+      if ( _f_findfilewc( fsname.filename, fsname.fileext, &gl_file.dirpos, &de, 0 ) )\r
+      {\r
+        if ( de->attr & ( F_ATTR_DIR | F_ATTR_READONLY ) )\r
+        {\r
+          return 0;\r
+        }\r
+\r
+        gl_file.startcluster = _f_getdecluster( de );\r
+        gl_file.filesize = _f_getlong( &de->filesize );\r
+\r
+        if ( gl_file.startcluster )\r
+        {\r
+          _f_clustertopos( gl_file.startcluster, &gl_file.pos );\r
+          gl_file.abspos = (unsigned long) (-1 * (long) F_SECTOR_SIZE);   /*forcing seek to read 1st sector! abspos=0;*/\r
+          if ( _f_fseek( (long)gl_file.filesize ) )\r
+          {\r
+            gl_file.mode = F_FILE_CLOSE;\r
+            return 0;\r
+          }\r
+        }\r
+      }\r
+      else\r
+      {\r
+        psp_memcpy( &( gl_file.dirpos ), &( gl_file.pos ), sizeof( F_POS ) );\r
+        _f_clustertopos( gl_file.dirpos.cluster, &gl_file.pos );\r
+\r
+        if ( _f_addentry( &fsname, &gl_file.dirpos, &de ) )\r
+        {\r
+          return 0;                                                  /*couldnt be added*/\r
+        }\r
+\r
+        de->attr |= F_ATTR_ARC;         /*set as archiv*/\r
+        if ( _f_writeglsector( (unsigned long)-1 ) )\r
+        {\r
+          return 0;\r
+        }\r
+      }\r
+\r
+ #if F_FILE_CHANGED_EVENT\r
+      _f_createfullname( gl_file.filename, sizeof( gl_file.filename ), fsname.path, fsname.filename, fsname.fileext );\r
+ #endif\r
+      break;\r
+\r
+\r
+    case F_FILE_WR:  /*w*/\r
+    case F_FILE_WRP: /*w+*/\r
+      _f_clustertopos( gl_file.dirpos.cluster, &gl_file.pos );\r
+      if ( _f_findfilewc( fsname.filename, fsname.fileext, &gl_file.pos, &de, 0 ) )\r
+      {\r
+        unsigned long  cluster = _f_getdecluster( de );    /*exist*/\r
+\r
+        if ( de->attr & ( F_ATTR_DIR | F_ATTR_READONLY ) )\r
+        {\r
+          return 0;\r
+        }\r
+\r
+        psp_memcpy( &( gl_file.dirpos ), &( gl_file.pos ), sizeof( F_POS ) );\r
+\r
+        _f_setlong( de->filesize, 0 );  /*reset size;*/\r
+        de->attr |= F_ATTR_ARC;         /*set as archiv*/\r
+        _f_setword( de->clusterlo, 0 ); /*no points anywhere*/\r
+        _f_setword( de->clusterhi, 0 );\r
+\r
+        if ( gl_volume.mediatype == F_FAT32_MEDIA )\r
+        {\r
+          f_igettimedate( &time, &date );\r
+          _f_setword( &de->crtdate, date );        /*if there is realtime clock then creation date could be set from*/\r
+          _f_setword( &de->crttime, time );        /*if there is realtime clock then creation time could be set from*/\r
+          _f_setword( &de->lastaccessdate, date ); /*if there is realtime clock then creation date could be set from*/\r
+        }\r
+\r
+        if ( _f_writeglsector( (unsigned long)-1 ) )\r
+        {\r
+          return 0;\r
+        }\r
+\r
+        if ( _f_removechain( cluster ) )\r
+        {\r
+          return 0;                                /*remove */\r
+        }\r
+      }\r
+      else\r
+      {\r
+        if ( _f_addentry( &fsname, &gl_file.dirpos, &de ) )\r
+        {\r
+          return 0;                                                  /*couldnt be added*/\r
+        }\r
+\r
+        psp_memset( &gl_file, 0, 21 );\r
+        de->attr |= F_ATTR_ARC;         /*set as archiv*/\r
+        if ( _f_writeglsector( (unsigned long)-1 ) )\r
+        {\r
+          return 0;\r
+        }\r
+      }\r
+\r
+ #if F_FILE_CHANGED_EVENT\r
+      _f_createfullname( gl_file.filename, sizeof( gl_file.filename ), fsname.path, fsname.filename, fsname.fileext );\r
+ #endif\r
+\r
+      break;\r
+\r
+    default:\r
+      return 0;        /*invalid mode*/\r
+  } /* switch */\r
+\r
+  if ( ( m_mode != F_FILE_RD ) && ( gl_file.startcluster == 0 ) )\r
+  {\r
+    gl_volume.fatsector = (unsigned long)-1;\r
+    if ( _f_alloccluster( &( gl_file.startcluster ) ) )\r
+    {\r
+      return 0;\r
+    }\r
+\r
+    _f_clustertopos( gl_file.startcluster, &gl_file.pos );\r
+    if ( _f_setclustervalue( gl_file.startcluster, F_CLUSTER_LAST ) )\r
+    {\r
+      return 0;\r
+    }\r
+\r
+    if ( _f_writefatsector() )\r
+    {\r
+      return 0;\r
+    }\r
+  }\r
+\r
+\r
+  gl_file.mode = m_mode; /* lock it */\r
+  return (F_FILE *)1;\r
+} /* fn_open */\r
+\r
+\r
+/****************************************************************************\r
+ * _f_updatefileentry\r
+ * Updated a file directory entry or removes the entry\r
+ * and the fat chain belonging to it.\r
+ ***************************************************************************/\r
+static unsigned char _f_updatefileentry ( int remove )\r
+{\r
+  F_DIRENTRY    * de;\r
+  unsigned short  date;\r
+  unsigned short  time;\r
+\r
+  de = (F_DIRENTRY *)( gl_sector + sizeof( F_DIRENTRY ) * gl_file.dirpos.pos );\r
+  if ( _f_readglsector( gl_file.dirpos.sector ) || remove )\r
+  {\r
+    _f_setdecluster( de, 0 );\r
+    _f_setlong( &de->filesize, 0 );\r
+    (void)_f_writeglsector( (unsigned long)-1 );\r
+    (void)_f_removechain( gl_file.startcluster );\r
+    return F_ERR_WRITE;\r
+  }\r
+\r
+  _f_setdecluster( de, gl_file.startcluster );\r
+  _f_setlong( &de->filesize, gl_file.filesize );\r
+  f_igettimedate( &time, &date );\r
+  _f_setword( &de->cdate, date );  /*if there is realtime clock then creation date could be set from*/\r
+  _f_setword( &de->ctime, time );  /*if there is realtime clock then creation time could be set from*/\r
+  if ( gl_volume.mediatype == F_FAT32_MEDIA )\r
+  {\r
+    _f_setword( &de->lastaccessdate, date );  /*if there is realtime clock then creation date could be set from*/\r
+  }\r
+\r
+  return _f_writeglsector( (unsigned long)-1 );\r
+} /* _f_updatefileentry */\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_close\r
+ *\r
+ * close a previously opened file\r
+ *\r
+ * INPUTS\r
+ *\r
+ * filehandle - which file needs to be closed\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+unsigned char fn_close ( F_FILE * f )\r
+{\r
+  unsigned char  ret;\r
+\r
+#if F_FILE_CHANGED_EVENT\r
+  unsigned char  mode;\r
+#endif\r
+\r
+  if ( !f )\r
+  {\r
+    return F_ERR_NOTOPEN;\r
+  }\r
+\r
+  ret = _f_getvolume();\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  if ( gl_file.mode == F_FILE_CLOSE )\r
+  {\r
+    return F_ERR_NOTOPEN;\r
+  }\r
+\r
+  else if ( gl_file.mode == F_FILE_RD )\r
+  {\r
+    gl_file.mode = F_FILE_CLOSE;\r
+    return F_NO_ERROR;\r
+  }\r
+  else\r
+  {\r
+ #if F_FILE_CHANGED_EVENT\r
+    mode = f->mode;\r
+ #endif\r
+    gl_file.mode = F_FILE_CLOSE;\r
+\r
+    if ( gl_file.modified )\r
+    {\r
+      if ( _f_writeglsector( (unsigned long)-1 ) )\r
+      {\r
+        (void)_f_updatefileentry( 1 );\r
+        return F_ERR_WRITE;\r
+      }\r
+    }\r
+\r
+    ret = _f_updatefileentry( 0 );\r
+\r
+ #if F_FILE_CHANGED_EVENT\r
+    if ( f_filechangedevent && !ret )\r
+    {\r
+      ST_FILE_CHANGED  fc;\r
+      if ( ( mode == F_FILE_WR )  || ( mode == F_FILE_WRP ) )\r
+      {\r
+        fc.action = FACTION_ADDED;\r
+        fc.flags  = FFLAGS_FILE_NAME;\r
+      }\r
+      else if ( ( mode == F_FILE_A )  || ( mode == F_FILE_RDP ) )\r
+      {\r
+        fc.action = FACTION_MODIFIED;\r
+        fc.flags  = FFLAGS_FILE_NAME | FFLAGS_SIZE;\r
+      }\r
+\r
+      strcpy( fc.filename, f->filename );\r
+      if ( f->filename[0] )\r
+      {\r
+        f_filechangedevent( &fc );\r
+      }\r
+\r
+      f->filename[0] = '\0';\r
+    }\r
+\r
+ #endif /* if F_FILE_CHANGED_EVENT */\r
+    return ret;\r
+  }\r
+} /* fn_close */\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_flush\r
+ *\r
+ * flush a previously opened file\r
+ *\r
+ * INPUTS\r
+ *\r
+ * filehandle - which file needs to be closed\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+unsigned char fn_flush ( F_FILE * f )\r
+{\r
+  unsigned char  ret;\r
+\r
+  if ( !f )\r
+  {\r
+    return F_ERR_NOTOPEN;\r
+  }\r
+\r
+  ret = _f_getvolume();\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  if ( gl_file.mode == F_FILE_CLOSE )\r
+  {\r
+    return F_ERR_NOTOPEN;\r
+  }\r
+  else if ( gl_file.mode != F_FILE_RD )\r
+  {\r
+    if ( gl_file.modified )\r
+    {\r
+      if ( _f_writeglsector( (unsigned long)-1 ) )\r
+      {\r
+        (void)_f_updatefileentry( 1 );\r
+        return F_ERR_WRITE;\r
+      }\r
+    }\r
+\r
+    return _f_updatefileentry( 0 );\r
+  }\r
+\r
+  return F_NO_ERROR;\r
+} /* fn_flush */\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_read\r
+ *\r
+ * read data from file\r
+ *\r
+ * INPUTS\r
+ *\r
+ * buf - where the store data\r
+ * size - size of items to be read\r
+ * _size_t - number of items need to be read\r
+ * filehandle - file where to read from\r
+ *\r
+ * RETURNS\r
+ *\r
+ * with the number of read bytes\r
+ *\r
+ ***************************************************************************/\r
+long fn_read ( void * buf, long size, long _size_st, F_FILE * f )\r
+{\r
+  char * buffer = (char *)buf;\r
+  long   retsize;\r
+\r
+  if ( !f )\r
+  {\r
+    return 0;\r
+  }\r
+\r
+  if ( ( gl_file.mode & ( F_FILE_RD | F_FILE_RDP | F_FILE_WRP | F_FILE_AP ) ) == 0 )\r
+  {\r
+    return 0;\r
+  }\r
+\r
+  retsize = size;\r
+  size *= _size_st;\r
+  _size_st = retsize;\r
+  retsize = 0;\r
+\r
+  if ( _f_getvolume() )\r
+  {\r
+    return 0;                     /*cant read any*/\r
+  }\r
+\r
+  if ( size + gl_file.relpos + gl_file.abspos >= gl_file.filesize ) /*read len longer than the file*/\r
+  {\r
+    size = (long)( ( gl_file.filesize ) - ( gl_file.relpos ) - ( gl_file.abspos ) ); /*calculate new size*/\r
+  }\r
+\r
+  if ( size <= 0 )\r
+  {\r
+    return 0;\r
+  }\r
+\r
+  if ( _f_getcurrsector() )\r
+  {\r
+    gl_file.mode = F_FILE_CLOSE; /*no more read allowed*/\r
+    return 0;\r
+  }\r
+\r
+  for( ; ; )\r
+  {\r
+    unsigned long  rdsize = (unsigned long)size;\r
+\r
+    if ( gl_file.relpos == F_SECTOR_SIZE )\r
+    {\r
+      unsigned char  ret;\r
+\r
+      gl_file.abspos += gl_file.relpos;\r
+      gl_file.relpos = 0;\r
+\r
+      if ( gl_file.modified )\r
+      {\r
+        ret = _f_writeglsector( (unsigned long)-1 );     /*empty write buffer */\r
+        if ( ret )\r
+        {\r
+          gl_file.mode = F_FILE_CLOSE;         /*no more read allowed*/\r
+          return retsize;\r
+        }\r
+      }\r
+\r
+      gl_file.pos.sector++;         /*goto next*/\r
+\r
+      ret = _f_getcurrsector();\r
+      if ( ( ret == F_ERR_EOF ) && ( !size ) )\r
+      {\r
+        return retsize;\r
+      }\r
+\r
+      if ( ret )\r
+      {\r
+        gl_file.mode = F_FILE_CLOSE;       /*no more read allowed*/\r
+        return retsize;\r
+      }\r
+    }\r
+\r
+    if ( !size )\r
+    {\r
+      break;\r
+    }\r
+\r
+    if ( rdsize >= F_SECTOR_SIZE - gl_file.relpos )\r
+    {\r
+      rdsize = (unsigned long)( F_SECTOR_SIZE - gl_file.relpos );\r
+    }\r
+\r
+    psp_memcpy( buffer, gl_sector + gl_file.relpos, rdsize ); /*always less than 512*/\r
+\r
+    buffer += rdsize;\r
+    gl_file.relpos += rdsize;\r
+    size -= rdsize;\r
+    retsize += rdsize;\r
+  }\r
+\r
+  return retsize / _size_st;\r
+} /* fn_read */\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_write\r
+ *\r
+ * write data into file\r
+ *\r
+ * INPUTS\r
+ *\r
+ * buf - where the store data\r
+ * size - size of items to be read\r
+ * size_t - number of items need to be read\r
+ * filehandle - file where to read from\r
+ *\r
+ * RETURNS\r
+ *\r
+ * with the number of read bytes\r
+ *\r
+ ***************************************************************************/\r
+\r
+long fn_write ( const void * buf, long size, long _size_st, F_FILE * f )\r
+{\r
+  char * buffer = (char *)buf;\r
+  long   retsize;\r
+  long   ret = 0;\r
+\r
+  if ( !f )\r
+  {\r
+    return 0;\r
+  }\r
+\r
+  if ( ( gl_file.mode & ( F_FILE_WR | F_FILE_A | F_FILE_RDP | F_FILE_WRP | F_FILE_AP ) ) == 0 )\r
+  {\r
+    return 0;\r
+  }\r
+\r
+  retsize = size;\r
+  size *= _size_st;\r
+  _size_st = retsize;\r
+  retsize = 0;\r
+\r
+  if ( _f_getvolume() )\r
+  {\r
+    return 0;                     /*can't write*/\r
+  }\r
+\r
+  if ( ( gl_file.mode ) & ( F_FILE_A | F_FILE_AP ) )\r
+  {\r
+    if ( _f_fseek( (long)gl_file.filesize ) )\r
+    {\r
+      gl_file.mode = F_FILE_CLOSE;\r
+      return 0;\r
+    }\r
+  }\r
+\r
+  if ( _f_getcurrsector() )\r
+  {\r
+    gl_file.mode = F_FILE_CLOSE;\r
+    return 0;\r
+  }\r
+\r
+  for( ; ; )\r
+  {\r
+    unsigned long  wrsize = (unsigned long)size;\r
+\r
+    if ( gl_file.relpos == F_SECTOR_SIZE )\r
+    {     /*now full*/\r
+      if ( gl_file.modified )\r
+      {\r
+        if ( _f_emptywritebuffer() )\r
+        {\r
+          gl_file.mode = F_FILE_CLOSE;\r
+          if ( _f_updatefileentry( 0 ) == 0 )\r
+          {\r
+            return retsize;\r
+          }\r
+          else\r
+          {\r
+            return 0;\r
+          }\r
+        }\r
+      }\r
+      else\r
+      {\r
+        gl_file.pos.sector++;       /*goto next*/\r
+      }\r
+\r
+      gl_file.abspos += gl_file.relpos;\r
+      gl_file.relpos = 0;\r
+\r
+      if ( wrsize && ( wrsize < F_SECTOR_SIZE ) )\r
+      {\r
+        ret = _f_getcurrsector();\r
+\r
+        if ( ret )\r
+        {\r
+          if ( ret != F_ERR_EOF )\r
+          {\r
+            gl_file.mode = F_FILE_CLOSE;       /*no more read allowed*/\r
+            return retsize;\r
+          }\r
+        }\r
+      }\r
+    }\r
+\r
+    if ( !size )\r
+    {\r
+      break;\r
+    }\r
+\r
+    if ( wrsize >= F_SECTOR_SIZE - gl_file.relpos )\r
+    {\r
+      wrsize = (unsigned long)( F_SECTOR_SIZE - gl_file.relpos );\r
+    }\r
+\r
+\r
+    psp_memcpy( gl_sector + gl_file.relpos, buffer, wrsize );\r
+    gl_file.modified = 1;    /*sector is modified*/\r
+\r
+    buffer += wrsize;\r
+    gl_file.relpos += wrsize;\r
+    size -= wrsize;\r
+    retsize += wrsize;\r
+\r
+    if ( gl_file.filesize < gl_file.abspos + gl_file.relpos )\r
+    {\r
+      gl_file.filesize = gl_file.abspos + gl_file.relpos;\r
+    }\r
+  }\r
+\r
+  return retsize / _size_st;\r
+} /* fn_write */\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_seek\r
+ *\r
+ * moves position into given offset in given file\r
+ *\r
+ * INPUTS\r
+ *\r
+ * filehandle - F_FILE structure which file position needed to be modified\r
+ * offset - relative position\r
+ * whence - where to calculate position (F_SEEK_SET,F_SEEK_CUR,F_SEEK_END)\r
+ *\r
+ * RETURNS\r
+ *\r
+ * 0 - if successfully\r
+ * other - if any error\r
+ *\r
+ ***************************************************************************/\r
+\r
+\r
+unsigned char fn_seek ( F_FILE * f, long offset, unsigned char whence )\r
+{\r
+  unsigned char  ret;\r
+\r
+  if ( !f )\r
+  {\r
+    return F_ERR_NOTOPEN;\r
+  }\r
+\r
+  if ( ( gl_file.mode & ( F_FILE_RD | F_FILE_WR | F_FILE_A | F_FILE_RDP | F_FILE_WRP | F_FILE_AP ) ) == 0 )\r
+  {\r
+    return F_ERR_NOTOPEN;\r
+  }\r
+\r
+  ret = _f_getvolume();\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  if ( whence == F_SEEK_CUR )\r
+  {\r
+    return _f_fseek( (long)( gl_file.abspos + gl_file.relpos + offset ) );\r
+  }\r
+  else if ( whence == F_SEEK_END )\r
+  {\r
+    return _f_fseek( (long)( gl_file.filesize + offset ) );\r
+  }\r
+  else if ( whence == F_SEEK_SET )\r
+  {\r
+    return _f_fseek( offset );\r
+  }\r
+\r
+  return F_ERR_NOTUSEABLE;\r
+} /* fn_seek */\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_tell\r
+ *\r
+ * Tells the current position of opened file\r
+ *\r
+ * INPUTS\r
+ *\r
+ * filehandle - which file needs the position\r
+ *\r
+ * RETURNS\r
+ *\r
+ * position in the file from start\r
+ *\r
+ ***************************************************************************/\r
+\r
+long fn_tell ( F_FILE * f )\r
+{\r
+  if ( !f )\r
+  {\r
+    return 0;\r
+  }\r
+\r
+  if ( ( gl_file.mode & ( F_FILE_RD | F_FILE_WR | F_FILE_A | F_FILE_RDP | F_FILE_WRP | F_FILE_AP ) ) == 0 )\r
+  {\r
+    return 0;\r
+  }\r
+\r
+  return (long)( gl_file.abspos + gl_file.relpos );\r
+}\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_eof\r
+ *\r
+ * Tells if the current position is end of file or not\r
+ *\r
+ * INPUTS\r
+ *\r
+ * filehandle - which file needs the checking\r
+ *\r
+ * RETURNS\r
+ *\r
+ * 0 - if not EOF\r
+ * other - if EOF or invalid file handle\r
+ *\r
+ ***************************************************************************/\r
+\r
+unsigned char fn_eof ( F_FILE * f )\r
+{\r
+  if ( !f )\r
+  {\r
+    return F_ERR_NOTOPEN;          /*if error*/\r
+  }\r
+\r
+  if ( gl_file.abspos + gl_file.relpos < gl_file.filesize )\r
+  {\r
+    return 0;\r
+  }\r
+\r
+  return F_ERR_EOF;  /*EOF*/\r
+}\r
+\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_rewind\r
+ *\r
+ * set the fileposition in the opened file to the begining\r
+ *\r
+ * INPUTS\r
+ *\r
+ * filehandle - which file needs to be rewinded\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+\r
+unsigned char fn_rewind ( F_FILE * filehandle )\r
+{\r
+  return fn_seek( filehandle, 0L, F_SEEK_SET );\r
+}\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_putc\r
+ *\r
+ * write a character into file\r
+ *\r
+ * INPUTS\r
+ *\r
+ * ch - what to write into file\r
+ * filehandle - file where to write\r
+ *\r
+ * RETURNS\r
+ *\r
+ * with the number of written bytes (1-success, 0-not successfully)\r
+ *\r
+ ***************************************************************************/\r
+\r
+int fn_putc ( int ch, F_FILE * filehandle )\r
+{\r
+  unsigned char  tmpch = (unsigned char)ch;\r
+\r
+  if ( fn_write( &tmpch, 1, 1, filehandle ) )\r
+  {\r
+    return ch;\r
+  }\r
+  else\r
+  {\r
+    return -1;\r
+  }\r
+}\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_getc\r
+ *\r
+ * get a character from file\r
+ *\r
+ * INPUTS\r
+ *\r
+ * filehandle - file where to read from\r
+ *\r
+ * RETURNS\r
+ *\r
+ * with the read character or -1 if read was not successfully\r
+ *\r
+ ***************************************************************************/\r
+int fn_getc ( F_FILE * filehandle )\r
+{\r
+  unsigned char  ch;\r
+\r
+  if ( !fn_read( &ch, 1, 1, filehandle ) )\r
+  {\r
+    return -1;\r
+  }\r
+\r
+  return (int)ch;\r
+}\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_delete\r
+ *\r
+ * delete a file\r
+ *\r
+ * INPUTS\r
+ *\r
+ * filename - file which wanted to be deleted (with or without path)\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+unsigned char fn_delete ( const char * filename )\r
+{\r
+  F_POS          pos;\r
+  F_DIRENTRY   * de;\r
+  F_NAME         fsname;\r
+  unsigned char  ret;\r
+\r
+  if ( _f_setfsname( filename, &fsname ) )\r
+  {\r
+    return F_ERR_INVALIDNAME;                                     /*invalid name*/\r
+  }\r
+\r
+  if ( _f_checknamewc( fsname.filename, fsname.fileext ) )\r
+  {\r
+    return F_ERR_INVALIDNAME;                                                    /*invalid name*/\r
+  }\r
+\r
+  if ( fsname.filename[0] == '.' )\r
+  {\r
+    return F_ERR_NOTFOUND;\r
+  }\r
+\r
+  ret = _f_getvolume();\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  if ( !( _f_findpath( &fsname, &pos ) ) )\r
+  {\r
+    return F_ERR_INVALIDDIR;\r
+  }\r
+\r
+  if ( !_f_findfilewc( fsname.filename, fsname.fileext, &pos, &de, 0 ) )\r
+  {\r
+    return F_ERR_NOTFOUND;\r
+  }\r
+\r
+  if ( de->attr & F_ATTR_DIR )\r
+  {\r
+    return F_ERR_INVALIDDIR;                                /*directory*/\r
+  }\r
+\r
+  if ( de->attr & F_ATTR_READONLY )\r
+  {\r
+    return F_ERR_ACCESSDENIED;                                      /*readonly*/\r
+  }\r
+\r
+  if ( ( gl_file.mode != F_FILE_CLOSE ) && ( gl_file.dirpos.sector == pos.sector ) && ( gl_file.dirpos.pos == pos.pos ) )\r
+  {\r
+    return F_ERR_LOCKED;\r
+  }\r
+\r
+  de->name[0] = (unsigned char)0xe5; /*removes it*/\r
+  ret = _f_writeglsector( (unsigned long)-1 );\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  ret = _f_removechain( _f_getdecluster( de ) );\r
+\r
+ #if F_FILE_CHANGED_EVENT\r
+  if ( f_filechangedevent && !ret )\r
+  {\r
+    ST_FILE_CHANGED  fc;\r
+    fc.action = FACTION_REMOVED;\r
+    fc.flags = FFLAGS_FILE_NAME;\r
+\r
+    if ( !_f_createfullname( fc.filename, sizeof( fc.filename ), fsname.path, fsname.filename, fsname.fileext ) )\r
+    {\r
+      f_filechangedevent( &fc );\r
+    }\r
+  }\r
+\r
+ #endif\r
+\r
+  return ret;\r
+} /* fn_delete */\r
+\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_seteof\r
+ *\r
+ * Set end of file\r
+ *\r
+ * INPUT:      f - file pointer\r
+ *             filesize - required new size\r
+ * RETURN:     F_NO_ERROR - on success\r
+ *             other if error\r
+ *\r
+ ***************************************************************************/\r
+unsigned char _f_seteof ( F_FILE * f, long filesize )\r
+{\r
+  unsigned char  rc = F_NO_ERROR;\r
+\r
+  if ( !f )\r
+  {\r
+    return F_ERR_NOTOPEN;        /*if error*/\r
+  }\r
+\r
+  if ( ( unsigned long) filesize < gl_file.filesize )\r
+  {\r
+    rc = _f_fseek( filesize );\r
+    if ( rc == F_NO_ERROR )\r
+    {\r
+      unsigned long  cluster;\r
+      rc = _f_getclustervalue( gl_file.pos.cluster, &cluster );\r
+      if ( rc == F_NO_ERROR )\r
+      {\r
+        if ( cluster != F_CLUSTER_LAST )\r
+        {\r
+          rc = _f_removechain( cluster );\r
+          if ( rc )\r
+          {\r
+            return rc;\r
+          }\r
+\r
+          rc = _f_setclustervalue( gl_file.pos.cluster, F_CLUSTER_LAST );\r
+          if ( rc )\r
+          {\r
+            return rc;\r
+          }\r
+\r
+          rc = _f_writefatsector();\r
+          if ( rc )\r
+          {\r
+            return rc;\r
+          }\r
+        }\r
+\r
+        gl_file.filesize = (unsigned long)filesize;\r
+      }\r
+    }\r
+  }\r
+  else if ( (unsigned long) filesize > gl_file.filesize )\r
+  {\r
+    rc = _f_fseek( filesize );\r
+  }\r
+\r
+  return rc;\r
+} /* _f_seteof */\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_seteof\r
+ *\r
+ * Set end of file\r
+ *\r
+ * INPUT:      f - file pointer\r
+ *             filesize - required new size\r
+ * RETURN:     F_NO_ERROR - on success\r
+ *             other if error\r
+ *\r
+ ***************************************************************************/\r
+unsigned char fn_seteof ( F_FILE * f )\r
+{\r
+  unsigned char  rc = F_NO_ERROR;\r
+\r
+  rc = _f_seteof( f, ( gl_file.abspos + gl_file.relpos ) );\r
+\r
+  return rc;\r
+} /* fn_seteof */\r
+\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_truncate\r
+ *\r
+ * Open a file and set end of file\r
+ *\r
+ * INPUT:      filename - name of the file\r
+ *             filesize - required new size\r
+ * RETURN:     NULL on error, otherwise file pointer\r
+ *\r
+ ***************************************************************************/\r
+F_FILE * fn_truncate ( const char * filename, long filesize )\r
+{\r
+  F_FILE       * f = fn_open( filename, "r+" );\r
+  unsigned char  rc;\r
+\r
+  if ( f != NULL )\r
+  {\r
+    rc = _f_fseek( (long)gl_file.filesize );\r
+    if ( rc == F_NO_ERROR )\r
+    {\r
+      rc = _f_seteof( f, filesize );\r
+    }\r
+\r
+    if ( rc )\r
+    {\r
+      fn_close( f );\r
+      f = NULL;\r
+    }\r
+  }\r
+\r
+  return f;\r
+} /* fn_truncate */\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/file.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/file.h
new file mode 100644 (file)
index 0000000..a124d07
--- /dev/null
@@ -0,0 +1,63 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef __FILE_H\r
+#define __FILE_H\r
+\r
+#include "../../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+#ifdef __cplusplus\r
+extern "C" {\r
+#endif\r
+\r
+#define F_FILE_CLOSE 0x00\r
+#define F_FILE_RD    0x01\r
+#define F_FILE_WR    0x02\r
+#define F_FILE_A     0x04\r
+#define F_FILE_RDP   0x08\r
+#define F_FILE_WRP   0x10\r
+#define F_FILE_AP    0x20\r
+\r
+#ifdef __cplusplus\r
+}\r
+#endif\r
+\r
+#endif /* ifndef __FILE_H */\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/util.c b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/util.c
new file mode 100644 (file)
index 0000000..590aecf
--- /dev/null
@@ -0,0 +1,320 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#include "../../api/fat_sl.h"\r
+#include "../../psp/include/psp_rtc.h"\r
+#include "dir.h"\r
+\r
+#include "util.h"\r
+\r
+#include "../../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_getword\r
+ *\r
+ * get a word 16bit number from a memory (it uses LITTLE ENDIAN mode always)\r
+ *\r
+ * INPUTS\r
+ *\r
+ * ptr - pointer where data is\r
+ *\r
+ * RETURNS\r
+ *\r
+ * word number\r
+ *\r
+ ***************************************************************************/\r
+unsigned short _f_getword ( void * ptr )\r
+{\r
+  unsigned char * sptr = (unsigned char *)ptr;\r
+  unsigned short  ret;\r
+\r
+  ret = (unsigned short)( sptr[1] & 0xff );\r
+  ret <<= 8;\r
+  ret |= ( sptr[0] & 0xff );\r
+  return ret;\r
+}\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_setword\r
+ *\r
+ * set a word 16bit number into a memory (it uses LITTLE ENDIAN mode always)\r
+ *\r
+ * INPUTS\r
+ *\r
+ * ptr - where to store data\r
+ * num - 16 bit number to store\r
+ *\r
+ ***************************************************************************/\r
+void _f_setword ( void * ptr, unsigned short num )\r
+{\r
+  unsigned char * sptr = (unsigned char *)ptr;\r
+\r
+  sptr[1] = (unsigned char)( num >> 8 );\r
+  sptr[0] = (unsigned char)( num );\r
+}\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_getlong\r
+ *\r
+ * get a long 32bit number from a memory (it uses LITTLE ENDIAN mode always)\r
+ *\r
+ * INPUTS\r
+ *\r
+ * ptr - pointer where data is\r
+ *\r
+ * RETURNS\r
+ *\r
+ * long number\r
+ *\r
+ ***************************************************************************/\r
+unsigned long _f_getlong ( void * ptr )\r
+{\r
+  unsigned char * sptr = (unsigned char *)ptr;\r
+  unsigned long   ret;\r
+\r
+  ret = (unsigned long)( sptr[3] & 0xff );\r
+  ret <<= 8;\r
+  ret |= ( sptr[2] & 0xff );\r
+  ret <<= 8;\r
+  ret |= ( sptr[1] & 0xff );\r
+  ret <<= 8;\r
+  ret |= ( sptr[0] & 0xff );\r
+  return ret;\r
+}\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_setlong\r
+ *\r
+ * set a long 32bit number into a memory (it uses LITTLE ENDIAN mode always)\r
+ *\r
+ * INPUTS\r
+ *\r
+ * ptr - where to store data\r
+ * num - 32 bit number to store\r
+ *\r
+ ***************************************************************************/\r
+void _f_setlong ( void * ptr, unsigned long num )\r
+{\r
+  unsigned char * sptr = (unsigned char *)ptr;\r
+\r
+  sptr[3] = (unsigned char)( num >> 24 );\r
+  sptr[2] = (unsigned char)( num >> 16 );\r
+  sptr[1] = (unsigned char)( num >> 8 );\r
+  sptr[0] = (unsigned char)( num );\r
+}\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _setcharzero\r
+ *\r
+ * fills with zero charater to memory\r
+ *\r
+ * INPUTS\r
+ *\r
+ * num - number of characters\r
+ * ptr - where to store data\r
+ *\r
+ * RETURNS\r
+ *\r
+ * last write position\r
+ *\r
+ ***************************************************************************/\r
+unsigned char * _setcharzero ( int num, unsigned char * ptr )\r
+{\r
+  while ( num-- )\r
+  {\r
+    *ptr++ = 0;\r
+  }\r
+\r
+  return ptr;\r
+}\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _setchar\r
+ *\r
+ * copy a charater string to memory\r
+ *\r
+ * INPUTS\r
+ *\r
+ * array - original code what to copy\r
+ * num - number of characters\r
+ * ptr - where to store data\r
+ *\r
+ * RETURNS\r
+ *\r
+ * last write position\r
+ *\r
+ ***************************************************************************/\r
+unsigned char * _setchar ( const unsigned char * array, int num, unsigned char * ptr )\r
+{\r
+  if ( !array )\r
+  {\r
+    return _setcharzero( num, ptr );\r
+  }\r
+\r
+  while ( num-- )\r
+  {\r
+    *ptr++ = *array++;\r
+  }\r
+\r
+  return ptr;\r
+}\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _setword\r
+ *\r
+ * store a 16bit word into memory\r
+ *\r
+ * INPUTS\r
+ *\r
+ * num - 16bit number to store\r
+ * ptr - where to store data\r
+ *\r
+ * RETURNS\r
+ *\r
+ * last write position\r
+ *\r
+ ***************************************************************************/\r
+unsigned char * _setword ( unsigned short num, unsigned char * ptr )\r
+{\r
+  _f_setword( ptr, num );\r
+  return ptr + 2;\r
+}\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _setlong\r
+ *\r
+ * store a 32bit long number into memory\r
+ *\r
+ * INPUTS\r
+ *\r
+ * num - 32bit number to store\r
+ * ptr - where to store data\r
+ *\r
+ * RETURNS\r
+ *\r
+ * last write position\r
+ *\r
+ ***************************************************************************/\r
+unsigned char * _setlong ( unsigned long num, unsigned char * ptr )\r
+{\r
+  _f_setlong( ptr, num );\r
+  return ptr + 4;\r
+}\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_toupper\r
+ *\r
+ * convert a string into lower case\r
+ *\r
+ * INPUTS\r
+ *\r
+ * s - input string to convert\r
+ *\r
+ ***************************************************************************/\r
+char _f_toupper ( char ch )\r
+{\r
+  if ( ( ch >= 'a' ) && ( ch <= 'z' ) )\r
+  {\r
+    return (char)( ch - 'a' + 'A' );\r
+  }\r
+\r
+  return ch;\r
+}\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * f_igettimedate\r
+ *\r
+ * INPUTS\r
+ *    time - pointer to time variable\r
+ *    date - pointer to date variable\r
+ * OUTPUTS\r
+ *    time - current time\r
+ *    date - current date\r
+ *\r
+ * RETURNS\r
+ *    none\r
+ *\r
+ ***************************************************************************/\r
+void f_igettimedate ( unsigned short * time, unsigned short * date )\r
+{\r
+  t_psp_timedate  s_timedate;\r
+\r
+  psp_getcurrenttimedate( &s_timedate );\r
+\r
+  *time = ( ( (uint16_t)s_timedate.hour << F_CTIME_HOUR_SHIFT ) & F_CTIME_HOUR_MASK )\r
+          | ( ( (uint16_t)s_timedate.min << F_CTIME_MIN_SHIFT )  & F_CTIME_MIN_MASK )\r
+          | ( ( ( (uint16_t)s_timedate.sec >> 1 ) << F_CTIME_SEC_SHIFT )  & F_CTIME_SEC_MASK );\r
+\r
+  *date = ( ( ( s_timedate.year - 1980 ) << F_CDATE_YEAR_SHIFT ) & F_CDATE_YEAR_MASK )\r
+          | ( ( (uint16_t)s_timedate.month << F_CDATE_MONTH_SHIFT ) & F_CDATE_MONTH_MASK )\r
+          | ( ( (uint16_t)s_timedate.day << F_CDATE_DAY_SHIFT ) & F_CDATE_DAY_MASK );\r
+\r
+  return;\r
+}\r
+\r
+\r
+\r
+\r
+\r
+\r
+\r
+\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/util.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/util.h
new file mode 100644 (file)
index 0000000..9d23665
--- /dev/null
@@ -0,0 +1,73 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef __UTIL_H\r
+#define __UTIL_H\r
+\r
+#include "util_sfn.h"\r
+\r
+#include "../../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+#ifdef __cplusplus\r
+extern "C" {\r
+#endif\r
+\r
+void f_igettimedate ( unsigned short * time, unsigned short * date );\r
+\r
+unsigned short _f_getword ( void * );\r
+unsigned long _f_getlong ( void * );\r
+char _f_toupper ( char );\r
+void _f_memset ( void *, unsigned char, int );\r
+void _f_memcpy ( void *, void *, int );\r
+\r
+void _f_setword ( void *, unsigned short );\r
+void _f_setlong ( void *, unsigned long );\r
+unsigned char * _setcharzero ( int, unsigned char * );\r
+unsigned char * _setchar ( const unsigned char *, int, unsigned char * );\r
+unsigned char * _setword ( unsigned short, unsigned char * );\r
+unsigned char * _setlong ( unsigned long, unsigned char * );\r
+\r
+#ifdef __cplusplus\r
+}\r
+#endif\r
+\r
+#endif /* ifndef __UTIL_H */\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/util_sfn.c b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/util_sfn.c
new file mode 100644 (file)
index 0000000..1ddbee1
--- /dev/null
@@ -0,0 +1,540 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#include "../../api/fat_sl.h"\r
+\r
+#include "util.h"\r
+\r
+#include "../../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_checknameprim\r
+ *\r
+ * checking a string if could be valid\r
+ *\r
+ * INPUTS\r
+ *\r
+ * ptr - pointer to name or extension\r
+ * len - number max char of name or extension\r
+ *\r
+ * RETURNS\r
+ *\r
+ ***************************************************************************/\r
+static unsigned char _f_checknameprim ( char * ptr, unsigned char len )\r
+{\r
+  unsigned char  inspace = 0;\r
+\r
+  while ( len-- )\r
+  {\r
+    char  ch = *ptr++;\r
+    if ( !inspace )\r
+    {\r
+      if ( ch == ' ' )\r
+      {\r
+        inspace = 1;\r
+      }\r
+\r
+      if ( ( ch == '|' ) || ( ch == '[' ) || ( ch == ']' ) || ( ch == '<' ) || ( ch == '>' ) || ( ch == '/' ) || ( ch == '\\' ) || ( ch == ':' ) )\r
+      {\r
+        return 1;\r
+      }\r
+    }\r
+    else if ( ch != ' ' )\r
+    {\r
+      return 1;                     /*no inspace allowed*/\r
+    }\r
+  }\r
+\r
+  return 0;\r
+} /* _f_checknameprim */\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_checkname\r
+ *\r
+ * checking filename and extension for special characters\r
+ *\r
+ * INPUTS\r
+ *\r
+ * name - filename (e.g.: filename)\r
+ * ext - extension of file (e.g.: txt)\r
+ *\r
+ * RETURNS\r
+ *\r
+ * 0 - if no contains invalid character\r
+ * other - if contains any invalid character\r
+ *\r
+ ***************************************************************************/\r
+unsigned char _f_checkname ( char * name, char * ext )\r
+{\r
+  if ( _f_checknameprim( name, F_MAXNAME ) )\r
+  {\r
+    return 1;\r
+  }\r
+\r
+  if ( _f_checknameprim( ext, F_MAXEXT ) )\r
+  {\r
+    return 1;\r
+  }\r
+\r
+  return 0;\r
+}\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_checknamewc\r
+ *\r
+ * checking filename and extension for wildcard character\r
+ *\r
+ * INPUTS\r
+ *\r
+ * name - filename (e.g.: filename)\r
+ * ext - extension of file (e.g.: txt)\r
+ *\r
+ * RETURNS\r
+ *\r
+ * 0 - if no contains wildcard character (? or *)\r
+ * other - if contains any wildcard character\r
+ *\r
+ ***************************************************************************/\r
+unsigned char _f_checknamewc ( const char * name, const char * ext )\r
+{\r
+  unsigned char  a = 0;\r
+\r
+  for ( a = 0 ; a < F_MAXNAME ; a++ )\r
+  {\r
+    char  ch = name[a];\r
+    if ( ( ch == '?' ) || ( ch == '*' ) )\r
+    {\r
+      return 1;\r
+    }\r
+  }\r
+\r
+  for ( a = 0 ; a < F_MAXEXT ; a++ )\r
+  {\r
+    char  ch = ext[a];\r
+    if ( ( ch == '?' ) || ( ch == '*' ) )\r
+    {\r
+      return 1;\r
+    }\r
+  }\r
+\r
+  return _f_checkname( (char *)name, (char *)ext );\r
+} /* _f_checknamewc */\r
+\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_setnameext\r
+ *\r
+ * convert a string into filename and extension separatelly, the terminator\r
+ * character could be zero char, '/' or '\'\r
+ *\r
+ * INPUTS\r
+ *\r
+ * s - source string (e.g.: hello.txt)\r
+ * name - where to store name (this array size has to be F_MAXNAME (8))\r
+ * ext - where to store extension (this array size has to be F_MAXEXT (3))\r
+ *\r
+ * RETURNS\r
+ *\r
+ * length of the used bytes from source string array\r
+ *\r
+ ***************************************************************************/\r
+unsigned char _f_setnameext ( char * s, char * name, char * ext )\r
+{\r
+  unsigned char  len, extlen = 0;\r
+  unsigned char  a;\r
+  unsigned char  setext = 1;\r
+\r
+  for ( len = 0 ; ; )\r
+  {\r
+    unsigned char  ch = s[len];\r
+    if ( ( ch == 0 ) || ( ch == '\\' ) || ( ch == '/' ) )\r
+    {\r
+      break;\r
+    }\r
+\r
+    len++;                      /*calculate len*/\r
+  }\r
+\r
+  if ( len && ( s[0] == '.' ) )\r
+  {\r
+/*             if (len==1 || (s[1]=='.' && len==2)) goto dots;         */\r
+    if ( ( len == 1 ) || ( s[1] == '.' ) )\r
+    {\r
+      goto dots;\r
+    }\r
+  }\r
+\r
+  for ( a = len ; a ; a-- )\r
+  {\r
+    if ( s[a - 1] == '.' )\r
+    {\r
+      unsigned char  b;\r
+\r
+      extlen = (unsigned char)( len - a + 1 );\r
+      len = (unsigned char)( a - 1 );\r
+\r
+      for ( b = 0 ; b < F_MAXEXT ; b++ )\r
+      {\r
+        if ( b < extlen - 1 )\r
+        {\r
+          ext[b] = _f_toupper( s[a++] );\r
+        }\r
+        else\r
+        {\r
+          ext[b] = ' ';\r
+        }\r
+      }\r
+\r
+      setext = 0;\r
+      break;\r
+    }\r
+  }\r
+\r
+dots:\r
+  if ( setext )\r
+  {\r
+    for ( a = 0 ; a < F_MAXEXT ; a++ )\r
+    {\r
+      ext[a] = ' ';\r
+    }\r
+  }\r
+\r
+  for ( a = 0 ; a < F_MAXNAME ; a++ )\r
+  {\r
+    if ( a < len )\r
+    {\r
+      name[a] = _f_toupper( s[a] );\r
+    }\r
+    else\r
+    {\r
+      name[a] = ' ';\r
+    }\r
+  }\r
+\r
+  return (unsigned char)( len + extlen );\r
+} /* _f_setnameext */\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_setfsname\r
+ *\r
+ * convert a single string into F_NAME structure\r
+ *\r
+ * INPUTS\r
+ *\r
+ * name - combined name with drive,path,filename,extension used for source\r
+ * fsname - where to fill this structure with separated drive,path,name,ext\r
+ *\r
+ * RETURNS\r
+ *\r
+ * 0 - if successfully\r
+ * other - if name contains invalid path or name\r
+ *\r
+ ***************************************************************************/\r
+unsigned char _f_setfsname ( const char * name, F_NAME * fsname )\r
+{\r
+  char           s[F_MAXPATH];\r
+  unsigned char  namepos = 0;\r
+\r
+  unsigned char  pathpos = 0;\r
+  unsigned char  a;\r
+\r
+  s[0] = 0;\r
+\r
+  if ( !name[0] )\r
+  {\r
+    return 1;               /*no name*/\r
+  }\r
+\r
+  if ( name[1] == ':' )\r
+  {\r
+    name += 2;\r
+  }\r
+\r
+  if ( ( name[0] != '/' ) && ( name[0] != '\\' ) )\r
+  {\r
+    if ( fn_getcwd( fsname->path, F_MAXPATH, 0 ) )\r
+    {\r
+      return 1;                                            /*error*/\r
+    }\r
+\r
+    for ( pathpos = 0 ; fsname->path[pathpos] ; )\r
+    {\r
+      pathpos++;\r
+    }\r
+  }\r
+\r
+\r
+  for ( ; ; )\r
+  {\r
+    char  ch = _f_toupper( *name++ );\r
+\r
+    if ( !ch )\r
+    {\r
+      break;\r
+    }\r
+\r
+    if ( ch == ':' )\r
+    {\r
+      return 1;                /*not allowed*/\r
+    }\r
+\r
+    if ( ( ch == '/' ) || ( ch == '\\' ) )\r
+    {\r
+      if ( pathpos )\r
+      {\r
+        if ( fsname->path[pathpos - 1] == '/' )\r
+        {\r
+          return 1;                                         /*not allowed double */\r
+        }\r
+\r
+        if ( pathpos >= F_MAXPATH - 2 )\r
+        {\r
+          return 1;                                 /*path too long*/\r
+        }\r
+\r
+        fsname->path[pathpos++] = '/';\r
+      }\r
+\r
+      for ( ; namepos ; )\r
+      {\r
+        if ( s[namepos - 1] != ' ' )\r
+        {\r
+          break;\r
+        }\r
+\r
+        namepos--;                /*remove end spaces*/\r
+      }\r
+\r
+      for ( a = 0 ; a < namepos ; a++ )\r
+      {\r
+        if ( pathpos >= F_MAXPATH - 2 )\r
+        {\r
+          return 1;                                 /*path too long*/\r
+        }\r
+\r
+        fsname->path[pathpos++] = s[a];\r
+      }\r
+\r
+      namepos = 0;\r
+      continue;\r
+    }\r
+\r
+    if ( ( ch == ' ' ) && ( !namepos ) )\r
+    {\r
+      continue;                              /*remove start spaces*/\r
+    }\r
+\r
+    if ( namepos >= ( sizeof( s ) - 2 ) )\r
+    {\r
+      return 1;                               /*name too long*/\r
+    }\r
+\r
+    s[namepos++] = ch;\r
+  }\r
+\r
+  s[namepos] = 0; /*terminates it*/\r
+  fsname->path[pathpos] = 0;  /*terminates it*/\r
+\r
+  for ( ; namepos ; )\r
+  {\r
+    if ( s[namepos - 1] != ' ' )\r
+    {\r
+      break;\r
+    }\r
+\r
+    s[namepos - 1] = 0; /*remove end spaces*/\r
+    namepos--;\r
+  }\r
+\r
+  if ( !_f_setnameext( s, fsname->filename, fsname->fileext ) )\r
+  {\r
+    return 2;                                                         /*no name*/\r
+  }\r
+\r
+  if ( fsname->filename[0] == ' ' )\r
+  {\r
+    return 1;                               /*cannot be*/\r
+  }\r
+\r
+  return 0;\r
+} /* _f_setfsname */\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_createfullname\r
+ *\r
+ * create full name\r
+ *\r
+ * INPUTS\r
+ *\r
+ * buffer - where to create\r
+ * buffersize - size of the buffer\r
+ * drivenum - drive number\r
+ * path - path of the file\r
+ * filename - file name\r
+ * fileext - file extension\r
+ *\r
+ * RETURNS\r
+ *\r
+ * 1 - if found and osize is filled\r
+ * 0 - not found\r
+ *\r
+ ***************************************************************************/\r
+int _f_createfullname ( char * buffer, int buffersize, char * path, char * filename, char * fileext )\r
+{\r
+  char * fullname = buffer;\r
+  int    a;\r
+\r
+  /* adding drive letter */\r
+  if ( buffersize < 1 )\r
+  {\r
+    return 1;\r
+  }\r
+\r
+  *fullname++ = '/';\r
+  buffersize -= 1;\r
+\r
+  /* adding path */\r
+  if ( path[0] )\r
+  {\r
+    for ( ; ; )\r
+    {\r
+      char  ch = *path++;\r
+\r
+      if ( !ch )\r
+      {\r
+        break;\r
+      }\r
+\r
+      if ( buffersize <= 0 )\r
+      {\r
+        return 1;\r
+      }\r
+\r
+      *fullname++ = ch;\r
+      buffersize--;\r
+    }\r
+\r
+    /* adding separator */\r
+    if ( buffersize <= 0 )\r
+    {\r
+      return 1;\r
+    }\r
+\r
+    *fullname++ = '/';\r
+  }\r
+\r
+  /* adding name */\r
+  for ( a = 0 ; a < F_MAXNAME ; a++ )\r
+  {\r
+    char  ch = *filename++;\r
+\r
+    if ( ( !ch ) || ( ch == 32 ) )\r
+    {\r
+      break;\r
+    }\r
+\r
+    if ( buffersize <= 0 )\r
+    {\r
+      return 1;\r
+    }\r
+\r
+    *fullname++ = ch;\r
+    buffersize--;\r
+  }\r
+\r
+  /* adding ext*/\r
+  if ( fileext[0] && ( fileext[0] != 32 ) )\r
+  {\r
+    /* adding dot */\r
+    if ( !buffersize )\r
+    {\r
+      return 1;\r
+    }\r
+\r
+    *fullname++ = '.';\r
+\r
+    for ( a = 0 ; a < F_MAXEXT ; a++ )\r
+    {\r
+      char  ch = *fileext++;\r
+\r
+      if ( ( !ch ) || ( ch == 32 ) )\r
+      {\r
+        break;\r
+      }\r
+\r
+      if ( buffersize <= 0 )\r
+      {\r
+        return 1;\r
+      }\r
+\r
+      *fullname++ = ch;\r
+      buffersize--;\r
+    }\r
+  }\r
+\r
+  /* adding terminator */\r
+  if ( buffersize <= 0 )\r
+  {\r
+    return 1;\r
+  }\r
+\r
+  *fullname++ = 0;\r
+\r
+  return 0;\r
+} /* _f_createfullname */\r
+\r
+\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/util_sfn.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/util_sfn.h
new file mode 100644 (file)
index 0000000..8e9751a
--- /dev/null
@@ -0,0 +1,62 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef __UTIL_SFN_H\r
+#define __UTIL_SFN_H\r
+\r
+#include "../../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+#ifdef __cplusplus\r
+extern "C" {\r
+#endif\r
+\r
+unsigned char _f_checknamewc ( const char *, const char * );\r
+unsigned char _f_checkname ( char *, char * );\r
+\r
+unsigned char _f_setnameext ( char *, char *, char * );\r
+unsigned char _f_setfsname ( const char *, F_NAME * );\r
+int _f_createfullname ( char * buffer, int buffersize, char * path, char * filename, char * fileext );\r
+\r
+#ifdef __cplusplus\r
+}\r
+#endif\r
+\r
+#endif /* ifndef __UTIL_SFN_H */\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/volume.c b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/volume.c
new file mode 100644 (file)
index 0000000..2260983
--- /dev/null
@@ -0,0 +1,939 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#include "../../api/fat_sl.h"\r
+#include "../../psp/include/psp_string.h"\r
+\r
+#include "volume.h"\r
+#include "util.h"\r
+#include "drv.h"\r
+#include "fat.h"\r
+#include "dir.h"\r
+#include "file.h"\r
+\r
+#include "../../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+#if F_FS_THREAD_AWARE == 1\r
+  #include "f_lock.h"\r
+#endif\r
+\r
+F_VOLUME  gl_volume;                /* only one volume */\r
+F_FILE    gl_file;                  /* file */\r
+char      gl_sector[F_SECTOR_SIZE]; /* actual sector */\r
+\r
+#if F_FILE_CHANGED_EVENT\r
+F_FILE_CHANGED_EVENTFUNC  f_filechangedevent;\r
+#endif\r
+\r
+\r
+/* Defines the number of sectors per cluster on a sector number basis */\r
+typedef struct\r
+{\r
+  unsigned long  max_sectors;\r
+  unsigned char  sector_per_cluster;\r
+} t_FAT32_CS;\r
+\r
+static const t_FAT32_CS  FAT32_CS[] =\r
+{\r
+  { 0x00020000, 1 }     /* ->64MB */\r
+  , { 0x00040000, 2 }   /* ->128MB */\r
+  , { 0x00080000, 4 }   /* ->256MB */\r
+  , { 0x01000000, 8 }   /* ->8GB */\r
+  , { 0x02000000, 16 }  /* ->16GB */\r
+  , { 0x0ffffff0, 32 }  /* -> ... */\r
+};\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_writebootrecord\r
+ *\r
+ * writing boot record onto a volume, it uses number of hidden sector variable\r
+ *\r
+ * INPUTS\r
+ * phy - media physical descriptor\r
+ *\r
+ * RETURNS\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+static unsigned char _f_writebootrecord ( F_PHY * phy )\r
+{\r
+  unsigned char   jump_code[] =\r
+  {\r
+    0xeb, 0x3c, 0x90\r
+  };\r
+  unsigned char   oem_name[] = "MSDOS5.0";\r
+  unsigned char   executable_marker[] =\r
+  {\r
+    0x55, 0xaa\r
+  };\r
+  unsigned char * ptr = (unsigned char *)gl_sector;\r
+  unsigned char   rs;\r
+  unsigned short  mre;\r
+\r
+  unsigned char  ret;\r
+  unsigned char  _n = 0;\r
+\r
+  if ( gl_volume.mediatype == F_FAT32_MEDIA )\r
+  {  /*write FS_INFO*/\r
+    unsigned char  a;\r
+\r
+    rs = 32 + 4;\r
+    mre = 0;\r
+\r
+    psp_memset( ptr, 0, F_SECTOR_SIZE );\r
+\r
+    for ( a = 0 ; a < rs ; a++ )\r
+    {\r
+      ret = _f_writeglsector( a ); /*erase reserved area*/\r
+      if ( ret )\r
+      {\r
+        return ret;\r
+      }\r
+    }\r
+\r
+    ptr = _setlong( 0x41615252, ptr ); /*signature*/\r
+    ptr = _setcharzero( 480, ptr );    /*reserved*/\r
+    ptr = _setlong( 0x61417272, ptr ); /*signature*/\r
+    ptr = _setlong( 0xffffffff, ptr ); /*no last*/\r
+    ptr = _setlong( 0xffffffff, ptr ); /*no hint*/\r
+    ptr = _setcharzero( 12, ptr );     /*reserved*/\r
+    ptr = _setlong( 0xaa550000, ptr ); /*trail*/\r
+\r
+\r
+    ret = _f_writeglsector( 1 ); /*write FSINFO*/\r
+    if ( ret )\r
+    {\r
+      return ret;\r
+    }\r
+\r
+    ret = _f_writeglsector( 1 + 6 ); /*write FSINFO*/\r
+    if ( ret )\r
+    {\r
+      return ret;\r
+    }\r
+  }\r
+  else\r
+  {\r
+    rs = 1;\r
+    mre = 512;\r
+  }\r
+\r
+  ptr = (unsigned char *)gl_sector;\r
+  ptr = _setchar( jump_code, sizeof( jump_code ), ptr );\r
+  ptr = _setchar( oem_name, sizeof( oem_name ) - 1, ptr );\r
+  ptr = _setword( F_SECTOR_SIZE, ptr );\r
+  *ptr++ = gl_volume.bootrecord.sector_per_cluster;\r
+  ptr = _setword( rs, ptr );  /* reserved sectors */\r
+  *ptr++ = 2;                 /* number of FATs */\r
+  ptr = _setword( mre, ptr ); /* max root entry */\r
+  if ( phy->number_of_sectors < 0x10000 )\r
+  {\r
+    ptr = _setword( (unsigned short)phy->number_of_sectors, ptr );\r
+  }\r
+  else\r
+  {\r
+    ptr = _setword( 0, ptr );\r
+  }\r
+\r
+  *ptr++ = 0xf0;                /* media descriptor */\r
+  ptr = _setword( (unsigned short)gl_volume.bootrecord.sector_per_FAT, ptr );\r
+  ptr = _setword( phy->sector_per_track, ptr );\r
+  ptr = _setword( phy->number_of_heads, ptr );\r
+  ptr = _setlong( 0, ptr ); /* number of hidden sectors */\r
+  if ( phy->number_of_sectors >= 0x10000 )\r
+  {\r
+    ptr = _setlong( phy->number_of_sectors, ptr );\r
+  }\r
+  else\r
+  {\r
+    ptr = _setlong( 0, ptr );                                       /* number of sectors */\r
+  }\r
+\r
+  if ( gl_volume.mediatype == F_FAT32_MEDIA )\r
+  {\r
+    ptr = _setlong( gl_volume.bootrecord.sector_per_FAT32, ptr );\r
+    ptr = _setword( 0, ptr );\r
+    ptr = _setword( 0, ptr );\r
+    ptr = _setlong( 2, ptr );\r
+    ptr = _setword( 1, ptr );\r
+    ptr = _setword( 6, ptr );\r
+    ptr = _setchar( NULL, 12, ptr );\r
+    _n = 28;\r
+  }\r
+\r
+\r
+  ptr = _setword( 0, ptr ); /* logical drive num */\r
+  *ptr++ = 0x29;            /* extended signature */\r
+  ptr = _setlong( 0x11223344, ptr );\r
+  ptr = _setchar( (const unsigned char *)"NO NAME    ", 11, ptr ); /* volume name */\r
+\r
+  switch ( gl_volume.mediatype )\r
+  {\r
+    case F_FAT12_MEDIA:\r
+      ptr = _setchar( (const unsigned char *)"FAT12   ", 8, ptr );\r
+      break;\r
+\r
+    case F_FAT16_MEDIA:\r
+      ptr = _setchar( (const unsigned char *)"FAT16   ", 8, ptr );\r
+      break;\r
+\r
+    case F_FAT32_MEDIA:\r
+      ptr = _setchar( (const unsigned char *)"FAT32   ", 8, ptr );\r
+      break;\r
+\r
+    default:\r
+      return F_ERR_INVALIDMEDIA;\r
+  } /* switch */\r
+\r
+  ptr = _setchar( 0, 448 - _n, ptr );\r
+  ptr = _setchar( executable_marker, sizeof( executable_marker ), ptr );\r
+\r
+  if ( _n )\r
+  {\r
+    ret = _f_writeglsector( 6 );\r
+    if ( ret )\r
+    {\r
+      return ret;\r
+    }\r
+  }\r
+\r
+\r
+  return _f_writeglsector( 0 ); /*write bootrecord*/\r
+} /* _f_writebootrecord */\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_buildsectors\r
+ *\r
+ * INPUTS\r
+ * phy - media physical descriptor\r
+ *\r
+ * calculate relative sector position from boot record\r
+ *\r
+ ***************************************************************************/\r
+static unsigned char _f_buildsectors ( F_PHY * phy )\r
+{\r
+  gl_volume.mediatype = F_UNKNOWN_MEDIA;\r
+\r
+\r
+  if ( gl_volume.bootrecord.sector_per_FAT )\r
+  {\r
+    gl_volume.firstfat.sector = 1;\r
+    gl_volume.firstfat.num = gl_volume.bootrecord.sector_per_FAT;\r
+    gl_volume.root.sector = gl_volume.firstfat.sector + ( gl_volume.firstfat.num * (unsigned long)( gl_volume.bootrecord.number_of_FATs ) );\r
+    gl_volume.root.num = ( 512 * sizeof( F_DIRENTRY ) ) / F_SECTOR_SIZE;\r
+\r
+    gl_volume._tdata.sector = gl_volume.root.sector + gl_volume.root.num;\r
+    gl_volume._tdata.num = 0;  /*??*/\r
+  }\r
+  else\r
+  {\r
+    gl_volume.firstfat.sector = ( 32 + 4 );\r
+    gl_volume.firstfat.num = gl_volume.bootrecord.sector_per_FAT32;\r
+    gl_volume._tdata.sector = gl_volume.firstfat.sector;\r
+    gl_volume._tdata.sector += gl_volume.firstfat.num * (unsigned long)( gl_volume.bootrecord.number_of_FATs );\r
+    gl_volume._tdata.num = 0;  /*??*/\r
+\r
+    {\r
+      unsigned long  sectorcou = gl_volume.bootrecord.sector_per_cluster;\r
+      gl_volume.root.sector = ( ( gl_volume.bootrecord.rootcluster - 2 ) * sectorcou ) + gl_volume._tdata.sector;\r
+      gl_volume.root.num = gl_volume.bootrecord.sector_per_cluster;\r
+    }\r
+  }\r
+\r
+  {\r
+    unsigned long  maxcluster;\r
+    maxcluster = phy->number_of_sectors;\r
+    maxcluster -= gl_volume._tdata.sector;\r
+    maxcluster /= gl_volume.bootrecord.sector_per_cluster;\r
+    gl_volume.maxcluster = maxcluster;\r
+  }\r
+\r
+  if ( gl_volume.maxcluster < ( F_CLUSTER_RESERVED & 0xfff ) )\r
+  {\r
+    gl_volume.mediatype = F_FAT12_MEDIA;\r
+  }\r
+  else if ( gl_volume.maxcluster < ( F_CLUSTER_RESERVED & 0xffff ) )\r
+  {\r
+    gl_volume.mediatype = F_FAT16_MEDIA;\r
+  }\r
+  else\r
+  {\r
+    gl_volume.mediatype = F_FAT32_MEDIA;\r
+  }\r
+\r
+  return F_NO_ERROR;\r
+} /* _f_buildsectors */\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_prepareformat\r
+ *\r
+ * preparing boot record for formatting, it sets and calculates values\r
+ *\r
+ * INPUTS\r
+ * phy - media physical descriptor\r
+ * f_bootrecord - which bootrecord need to be prepare\r
+ * number_of_hidden_sectors - where boot record starts\r
+ * fattype - one of this definitions F_FAT12_MEDIA,F_FAT16_MEDIA,F_FAT32_MEDIA\r
+ *\r
+ * RETURNS\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+static unsigned char _f_prepareformat ( F_PHY * phy, unsigned char fattype )\r
+{\r
+  if ( !phy->number_of_sectors )\r
+  {\r
+    return F_ERR_INVALIDSECTOR;\r
+  }\r
+\r
+  gl_volume.bootrecord.number_of_FATs = 2;\r
+  gl_volume.bootrecord.media_descriptor = 0xf0;\r
+\r
+  if ( fattype != F_FAT32_MEDIA )\r
+  {\r
+    unsigned long  _n;\r
+    switch ( fattype )\r
+    {\r
+      case F_FAT12_MEDIA:\r
+        _n = F_CLUSTER_RESERVED & 0xfff;\r
+        break;\r
+\r
+      case F_FAT16_MEDIA:\r
+        _n = F_CLUSTER_RESERVED & 0xffff;\r
+        break;\r
+\r
+      default:\r
+        return F_ERR_INVFATTYPE;\r
+    }\r
+\r
+    gl_volume.bootrecord.sector_per_cluster = 1;\r
+    while ( gl_volume.bootrecord.sector_per_cluster )\r
+    {\r
+      if ( phy->number_of_sectors / gl_volume.bootrecord.sector_per_cluster < _n )\r
+      {\r
+        break;\r
+      }\r
+\r
+      gl_volume.bootrecord.sector_per_cluster <<= 1;\r
+    }\r
+\r
+    if ( !gl_volume.bootrecord.sector_per_cluster )\r
+    {\r
+      return F_ERR_MEDIATOOLARGE;\r
+    }\r
+  }\r
+\r
+  else\r
+  {\r
+    unsigned char  i;\r
+    for ( i = 0 ; i<( sizeof( FAT32_CS ) / sizeof( t_FAT32_CS ) ) - 1 && phy->number_of_sectors>FAT32_CS[i].max_sectors ; i++ )\r
+    {\r
+    }\r
+\r
+    gl_volume.bootrecord.sector_per_cluster = FAT32_CS[i].sector_per_cluster;\r
+  }\r
+  if ( !gl_volume.bootrecord.sector_per_cluster )\r
+  {\r
+    return F_ERR_INVALIDMEDIA;                                               /*fat16 cannot be there*/\r
+  }\r
+\r
+  {\r
+    long           secpercl = gl_volume.bootrecord.sector_per_cluster;\r
+    long           nfat = gl_volume.bootrecord.number_of_FATs;\r
+    unsigned long  roots;\r
+    unsigned long  fatsec;\r
+\r
+    roots = ( 512 * sizeof( F_DIRENTRY ) ) / F_SECTOR_SIZE;\r
+\r
+    switch ( fattype )\r
+    {\r
+      case F_FAT32_MEDIA:\r
+      {\r
+        unsigned long  _n = (unsigned long)( 128 * secpercl + nfat );\r
+        fatsec = ( phy->number_of_sectors - ( 32 + 4 ) + 2 * secpercl );\r
+        fatsec += ( _n - 1 );\r
+        fatsec /= _n;\r
+        gl_volume.bootrecord.sector_per_FAT32 = fatsec;\r
+        gl_volume.bootrecord.sector_per_FAT = 0;\r
+      }\r
+      break;\r
+\r
+      case F_FAT16_MEDIA:\r
+      {\r
+        unsigned long  _n = (unsigned long)( 256 * secpercl + nfat );\r
+        fatsec = ( phy->number_of_sectors - 1 - roots + 2 * secpercl );\r
+        fatsec += ( _n - 1 );\r
+        fatsec /= _n;\r
+        gl_volume.bootrecord.sector_per_FAT = (unsigned short)( fatsec );\r
+      }\r
+      break;\r
+\r
+      case F_FAT12_MEDIA:\r
+      {\r
+        unsigned long  _n = (unsigned long)( 1024 * secpercl + 3 * nfat );\r
+        fatsec = ( phy->number_of_sectors - 1 - roots + 2 * secpercl );\r
+        fatsec *= 3;\r
+        fatsec += ( _n - 1 );\r
+        fatsec /= _n;\r
+        gl_volume.bootrecord.sector_per_FAT = (unsigned short)( fatsec );\r
+      }\r
+      break;\r
+\r
+      default:\r
+        return F_ERR_INVALIDMEDIA;\r
+    } /* switch */\r
+\r
+    return F_NO_ERROR;\r
+  }\r
+} /* _f_prepareformat */\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_postformat\r
+ *\r
+ * erase fats, erase root directory, reset variables after formatting\r
+ *\r
+ * INPUTS\r
+ * phy - media physical descriptor\r
+ * fattype - one of this definitions F_FAT12_MEDIA,F_FAT16_MEDIA,F_FAT32_MEDIA\r
+ *\r
+ * RETURNS\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+static unsigned char _f_postformat ( F_PHY * phy, unsigned char fattype )\r
+{\r
+  unsigned long  a;\r
+  unsigned char  ret;\r
+\r
+  _f_buildsectors( phy ); /*get positions*/\r
+  if ( gl_volume.mediatype != fattype )\r
+  {\r
+    return F_ERR_MEDIATOOSMALL;\r
+  }\r
+\r
+  gl_volume.fatsector = (unsigned long)( -1 );\r
+\r
+  {\r
+    unsigned char * ptr = (unsigned char *)gl_sector;\r
+    unsigned char   j = 2;\r
+    unsigned long   i;\r
+\r
+    psp_memset( ptr, 0, F_SECTOR_SIZE );\r
+\r
+    switch ( gl_volume.mediatype )\r
+    {\r
+      case F_FAT16_MEDIA:\r
+        j = 3;\r
+        break;\r
+\r
+      case F_FAT32_MEDIA:\r
+        j = 11;\r
+        break;\r
+    }\r
+\r
+    *ptr = gl_volume.bootrecord.media_descriptor;\r
+    psp_memset( ptr + 1, 0xff, j );\r
+    if ( gl_volume.mediatype == F_FAT32_MEDIA )\r
+    {\r
+      *( ptr + 8 ) = (unsigned char)( F_CLUSTER_LAST & 0xff );\r
+    }\r
+\r
+    (void)_f_writeglsector( gl_volume.firstfat.sector );\r
+    (void)_f_writeglsector( gl_volume.firstfat.sector + gl_volume.firstfat.num );\r
+    psp_memset( ptr, 0, ( j + 1 ) );\r
+\r
+    for ( i = 1 ; i < gl_volume.firstfat.num ; i++ )\r
+    {\r
+      (void)_f_writeglsector( gl_volume.firstfat.sector + i );\r
+      (void)_f_writeglsector( gl_volume.firstfat.sector + i + gl_volume.firstfat.num );\r
+    }\r
+  }\r
+\r
+  for ( a = 0 ; a < gl_volume.root.num ; a++ ) /*reset root direntries*/\r
+  {\r
+    ret = _f_writeglsector( gl_volume.root.sector + a );\r
+    if ( ret )\r
+    {\r
+      return ret;\r
+    }\r
+  }\r
+\r
+  return _f_writebootrecord( phy );\r
+} /* _f_postformat */\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_hardformat\r
+ *\r
+ * Making a complete format on media, independently from master boot record,\r
+ * according to media physical\r
+ *\r
+ * INPUTS\r
+ * fattype - one of this definitions F_FAT12_MEDIA,F_FAT16_MEDIA,F_FAT32_MEDIA\r
+ *\r
+ * RETURNS\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+unsigned char fn_hardformat ( unsigned char fattype )\r
+{\r
+  unsigned char  ret;\r
+  int            mdrv_ret;\r
+  F_PHY          phy;\r
+\r
+  ret = _f_getvolume();\r
+  if ( ret && ( ret != F_ERR_NOTFORMATTED ) )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  gl_volume.state = F_STATE_NEEDMOUNT;\r
+\r
+  psp_memset( &phy, 0, sizeof( F_PHY ) );\r
+\r
+  mdrv_ret = mdrv->getphy( mdrv, &phy );\r
+  if ( mdrv_ret )\r
+  {\r
+    return F_ERR_ONDRIVE;\r
+  }\r
+\r
+  ret = _f_prepareformat( &phy, fattype ); /*no partition*/\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  return _f_postformat( &phy, fattype );\r
+} /* fn_hardformat */\r
+\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_readbootrecord\r
+ *\r
+ * read boot record from a volume, it detects if there is MBR on the media\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+static unsigned char _f_readbootrecord ( void )\r
+{\r
+  unsigned char   ret;\r
+  unsigned char * ptr = (unsigned char *)gl_sector;\r
+  unsigned long   maxcluster, _n;\r
+  unsigned long   first_sector = 0;\r
+\r
+  gl_volume.mediatype = F_UNKNOWN_MEDIA;\r
+\r
+\r
+  ret = _f_readglsector( 0 );\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+\r
+  if ( ( ptr[0x1fe] != 0x55 ) || ( ptr[0x1ff] != 0xaa ) )\r
+  {\r
+    return F_ERR_NOTFORMATTED;                                              /*??*/\r
+  }\r
+\r
+  if ( ( ptr[0] != 0xeb ) && ( ptr[0] != 0xe9 ) )\r
+  {\r
+    first_sector = _f_getlong( &ptr[0x08 + 0x1be] ); /*start sector for 1st partioon*/\r
+\r
+    ret = _f_readglsector( first_sector );\r
+    if ( ret )\r
+    {\r
+      return ret;\r
+    }\r
+\r
+    if ( ( ptr[0x1fe] != 0x55 ) || ( ptr[0x1ff] != 0xaa ) )\r
+    {\r
+      return F_ERR_NOTFORMATTED;                                                /*??*/\r
+    }\r
+\r
+    if ( ( ptr[0] != 0xeb ) && ( ptr[0] != 0xe9 ) )\r
+    {\r
+      return F_ERR_NOTFORMATTED;                                        /*??*/\r
+    }\r
+  }\r
+\r
+  ptr += 11;\r
+  if ( _f_getword( ptr ) != F_SECTOR_SIZE )\r
+  {\r
+    return F_ERR_NOTSUPPSECTORSIZE;\r
+  }\r
+\r
+  ptr += 2;\r
+  gl_volume.bootrecord.sector_per_cluster = *ptr++;\r
+  gl_volume.firstfat.sector = _f_getword( ptr );\r
+  ptr += 2;\r
+  gl_volume.bootrecord.number_of_FATs = *ptr++;\r
+  gl_volume.root.num = _f_getword( ptr );\r
+  ptr += 2;\r
+  gl_volume.root.num *= sizeof( F_DIRENTRY );\r
+  gl_volume.root.num /= F_SECTOR_SIZE;\r
+  maxcluster = _f_getword( ptr );\r
+  ptr += 2;\r
+  gl_volume.bootrecord.media_descriptor = *ptr++;\r
+  gl_volume.firstfat.num = _f_getword( ptr );\r
+  ptr += 6;\r
+  _n = _f_getlong( ptr );\r
+  ptr += 4;\r
+  if ( _n < first_sector )\r
+  {\r
+    _n = first_sector;\r
+  }\r
+\r
+  gl_volume.firstfat.sector += _n;\r
+  if ( !maxcluster )\r
+  {\r
+    maxcluster = _f_getlong( ptr );\r
+  }\r
+\r
+  ptr += 4;\r
+\r
+\r
+  if ( gl_volume.firstfat.num )\r
+  {\r
+    gl_volume.root.sector = gl_volume.firstfat.sector + ( gl_volume.firstfat.num * gl_volume.bootrecord.number_of_FATs );\r
+    gl_volume._tdata.sector = gl_volume.root.sector + gl_volume.root.num;\r
+    gl_volume._tdata.num = 0;\r
+    ptr += 3;\r
+  }\r
+  else\r
+  {\r
+    gl_volume.firstfat.num = _f_getlong( ptr );\r
+    ptr += 8;\r
+    gl_volume._tdata.sector = gl_volume.firstfat.sector;\r
+    gl_volume._tdata.sector += gl_volume.firstfat.num * gl_volume.bootrecord.number_of_FATs;\r
+    gl_volume._tdata.num = 0;\r
+    gl_volume.bootrecord.rootcluster = _f_getlong( ptr );\r
+    ptr += 23;\r
+    gl_volume.root.num = gl_volume.bootrecord.sector_per_cluster;\r
+    gl_volume.root.sector = ( ( gl_volume.bootrecord.rootcluster - 2 ) * gl_volume.root.num ) + gl_volume._tdata.sector;\r
+  }\r
+\r
+  gl_volume.bootrecord.serial_number = _f_getlong( ptr );\r
+\r
+  maxcluster -= gl_volume._tdata.sector;\r
+  maxcluster += _n;\r
+  gl_volume.maxcluster = maxcluster / gl_volume.bootrecord.sector_per_cluster;\r
+\r
+  if ( gl_volume.maxcluster < ( F_CLUSTER_RESERVED & 0xfff ) )\r
+  {\r
+    gl_volume.mediatype = F_FAT12_MEDIA;\r
+  }\r
+  else if ( gl_volume.maxcluster < ( F_CLUSTER_RESERVED & 0xffff ) )\r
+  {\r
+    gl_volume.mediatype = F_FAT16_MEDIA;\r
+  }\r
+  else\r
+  {\r
+    gl_volume.mediatype = F_FAT32_MEDIA;\r
+  }\r
+\r
+  if ( gl_volume.bootrecord.media_descriptor != 0xf8 )    /*fixdrive*/\r
+  {\r
+    if ( gl_volume.bootrecord.media_descriptor != 0xf0 )  /*removable*/\r
+    {\r
+      return F_ERR_NOTFORMATTED;      /*??*/\r
+    }\r
+  }\r
+\r
+  return F_NO_ERROR;\r
+} /* _f_readbootrecord */\r
+\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * _f_getvolume\r
+ *\r
+ * getting back a volume info structure of a given drive, it try to mounts\r
+ * drive if it was not mounted before\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+unsigned char _f_getvolume ( void )\r
+{\r
+  switch ( gl_volume.state )\r
+  {\r
+    case F_STATE_NONE:\r
+      return F_ERR_ONDRIVE;\r
+\r
+    case F_STATE_WORKING:\r
+\r
+      if ( !_f_checkstatus() )\r
+      {\r
+        return F_NO_ERROR;\r
+      }\r
+\r
+    /* here we don't stop case flow,  */\r
+    /* because we have to clean up this volume! */\r
+\r
+    case F_STATE_NEEDMOUNT:\r
+    {\r
+      gl_file.modified = 0;\r
+      gl_volume.modified = 0;\r
+      gl_volume.lastalloccluster = 0;\r
+      gl_volume.actsector = (unsigned long)( -1 );\r
+      gl_volume.fatsector = (unsigned long)( -1 );\r
+\r
+      gl_file.mode = F_FILE_CLOSE;\r
+\r
+      gl_volume.cwd[0] = 0;     /*reset cwd*/\r
+      gl_volume.mediatype = F_UNKNOWN_MEDIA;\r
+\r
+      if ( mdrv->getstatus != NULL )\r
+      {\r
+        if ( mdrv->getstatus( mdrv ) & F_ST_MISSING )\r
+        {\r
+          gl_volume.state = F_STATE_NEEDMOUNT;         /*card missing*/\r
+          return F_ERR_CARDREMOVED;\r
+        }\r
+      }\r
+\r
+      if ( !_f_readbootrecord() )\r
+      {\r
+        gl_volume.state = F_STATE_WORKING;\r
+        return F_NO_ERROR;\r
+      }\r
+\r
+      gl_volume.mediatype = F_UNKNOWN_MEDIA;\r
+      return F_ERR_NOTFORMATTED;\r
+    }\r
+  } /* switch */\r
+\r
+  return F_ERR_ONDRIVE;\r
+} /* _f_getvolume */\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_getfreespace\r
+ *\r
+ * get total/free/used/bad diskspace\r
+ *\r
+ * INPUTS\r
+ * pspace - pointer where to store the information\r
+ *\r
+ * RETURNS\r
+ * error code\r
+ *\r
+ ***************************************************************************/\r
+unsigned char fn_getfreespace ( F_SPACE * pspace )\r
+{\r
+  unsigned char  ret;\r
+  unsigned long  a;\r
+  unsigned long  clustersize;\r
+\r
+  ret = _f_getvolume();\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  psp_memset( pspace, 0, sizeof( F_SPACE ) );\r
+  pspace->total = gl_volume.maxcluster;\r
+\r
+  gl_volume.fatsector = (unsigned long)-1;\r
+  for ( a = 2 ; a < gl_volume.maxcluster + 2 ; a++ )\r
+  {\r
+    unsigned long  value;\r
+\r
+    ret = _f_getclustervalue( a, &value );\r
+    if ( ret )\r
+    {\r
+      return ret;\r
+    }\r
+\r
+    if ( !value )\r
+    {\r
+      ++( pspace->free );\r
+    }\r
+    else if ( value == F_CLUSTER_BAD )\r
+    {\r
+      ++( pspace->bad );\r
+    }\r
+    else\r
+    {\r
+      ++( pspace->used );\r
+    }\r
+  }\r
+\r
+  clustersize = (unsigned long)( gl_volume.bootrecord.sector_per_cluster * F_SECTOR_SIZE );\r
+  for ( a = 0 ; ( clustersize & 1 ) == 0 ; a++ )\r
+  {\r
+    clustersize >>= 1;\r
+  }\r
+\r
+  pspace->total_high = ( pspace->total ) >> ( 32 - a );\r
+  pspace->total <<= a;\r
+  pspace->free_high = ( pspace->free ) >> ( 32 - a );\r
+  pspace->free <<= a;\r
+  pspace->used_high = ( pspace->used ) >> ( 32 - a );\r
+  pspace->used <<= a;\r
+  pspace->bad_high = ( pspace->bad ) >> ( 32 - a );\r
+  pspace->bad <<= a;\r
+\r
+  return F_NO_ERROR;\r
+} /* fn_getfreespace */\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_getserial\r
+ *\r
+ * get serial number\r
+ *\r
+ * INPUTS\r
+ * serial - pointer where to store the serial number\r
+ *\r
+ * RETURNS\r
+ * error code\r
+ *\r
+ ***************************************************************************/\r
+unsigned char fn_getserial ( unsigned long * serial )\r
+{\r
+  unsigned char  ret;\r
+\r
+  ret = _f_getvolume();\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  *serial = gl_volume.bootrecord.serial_number;\r
+  return 0;\r
+}\r
+\r
+/*\r
+** fn_init\r
+**\r
+** Initialize FAT_SL file system\r
+**\r
+** RETURN: F_NO_ERROR on success, other if error.\r
+*/\r
+unsigned char fn_init ( void )\r
+{\r
+  return F_NO_ERROR;\r
+} /* fn_init */\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_initvolume\r
+ *\r
+ * initiate a volume, this function has to be called 1st to set physical\r
+ * driver function to a given volume\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+unsigned char fn_initvolume ( F_DRIVERINIT initfunc )\r
+{\r
+#if F_FS_THREAD_AWARE == 1\r
+  {\r
+    if( fs_lock_semaphore == NULL )\r
+    {\r
+      fs_lock_semaphore = xSemaphoreCreateMutex();\r
+      if( fs_lock_semaphore == NULL )\r
+      {\r
+        return F_ERR_OS;\r
+      }\r
+    }\r
+  }\r
+#endif /* F_FS_THREAD_AWARE */\r
+\r
+  gl_volume.state = F_STATE_NONE;\r
+\r
+  mdrv = initfunc( 0 );\r
+  if ( mdrv == NULL )\r
+  {\r
+    return F_ERR_INITFUNC;\r
+  }\r
+\r
+  gl_volume.state = F_STATE_NEEDMOUNT;\r
+\r
+#if F_FILE_CHANGED_EVENT\r
+  f_filechangedevent = 0;\r
+#endif\r
+\r
+  return _f_getvolume();\r
+} /* fn_initvolume */\r
+\r
+/****************************************************************************\r
+ *\r
+ * fn_delvolume\r
+ *\r
+ ***************************************************************************/\r
+unsigned char fn_delvolume ( void )\r
+{\r
+  if ( mdrv->release )\r
+  {\r
+    (void)mdrv->release( mdrv );\r
+  }\r
+\r
+  return 0;\r
+}\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/volume.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/common/volume.h
new file mode 100644 (file)
index 0000000..e65a44f
--- /dev/null
@@ -0,0 +1,113 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef __VOLUME_H\r
+#define __VOLUME_H\r
+\r
+#include "config_fat_sl.h"\r
+\r
+#include "../../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+#ifdef __cplusplus\r
+extern "C" {\r
+#endif\r
+\r
+\r
+typedef struct\r
+{\r
+  unsigned char  sector_per_cluster;\r
+  unsigned char  number_of_FATs;\r
+  unsigned char  media_descriptor;\r
+  unsigned long  rootcluster;\r
+  unsigned long  sector_per_FAT;\r
+  unsigned long  sector_per_FAT32;\r
+  unsigned long  serial_number;\r
+} F_BOOTRECORD;\r
+\r
+\r
+typedef struct\r
+{\r
+  unsigned long  sector; /*start sector*/\r
+  unsigned long  num;    /*number of sectors*/\r
+} F_SECTOR;\r
+\r
+\r
+typedef struct\r
+{\r
+  unsigned char  state;\r
+  F_BOOTRECORD   bootrecord;\r
+  F_SECTOR       firstfat;\r
+  F_SECTOR       root;\r
+  F_SECTOR       _tdata;\r
+\r
+  unsigned long  actsector;\r
+  unsigned long  fatsector;\r
+\r
+  unsigned long  lastalloccluster;\r
+  unsigned char  modified;\r
+  char           cwd[F_MAXPATH]; /*current working folder in this volume*/\r
+  unsigned char  mediatype;\r
+  unsigned long  maxcluster;\r
+} F_VOLUME;\r
+\r
+\r
+enum\r
+{\r
+/*  0 */\r
+  F_STATE_NONE,\r
+\r
+/*  1 */ F_STATE_NEEDMOUNT,\r
+\r
+/*  2 */ F_STATE_WORKING\r
+};\r
+\r
+\r
+extern F_VOLUME  gl_volume;\r
+extern F_FILE    gl_file;\r
+extern char      gl_sector[F_SECTOR_SIZE]; /* actual sector */\r
+\r
+unsigned char _f_getvolume ( void );\r
+\r
+#ifdef __cplusplus\r
+}\r
+#endif\r
+\r
+#endif /* ifndef __VOLUME_H */\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/test/test.c b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/test/test.c
new file mode 100644 (file)
index 0000000..ef67ad0
--- /dev/null
@@ -0,0 +1,2752 @@
+#ifndef _TEST_C_\r
+#define _TEST_C_\r
+\r
+\r
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#include "test.h"\r
+#include "../../api/fat_sl.h"\r
+#include "../../psp/target/fat_sl/psp_test.h"\r
+\r
+#include "../../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+static char  cwd[F_MAXPATH];\r
+\r
+static F_FIND  find;\r
+\r
+static void _f_deleteall ( void )\r
+{\r
+  F_FIND         f2;\r
+  unsigned char  sd = 0, rc, fl = 0;\r
+\r
+  f2 = find;\r
+  do\r
+  {\r
+    rc = f_findfirst( "*.*", &find );\r
+    while ( rc == 0 && find.filename[0] == '.' )\r
+    {\r
+      rc = f_findnext( &find );\r
+    }\r
+\r
+    if ( rc == 0 )\r
+    {\r
+      if ( find.attr & F_ATTR_DIR )\r
+      {\r
+        ++sd;\r
+        fl = 1;\r
+        f2 = find;\r
+        (void)f_chdir( find.filename );\r
+        continue;\r
+      }\r
+      else\r
+      {\r
+        (void)f_delete( find.filename );\r
+        rc = f_findnext( &find );\r
+      }\r
+    }\r
+\r
+    if ( rc && sd && fl )\r
+    {\r
+      (void)f_chdir( ".." );\r
+      --sd;\r
+      fl = 0;\r
+      find = f2;\r
+      (void)f_rmdir( find.filename );\r
+      rc = f_findnext( &find );\r
+    }\r
+\r
+    if ( rc && sd && !fl )\r
+    {\r
+      (void)f_chdir( "/" );\r
+      sd = 0;\r
+      rc = 0;\r
+    }\r
+  }\r
+  while ( rc == 0 );\r
+} /* _f_deleteall */\r
+\r
+char  stmp[20];\r
+static char * f_nameconv ( char * s )\r
+{\r
+  char * ss = stmp;\r
+\r
+  for ( ; ; )\r
+  {\r
+    char  ch = *s++;\r
+    if ( ( ch >= 'a' ) && ( ch <= 'z' ) )\r
+    {\r
+      ch += 'A' - 'a';\r
+    }\r
+\r
+    *ss++ = ch;\r
+    if ( !ch )\r
+    {\r
+      break;\r
+    }\r
+  }\r
+\r
+  return stmp;\r
+} /* f_nameconv */\r
+\r
+static unsigned char f_formatting ( void )\r
+{\r
+  unsigned char  ret;\r
+\r
+  _f_dump( "f_formatting" );\r
+\r
+/*checking formatting*/\r
+  ret = f_format( F_FAT_TYPE );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 0, ret );\r
+  }\r
+\r
+  ret = _f_poweron();\r
+  if ( ret )\r
+  {\r
+    return _f_result( 1, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "*.*", &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 2, ret );\r
+  }\r
+\r
+  _f_dump( "passed..." );\r
+  return 0;\r
+} /* f_formatting */\r
+\r
+static unsigned char _f_checkcwd ( char * orig )\r
+{\r
+  unsigned char  ret;\r
+\r
+  ret = f_getcwd( cwd, F_MAXPATH );\r
+  if ( ret )\r
+  {\r
+    return ret;\r
+  }\r
+\r
+  if ( strcmp( orig, cwd ) )\r
+  {\r
+    return (unsigned char)-1;\r
+  }\r
+\r
+  return 0;\r
+}\r
+\r
+static unsigned char f_dirtest ( void )\r
+{\r
+  unsigned char  ret;\r
+\r
+  _f_dump( "f_dirtest" );\r
+\r
+  _f_deleteall();\r
+\r
+/*creates a ab abc abcd*/\r
+  ret = f_mkdir( "a" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 1, ret );\r
+  }\r
+\r
+  ret = f_mkdir( "ab" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 2, ret );\r
+  }\r
+\r
+  ret = f_mkdir( "abc" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 3, ret );\r
+  }\r
+\r
+  ret = f_mkdir( "abca" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 4, ret );\r
+  }\r
+\r
+/*creates directories in /a  -  a ab abc abcd*/\r
+  ret = f_mkdir( "a/a" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 5, ret );\r
+  }\r
+\r
+  ret = f_mkdir( "a/ab" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 6, ret );\r
+  }\r
+\r
+  ret = f_mkdir( "a/abc" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 7, ret );\r
+  }\r
+\r
+  ret = f_mkdir( "a/abcd" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 8, ret );\r
+  }\r
+\r
+/*change into a/abcd and check cwd*/\r
+  ret = f_chdir( "a/abcd" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 9, ret );\r
+  }\r
+\r
+  ret = _f_checkcwd( f_nameconv( "/a/abcd" ) );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 10, ret );\r
+  }\r
+\r
+/*make directory t change into t and check cwd="a/abcd/t"*/\r
+  ret = f_mkdir( "t" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 11, ret );\r
+  }\r
+\r
+  ret = f_chdir( "t" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 12, ret );\r
+  }\r
+\r
+  ret = _f_checkcwd( f_nameconv( "/a/abcd/t" ) );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 13, ret );\r
+  }\r
+\r
+  ret = f_chdir( "." );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 14, ret );\r
+  }\r
+\r
+  ret = _f_checkcwd( f_nameconv( "/a/abcd/t" ) );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 15, ret );\r
+  }\r
+\r
+  ret = f_chdir( "../." );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 16, ret );\r
+  }\r
+\r
+  ret = _f_checkcwd( f_nameconv( "/a/abcd" ) );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 17, ret );\r
+  }\r
+\r
+/*removing t dir*/\r
+  ret = f_rmdir( "t" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 18, ret );\r
+  }\r
+\r
+  ret = f_chdir( "t" );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 19, ret );\r
+  }\r
+\r
+/*removing /a dir*/\r
+  ret = f_rmdir( "/ab" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 20, ret );\r
+  }\r
+\r
+  ret = f_chdir( "/ab" );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 21, ret );\r
+  }\r
+\r
+/*removing /a dir*/\r
+  ret = f_rmdir( "../../a" );\r
+  if ( ret != F_ERR_NOTEMPTY )\r
+  {\r
+    return _f_result( 22, ret );\r
+  }\r
+\r
+/*removing /abca dir*/\r
+  ret = f_rmdir( "a:/abca" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 24, ret );\r
+  }\r
+\r
+/*changing invalid dirs*/\r
+  ret = f_chdir( "" );\r
+  if ( ret != F_ERR_INVALIDNAME )\r
+  {\r
+    return _f_result( 25, ret );\r
+  }\r
+\r
+  ret = f_chdir( " " );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 26, ret );\r
+  }\r
+\r
+  ret = _f_checkcwd( f_nameconv( "/a/abcd" ) );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 27, ret );\r
+  }\r
+\r
+  ret = f_chdir( "?" );\r
+  if ( ret != F_ERR_INVALIDNAME )\r
+  {\r
+    return _f_result( 28, ret );\r
+  }\r
+\r
+  ret = f_chdir( "*.*" );\r
+  if ( ret != F_ERR_INVALIDNAME )\r
+  {\r
+    return _f_result( 29, ret );\r
+  }\r
+\r
+  ret = _f_checkcwd( f_nameconv( "/a/abcd" ) );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 30, ret );\r
+  }\r
+\r
+/*changing into /abc and removes subfolder from /a/ */\r
+  ret = f_chdir( "/abc" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 31, ret );\r
+  }\r
+\r
+  ret = f_rmdir( "/a/a" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 32, ret );\r
+  }\r
+\r
+  ret = f_rmdir( "A:../a/ab" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 33, ret );\r
+  }\r
+\r
+  ret = f_rmdir( "A:/a/abc" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 34, ret );\r
+  }\r
+\r
+  ret = f_rmdir( ".././abc/.././a/../a/abcd" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 35, ret );\r
+  }\r
+\r
+/*some invalid rmdir*/\r
+  ret = f_rmdir( "." );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 36, ret );\r
+  }\r
+\r
+  ret = f_rmdir( ".." );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 37, ret );\r
+  }\r
+\r
+/*create again abc remove abc*/\r
+  ret = f_mkdir( ".././abc" );\r
+  if ( ret != F_ERR_DUPLICATED )\r
+  {\r
+    return _f_result( 38, ret );\r
+  }\r
+\r
+  ret = f_rmdir( "../abc" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 39, ret );\r
+  }\r
+\r
+  ret = f_mkdir( ".././abc" );\r
+  if ( ret != F_ERR_INVALIDDIR )\r
+  {\r
+    return _f_result( 40, ret );                         /*cwd is not exist*/\r
+  }\r
+\r
+  ret = f_chdir( "/" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 41, ret );\r
+  }\r
+\r
+/*try . and .. in the root*/\r
+  ret = f_chdir( "." );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 42, ret );\r
+  }\r
+\r
+  ret = f_chdir( "./././." );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 43, ret );\r
+  }\r
+\r
+  ret = f_chdir( ".." );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 44, ret );\r
+  }\r
+\r
+  ret = _f_checkcwd( "/" ); /*root!*/\r
+  if ( ret )\r
+  {\r
+    return _f_result( 45, ret );\r
+  }\r
+\r
+/*test . and .. in a and remove a*/\r
+  ret = f_chdir( "a" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 46, ret );\r
+  }\r
+\r
+  ret = f_chdir( ".." );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 47, ret );\r
+  }\r
+\r
+  ret = f_chdir( "a" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 48, ret );\r
+  }\r
+\r
+  ret = f_chdir( "." );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 49, ret );\r
+  }\r
+\r
+  ret = f_chdir( "a" );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 50, ret );\r
+  }\r
+\r
+  ret = f_chdir( "./.." );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 51, ret );\r
+  }\r
+\r
+  ret = f_rmdir( "a" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 52, ret );\r
+  }\r
+\r
+/*check if all are removed*/\r
+  ret = f_findfirst( "*.*", &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 53, ret );\r
+  }\r
+\r
+  _f_dump( "passed..." );\r
+  return 0;\r
+} /* f_dirtest */\r
+\r
+\r
+static unsigned char f_findingtest ( void )\r
+{\r
+  unsigned char  ret;\r
+\r
+  _f_dump( "f_findingtest" );\r
+\r
+  _f_deleteall();\r
+\r
+/*check empty*/\r
+  ret = f_findfirst( "*.*", &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 0, ret );\r
+  }\r
+\r
+/*create Hello.dir*/\r
+  ret = f_mkdir( "Hello.dir" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 1, ret );\r
+  }\r
+\r
+/*check if it is exist, and only exist*/\r
+  ret = f_findfirst( "*.*", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 2, ret );\r
+  }\r
+\r
+  if ( strcmp( find.filename, f_nameconv( "Hello.dir" ) ) )\r
+  {\r
+    return _f_result( 3, 0 );\r
+  }\r
+\r
+  if ( find.attr != F_ATTR_DIR )\r
+  {\r
+    return _f_result( 4, 0 );\r
+  }\r
+\r
+  ret = f_findnext( &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 5, ret );\r
+  }\r
+\r
+/*check some not founds*/\r
+  ret = f_findfirst( "q*.*", &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 6, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "Hello.", &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 7, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "a/*.*", &find );\r
+  if ( ret != F_ERR_INVALIDDIR )\r
+  {\r
+    return _f_result( 8, ret );\r
+  }\r
+\r
+  ret = f_findfirst( ".", &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 9, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "..", &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 10, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "?e.*", &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 11, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "*.", &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 12, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "*.?", &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 13, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "*.??", &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 14, ret );\r
+  }\r
+\r
+\r
+/*check some founds*/\r
+  ret = f_findfirst( "*.dir", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 15, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "*.d?r", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 16, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "*.d??", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 17, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "*.???", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 18, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "?ello.???", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 19, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "he??o.dir", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 20, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "he?*.dir", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 21, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "HELLO.DIR", &find ); /*no capitals sensitivity in find!!*/\r
+  if ( ret )\r
+  {\r
+    return _f_result( 22, ret );\r
+  }\r
+\r
+/*change into hello.dir*/\r
+  ret = f_chdir( "hello.dir" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 23, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "*.*", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 24, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "..", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 25, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "??", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 26, ret );\r
+  }\r
+\r
+  ret = f_findfirst( ".", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 27, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "k*.*", &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 28, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "*.", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 29, ret );\r
+  }\r
+\r
+  if ( strcmp( find.filename, "." ) )\r
+  {\r
+    return _f_result( 29, 0 );\r
+  }\r
+\r
+  ret = f_findnext( &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 29, ret );\r
+  }\r
+\r
+  if ( strcmp( find.filename, ".." ) )\r
+  {\r
+    return _f_result( 29, 0 );\r
+  }\r
+\r
+  ret = f_findnext( &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 29, ret );\r
+  }\r
+\r
+\r
+  ret = f_findfirst( "*.a", &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 30, ret );\r
+  }\r
+\r
+/*creating testdir and find it*/\r
+  ret = f_mkdir( "testdir" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 31, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "*.", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 32, ret );\r
+  }\r
+\r
+  if ( strcmp( find.filename, "." ) )\r
+  {\r
+    return _f_result( 32, 0 );\r
+  }\r
+\r
+  ret = f_findnext( &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 32, ret );\r
+  }\r
+\r
+  if ( strcmp( find.filename, ".." ) )\r
+  {\r
+    return _f_result( 32, 0 );\r
+  }\r
+\r
+  ret = f_findnext( &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 32, ret );\r
+  }\r
+\r
+\r
+  if ( strcmp( find.filename, f_nameconv( "testdir" ) ) )\r
+  {\r
+    return _f_result( 33, 0 );\r
+  }\r
+\r
+  ret = f_findfirst( "*.*", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 34, ret );\r
+  }\r
+\r
+  if ( strcmp( find.filename, "." ) )\r
+  {\r
+    return _f_result( 35, 0 );\r
+  }\r
+\r
+  ret = f_findnext( &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 35, ret );\r
+  }\r
+\r
+  if ( strcmp( find.filename, ".." ) )\r
+  {\r
+    return _f_result( 35, 0 );\r
+  }\r
+\r
+  ret = f_findnext( &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 36, ret );\r
+  }\r
+\r
+  if ( strcmp( find.filename, f_nameconv( "testdir" ) ) )\r
+  {\r
+    return _f_result( 37, 0 );\r
+  }\r
+\r
+  ret = f_findnext( &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 38, ret );\r
+  }\r
+\r
+/*search exact file*/\r
+  ret = f_findfirst( "testDir", &find ); /*no capitals!*/\r
+  if ( ret )\r
+  {\r
+    return _f_result( 39, ret );\r
+  }\r
+\r
+  if ( strcmp( find.filename, f_nameconv( "testdir" ) ) )\r
+  {\r
+    return _f_result( 40, 0 );\r
+  }\r
+\r
+  ret = f_findnext( &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 41, ret );\r
+  }\r
+\r
+\r
+/*go back to root and remove dirs*/\r
+  ret = f_chdir( "\\" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 42, ret );\r
+  }\r
+\r
+  ret = f_rmdir( "Hello.dir/testdir" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 43, ret );\r
+  }\r
+\r
+  ret = f_rmdir( "Hello.dir" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 44, ret );\r
+  }\r
+\r
+/*check if all are removed*/\r
+  ret = f_findfirst( "*.*", &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 45, ret );\r
+  }\r
+\r
+  _f_dump( "passed..." );\r
+  return 0;\r
+} /* f_findingtest */\r
+\r
+static unsigned char f_powerfail ( void )\r
+{\r
+  unsigned char  ret;\r
+\r
+  _f_dump( "f_powerfail" );\r
+\r
+/*checking if its power fail system (RAMDRIVE is not powerfail!)*/\r
+  ret = f_mkdir( "testdir" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 0, ret );\r
+  }\r
+\r
+  ret = _f_poweron();\r
+  if ( ret )\r
+  {\r
+    return _f_result( 1, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "testdir", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 2, ret );\r
+  }\r
+\r
+/*checking formatting*/\r
+  ret = f_format( F_FAT_TYPE );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 3, ret );\r
+  }\r
+\r
+  ret = _f_poweron();\r
+  if ( ret )\r
+  {\r
+    return _f_result( 4, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "*.*", &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 5, ret );\r
+  }\r
+\r
+/*checking formatting, 1st creating*/\r
+  ret = f_format( F_FAT_TYPE );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 6, ret );\r
+  }\r
+\r
+  ret = f_mkdir( "testdir" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 7, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "testdir", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 8, ret );\r
+  }\r
+\r
+  if ( strcmp( find.filename, f_nameconv( "testdir" ) ) )\r
+  {\r
+    return _f_result( 9, 0 );\r
+  }\r
+\r
+  ret = _f_poweron();\r
+  if ( ret )\r
+  {\r
+    return _f_result( 10, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "*.*", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 11, ret );\r
+  }\r
+\r
+  if ( strcmp( find.filename, f_nameconv( "testdir" ) ) )\r
+  {\r
+    return _f_result( 12, 0 );\r
+  }\r
+\r
+/*checking formatting, 2nd creating*/\r
+  ret = f_format( F_FAT_TYPE );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 13, ret );\r
+  }\r
+\r
+  ret = f_mkdir( "testdir" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 14, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "testdir", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 15, ret );\r
+  }\r
+\r
+  if ( strcmp( find.filename, f_nameconv( "testdir" ) ) )\r
+  {\r
+    return _f_result( 16, 0 );\r
+  }\r
+\r
+  ret = f_mkdir( "testdir2" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 17, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "testdir2", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 18, ret );\r
+  }\r
+\r
+  if ( strcmp( find.filename, f_nameconv( "testdir2" ) ) )\r
+  {\r
+    return _f_result( 19, 0 );\r
+  }\r
+\r
+  ret = _f_poweron();\r
+  if ( ret )\r
+  {\r
+    return _f_result( 20, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "*.*", &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 21, ret );\r
+  }\r
+\r
+  if ( strcmp( find.filename, f_nameconv( "testdir" ) ) )\r
+  {\r
+    return _f_result( 22, 0 );\r
+  }\r
+\r
+  ret = f_findnext( &find );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 23, ret );\r
+  }\r
+\r
+  if ( strcmp( find.filename, f_nameconv( "testdir2" ) ) )\r
+  {\r
+    return _f_result( 24, 0 );\r
+  }\r
+\r
+  ret = f_findnext( &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 25, ret );\r
+  }\r
+\r
+\r
+/*checking empty*/\r
+  ret = _f_poweron();\r
+  if ( ret )\r
+  {\r
+    return _f_result( 26, ret );\r
+  }\r
+\r
+  ret = f_format( F_FAT_TYPE );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 27, ret );\r
+  }\r
+\r
+  ret = _f_poweron();\r
+  if ( ret )\r
+  {\r
+    return _f_result( 28, ret );\r
+  }\r
+\r
+  ret = f_findfirst( "*.*", &find );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 29, ret );\r
+  }\r
+\r
+\r
+  _f_dump( "passed..." );\r
+  return 0;\r
+} /* f_powerfail */\r
+\r
+\r
+char  testbuffer[F_MAX_SEEK_TEST + 16]; /* +16 for f_appending test */\r
+\r
+static unsigned char checkfilecontent ( long nums, unsigned char value, F_FILE * file )\r
+{\r
+  unsigned char  ch;\r
+\r
+  while ( nums-- )\r
+  {\r
+    if ( f_eof( file ) )\r
+    {\r
+      return 1;                    /*eof ?*/\r
+    }\r
+\r
+    if ( 1 != f_read( &ch, 1, 1, file ) )\r
+    {\r
+      return 1;\r
+    }\r
+\r
+    if ( ch != value )\r
+    {\r
+      return 1;\r
+    }\r
+  }\r
+\r
+  return 0;\r
+} /* checkfilecontent */\r
+\r
+static unsigned char f_seeking ( int sectorsize )\r
+{\r
+  F_FILE       * file;\r
+  unsigned char  ret;\r
+  unsigned long  size;\r
+  unsigned long  pos;\r
+\r
+  if ( sectorsize == 128 )\r
+  {\r
+    _f_dump( "f_seeking with 128" );\r
+  }\r
+\r
+  #if ( F_MAX_SEEK_TEST > 128 )\r
+  else if ( sectorsize == 256 )\r
+  {\r
+    _f_dump( "f_seeking with 256" );\r
+  }\r
+  #endif\r
+  #if ( F_MAX_SEEK_TEST > 256 )\r
+  else if ( sectorsize == 512 )\r
+  {\r
+    _f_dump( "f_seeking with 512" );\r
+  }\r
+  #endif\r
+  #if ( F_MAX_SEEK_TEST > 512 )\r
+  else if ( sectorsize == 1024 )\r
+  {\r
+    _f_dump( "f_seeking with 1024" );\r
+  }\r
+  #endif\r
+  #if ( F_MAX_SEEK_TEST > 1024 )\r
+  else if ( sectorsize == 2048 )\r
+  {\r
+    _f_dump( "f_seeking with 2048" );\r
+  }\r
+  #endif\r
+  #if ( F_MAX_SEEK_TEST > 2048 )\r
+  else if ( sectorsize == 4096 )\r
+  {\r
+    _f_dump( "f_seeking with 4096" );\r
+  }\r
+  #endif\r
+  #if ( F_MAX_SEEK_TEST > 4096 )\r
+  else if ( sectorsize == 8192 )\r
+  {\r
+    _f_dump( "f_seeking with 8192" );\r
+  }\r
+  #endif\r
+  #if ( F_MAX_SEEK_TEST > 8192 )\r
+  else if ( sectorsize == 16384 )\r
+  {\r
+    _f_dump( "f_seeking with 16384" );\r
+  }\r
+  #endif\r
+  #if ( F_MAX_SEEK_TEST > 16384 )\r
+  else if ( sectorsize == 32768 )\r
+  {\r
+    _f_dump( "f_seeking with 32768" );\r
+  }\r
+  #endif\r
+  else\r
+  {\r
+    _f_dump( "f_seeking with random" );\r
+  }\r
+\r
+/*checking sector boundary seekeng*/\r
+  file = f_open( "test.bin", "w+" );\r
+  if ( !file )\r
+  {\r
+    return _f_result( 0, 0 );\r
+  }\r
+\r
+/*write sectorsize times 0*/\r
+  psp_memset( testbuffer, 0, sectorsize );\r
+  size = (unsigned long)f_write( testbuffer, 1, (long)sectorsize, file );\r
+  if ( size != (unsigned long) sectorsize )\r
+  {\r
+    return _f_result( 1, size );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos != (unsigned long) sectorsize )\r
+  {\r
+    return _f_result( 2, pos );\r
+  }\r
+\r
+/*seek back and read some*/\r
+  ret = f_seek( file, 0, F_SEEK_SET ); /*seek back*/\r
+  if ( ret )\r
+  {\r
+    return _f_result( 3, ret );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos )\r
+  {\r
+    return _f_result( 4, pos );\r
+  }\r
+\r
+  size = (unsigned long)f_read( testbuffer, 1, sectorsize, file );\r
+  if ( size != (unsigned long) sectorsize )\r
+  {\r
+    return _f_result( 5, size );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos != (unsigned long) sectorsize )\r
+  {\r
+    return _f_result( 6, pos );\r
+  }\r
+\r
+/*fake read at eof*/\r
+  size = (unsigned long)f_read( testbuffer, 1, 2, file ); /*eof!*/\r
+  if ( size != 0 )\r
+  {\r
+    return _f_result( 7, size );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos != (unsigned long) sectorsize )\r
+  {\r
+    return _f_result( 8, pos );\r
+  }\r
+\r
+/*writing sectorsize times 1 at the end*/\r
+  psp_memset( testbuffer, 1, sectorsize );\r
+  size = (unsigned long)f_write( testbuffer, 1, sectorsize, file );\r
+  if ( size != (unsigned long) sectorsize )\r
+  {\r
+    return _f_result( 11, size );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos != (unsigned long) ( sectorsize * 2 ) )\r
+  {\r
+    return _f_result( 12, pos );\r
+  }\r
+\r
+/*seeking back and read 1byte less*/\r
+  ret = f_seek( file, 0, F_SEEK_SET );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 13, ret );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos )\r
+  {\r
+    return _f_result( 14, pos );\r
+  }\r
+\r
+  size = (unsigned long)f_read( testbuffer, 1, sectorsize - 1, file );\r
+  if ( size != (unsigned long) ( sectorsize - 1 ) )\r
+  {\r
+    return _f_result( 15, size );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos != (unsigned long) ( sectorsize - 1 ) )\r
+  {\r
+    return _f_result( 16, pos );\r
+  }\r
+\r
+\r
+/*write 2 times 2*/\r
+  psp_memset( testbuffer, 2, sectorsize );\r
+  size = (unsigned long)f_write( testbuffer, 1, 2, file );\r
+  if ( size != 2 )\r
+  {\r
+    return _f_result( 17, size );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos != (unsigned long) ( sectorsize + 1 ) )\r
+  {\r
+    return _f_result( 18, pos );\r
+  }\r
+\r
+/*read 2 bytes*/\r
+  size = (unsigned long)f_read( testbuffer, 2, 1, file );\r
+  if ( size != 1 )\r
+  {\r
+    return _f_result( 19, size );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos != (unsigned long) ( sectorsize + 3 ) )\r
+  {\r
+    return _f_result( 20, pos );\r
+  }\r
+\r
+\r
+/*write 4 times 3*/\r
+  psp_memset( testbuffer, 3, sectorsize );\r
+  size = (unsigned long)f_write( testbuffer, 1, 4, file );\r
+  if ( size != 4 )\r
+  {\r
+    return _f_result( 21, size );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos != (unsigned long) ( sectorsize + 3 + 4 ) )\r
+  {\r
+    return _f_result( 22, pos );\r
+  }\r
+\r
+/*seek at 2*/\r
+  ret = f_seek( file, 2, F_SEEK_SET );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 23, ret );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos != 2 )\r
+  {\r
+    return _f_result( 24, pos );\r
+  }\r
+\r
+/*write 6 times 4*/\r
+  psp_memset( testbuffer, 4, sectorsize );\r
+  size = (unsigned long)f_write( testbuffer, 1, 6, file );\r
+  if ( size != 6 )\r
+  {\r
+    return _f_result( 25, size );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos != 8 )\r
+  {\r
+    return _f_result( 26, pos );\r
+  }\r
+\r
+/*seek end -4*/\r
+  ret = f_seek( file, -4, F_SEEK_END );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 27, ret );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos != (unsigned long) ( 2 * sectorsize - 4 ) )\r
+  {\r
+    return _f_result( 28, pos );\r
+  }\r
+\r
+/*read 2 bytes*/\r
+  size = (unsigned long)f_read( testbuffer, 1, 2, file );\r
+  if ( size != 2 )\r
+  {\r
+    return _f_result( 29, size );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos != (unsigned long) ( 2 * sectorsize - 2 ) )\r
+  {\r
+    return _f_result( 30, pos );\r
+  }\r
+\r
+/*write 8 times 5*/\r
+  psp_memset( testbuffer, 5, sectorsize );\r
+  size = (unsigned long)f_write( testbuffer, 1, 8, file );\r
+  if ( size != 8 )\r
+  {\r
+    return _f_result( 31, size );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos != (unsigned long) ( 2 * sectorsize + 6 ) )\r
+  {\r
+    return _f_result( 32, pos );\r
+  }\r
+\r
+/*seek to the begining*/\r
+  ret = f_seek( file, 0, F_SEEK_SET );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 33, ret );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos )\r
+  {\r
+    return _f_result( 34, pos );\r
+  }\r
+\r
+/*seek to the end*/\r
+  ret = f_seek( file, 2 * sectorsize + 6, F_SEEK_SET );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 35, ret );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos != (unsigned long) ( 2 * sectorsize + 6 ) )\r
+  {\r
+    return _f_result( 36, pos );\r
+  }\r
+\r
+/*write 2 times 6*/\r
+  psp_memset( testbuffer, 6, sectorsize );\r
+  size = (unsigned long)f_write( testbuffer, 1, 2, file );\r
+  if ( size != 2 )\r
+  {\r
+    return _f_result( 37, size );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos != (unsigned long) ( 2 * sectorsize + 8 ) )\r
+  {\r
+    return _f_result( 38, pos );\r
+  }\r
+\r
+/*seek to the begining*/\r
+  (void)f_seek( file, -( 2 * sectorsize + 8 ), F_SEEK_CUR );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 39, ret );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos )\r
+  {\r
+    return _f_result( 40, pos );\r
+  }\r
+\r
+/*read 2 times sector*/\r
+  size = (unsigned long)f_read( testbuffer, 1, sectorsize, file );\r
+  if ( size != (unsigned long) sectorsize )\r
+  {\r
+    return _f_result( 41, size );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos != (unsigned long) sectorsize )\r
+  {\r
+    return _f_result( 42, pos );\r
+  }\r
+\r
+  size = (unsigned long)f_read( testbuffer, 1, sectorsize, file );\r
+  if ( size != (unsigned long) sectorsize )\r
+  {\r
+    return _f_result( 43, size );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos != (unsigned long) ( 2 * sectorsize ) )\r
+  {\r
+    return _f_result( 44, pos );\r
+  }\r
+\r
+/*write 1 once 7*/\r
+  psp_memset( testbuffer, 7, sectorsize );\r
+  size = (unsigned long)f_write( testbuffer, 1, 1, file );\r
+  if ( size != 1 )\r
+  {\r
+    return _f_result( 45, size );\r
+  }\r
+\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos != (unsigned long) ( 2 * sectorsize + 1 ) )\r
+  {\r
+    return _f_result( 46, pos );\r
+  }\r
+\r
+/*close it*/\r
+  ret = f_close( file );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 47, ret );\r
+  }\r
+\r
+\r
+/*check the result*/\r
+  size = (unsigned long)f_filelength( "test.bin" );\r
+  if ( size != (unsigned long) ( 2 * sectorsize + 8 ) )\r
+  {\r
+    return _f_result( 48, size );\r
+  }\r
+\r
+/*opens it*/\r
+  file = f_open( "test.bin", "r" );\r
+  if ( !file )\r
+  {\r
+    return _f_result( 49, size );\r
+  }\r
+\r
+  if ( checkfilecontent( 2, 0, file ) )\r
+  {\r
+    return _f_result( 50, 0 );\r
+  }\r
+\r
+  if ( checkfilecontent( 6, 4, file ) )\r
+  {\r
+    return _f_result( 51, 0 );\r
+  }\r
+\r
+  if ( checkfilecontent( sectorsize - 8 - 1, 0, file ) )\r
+  {\r
+    return _f_result( 52, 0 );\r
+  }\r
+\r
+  if ( checkfilecontent( 2, 2, file ) )\r
+  {\r
+    return _f_result( 53, 0 );\r
+  }\r
+\r
+  if ( checkfilecontent( 2, 1, file ) )\r
+  {\r
+    return _f_result( 54, 0 );\r
+  }\r
+\r
+  if ( checkfilecontent( 4, 3, file ) )\r
+  {\r
+    return _f_result( 55, 0 );\r
+  }\r
+\r
+  if ( checkfilecontent( sectorsize - 7 - 2, 1, file ) )\r
+  {\r
+    return _f_result( 56, 0 );\r
+  }\r
+\r
+  if ( checkfilecontent( 2, 5, file ) )\r
+  {\r
+    return _f_result( 57, 0 );\r
+  }\r
+\r
+  if ( checkfilecontent( 1, 7, file ) )\r
+  {\r
+    return _f_result( 58, 0 );\r
+  }\r
+\r
+  if ( checkfilecontent( 5, 5, file ) )\r
+  {\r
+    return _f_result( 59, 0 );\r
+  }\r
+\r
+  if ( checkfilecontent( 2, 6, file ) )\r
+  {\r
+    return _f_result( 60, 0 );\r
+  }\r
+\r
+/*check pos result*/\r
+  pos = (unsigned long)f_tell( file );\r
+  if ( pos != (unsigned long) ( 2 * sectorsize + 8 ) )\r
+  {\r
+    return _f_result( 61, pos );\r
+  }\r
+\r
+/*this has to be eof*/\r
+  pos = f_eof( file );\r
+  if ( !pos )\r
+  {\r
+    return _f_result( 62, pos );\r
+  }\r
+\r
+/*close it*/\r
+  ret = f_close( file );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 63, ret );\r
+  }\r
+\r
+/*deletes it*/\r
+  ret = f_delete( "test.bin" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 64, ret );\r
+  }\r
+\r
+  _f_dump( "passed..." );\r
+  return 0;\r
+} /* f_seeking */\r
+\r
+static unsigned char f_opening ( void )\r
+{\r
+  F_FILE        * file;\r
+  F_FILE        * file2;\r
+  unsigned char   ret;\r
+  unsigned short  size, pos;\r
+\r
+  _f_dump( "f_opening" );\r
+\r
+/*test non existing file open r, r+*/\r
+  file = f_open( "file.bin", "r" );\r
+  if ( file )\r
+  {\r
+    return _f_result( 0, 0 );\r
+  }\r
+\r
+  file = f_open( "file.bin", "r+" );\r
+  if ( file )\r
+  {\r
+    return _f_result( 1, 0 );\r
+  }\r
+\r
+/*test non existing appends    "a" a+*/\r
+  file = f_open( "file.bin", "a" );\r
+  if ( !file )\r
+  {\r
+    return _f_result( 2, 0 );\r
+  }\r
+\r
+  file2 = f_open( "file.bin", "a+" ); /*open again*/\r
+  if ( file2 )\r
+  {\r
+    return _f_result( 3, 0 );\r
+  }\r
+\r
+  ret = f_close( file );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 3, 1 );\r
+  }\r
+\r
+  ret = f_close( file2 );\r
+  if ( ret != F_ERR_NOTOPEN )\r
+  {\r
+    return _f_result( 3, 2 );\r
+  }\r
+\r
+\r
+/*try to creates it w*/\r
+  file = f_open( "file.bin", "w" );\r
+  if ( !file )\r
+  {\r
+    return _f_result( 4, 0 );\r
+  }\r
+\r
+/*write 512 times 1*/\r
+  psp_memset( testbuffer, 1, 512 );                           /*set all 1*/\r
+  size = (unsigned short)f_write( testbuffer, 1, 512, file ); /*test write*/\r
+  if ( size != 512 )\r
+  {\r
+    return _f_result( 5, size );\r
+  }\r
+\r
+/*go back, and read it*/\r
+  ret = f_rewind( file ); /*back to the begining*/\r
+  if ( ret )\r
+  {\r
+    return _f_result( 6, ret );       /*it should fail*/\r
+  }\r
+\r
+  size = (unsigned short)f_read( testbuffer, 1, 512, file ); /*test read*/\r
+  if ( size )\r
+  {\r
+    return _f_result( 7, size );        /*it should fail*/\r
+  }\r
+\r
+/*close and check size*/\r
+  size = (unsigned short)f_filelength( "file.bin" );\r
+  if ( size )\r
+  {\r
+    return _f_result( 8, size );        /*has to be zero*/\r
+  }\r
+\r
+  ret = f_close( file );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 9, ret );\r
+  }\r
+\r
+  size = (unsigned short)f_filelength( "file.bin" );\r
+  if ( size != 512 )\r
+  {\r
+    return _f_result( 10, size );\r
+  }\r
+\r
+/*try to owerwrites it it*/\r
+  file = f_open( "file.bin", "w+" );\r
+  if ( !file )\r
+  {\r
+    return _f_result( 11, 0 );\r
+  }\r
+\r
+/*close and check size*/\r
+  size = (unsigned short)f_filelength( "file.bin" );\r
+  if ( size )\r
+  {\r
+    return _f_result( 12, size );        /*has to be zero*/\r
+  }\r
+\r
+  ret = f_close( file );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 13, ret );\r
+  }\r
+\r
+  size = (unsigned short)f_filelength( "file.bin" );\r
+  if ( size )\r
+  {\r
+    return _f_result( 14, size );\r
+  }\r
+\r
+\r
+\r
+/*test non existing appends    "a" */\r
+  file = f_open( "file.bin", "r+" );\r
+  if ( !file )\r
+  {\r
+    return _f_result( 15, 0 );\r
+  }\r
+\r
+/*write 512 times 1*/\r
+  psp_memset( testbuffer, 1, 512 );                           /*set all 1*/\r
+  size = (unsigned short)f_write( testbuffer, 1, 512, file ); /*test write*/\r
+  if ( size != 512 )\r
+  {\r
+    return _f_result( 16, size );\r
+  }\r
+\r
+/*go back, and read it*/\r
+  ret = f_rewind( file );                                    /*back to the begining*/\r
+  size = (unsigned short)f_read( testbuffer, 1, 512, file ); /*test read*/\r
+  if ( size != 512 )\r
+  {\r
+    return _f_result( 17, size );             /*it should fail*/\r
+  }\r
+\r
+  ret = f_rewind( file ); /*back to the begining*/\r
+\r
+/*write 256 times 2*/\r
+  psp_memset( testbuffer, 2, 512 );                           /*set all 2*/\r
+  size = (unsigned short)f_write( testbuffer, 1, 256, file ); /*test write*/\r
+  if ( size != 256 )\r
+  {\r
+    return _f_result( 18, size );\r
+  }\r
+\r
+  pos = (unsigned short)f_tell( file );\r
+  if ( pos != 256 )\r
+  {\r
+    return _f_result( 19, pos );            /*position has to be 512*/\r
+  }\r
+\r
+  size = (unsigned short)f_filelength( "file.bin" );\r
+  if ( size )\r
+  {\r
+    return _f_result( 20, size );        /*has to be zero*/\r
+  }\r
+\r
+/*close and check size*/\r
+  ret = f_close( file );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 21, ret );\r
+  }\r
+\r
+  size = (unsigned short)f_filelength( "file.bin" );\r
+  if ( size != 512 )\r
+  {\r
+    return _f_result( 22, size );\r
+  }\r
+\r
+\r
+/*test non existing appends a+*/\r
+  file = f_open( "file.bin", "a+" );\r
+  if ( !file )\r
+  {\r
+    return _f_result( 23, 0 );\r
+  }\r
+\r
+  pos = (unsigned short)f_tell( file );\r
+  if ( pos != 512 )\r
+  {\r
+    return _f_result( 24, pos );            /*position has to be 512*/\r
+  }\r
+\r
+/*write 512 times 3*/\r
+  psp_memset( testbuffer, 3, 512 );                           /*set all 3*/\r
+  size = (unsigned short)f_write( testbuffer, 1, 512, file ); /*test write*/\r
+  if ( size != 512 )\r
+  {\r
+    return _f_result( 25, size );\r
+  }\r
+\r
+/*go back, and read it*/\r
+  ret = f_rewind( file ); /*back to the begining*/\r
+  if ( ret )\r
+  {\r
+    return _f_result( 26, ret );       /*it should fail*/\r
+  }\r
+\r
+  size = (unsigned short)f_read( testbuffer, 1, 512, file ); /*test read*/\r
+  if ( size != 512 )\r
+  {\r
+    return _f_result( 27, size );             /*it should fail*/\r
+  }\r
+\r
+  pos = (unsigned short)f_tell( file );\r
+  if ( pos != 512 )\r
+  {\r
+    return _f_result( 28, pos );            /*position has to be 512*/\r
+  }\r
+\r
+/*close and check size*/\r
+  size = (unsigned short)f_filelength( "file.bin" );\r
+  if ( size != 512 )\r
+  {\r
+    return _f_result( 29, size );             /*has to be zero*/\r
+  }\r
+\r
+  ret = f_close( file );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 30, ret );\r
+  }\r
+\r
+  size = (unsigned short)f_filelength( "file.bin" );\r
+  if ( size != 1024 )\r
+  {\r
+    return _f_result( 31, size );\r
+  }\r
+\r
+/*close again!*/\r
+  ret = f_close( file );\r
+  if ( ret != F_ERR_NOTOPEN )\r
+  {\r
+    return _f_result( 32, pos );\r
+  }\r
+\r
+  ret = f_delete( "file.bin" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 33, ret );\r
+  }\r
+\r
+  _f_dump( "passed..." );\r
+  return 0;\r
+} /* f_opening */\r
+\r
+static unsigned char f_appending ( void )\r
+{\r
+  F_FILE        * file;\r
+  unsigned short  size, tsize, pos;\r
+  unsigned char   a, b, ret;\r
+\r
+  _f_dump( "f_appending" );\r
+\r
+  _f_deleteall();\r
+\r
+  for ( tsize = 0, a = 0 ; a < 16 ; a++ )\r
+  {\r
+    file = f_open( "ap.bin", "a" );\r
+    if ( !file )\r
+    {\r
+      return _f_result( 1, 0 );\r
+    }\r
+\r
+    psp_memset( testbuffer, a, sizeof( testbuffer ) );\r
+    size = (unsigned short)f_write( testbuffer, 1, a + 128, file );\r
+    if ( size != a + 128 )\r
+    {\r
+      return _f_result( 2, size );\r
+    }\r
+\r
+    size = (unsigned short)f_filelength( "ap.bin" );\r
+    if ( size != tsize )\r
+    {\r
+      return _f_result( 3, size );\r
+    }\r
+\r
+    tsize += a + 128;\r
+\r
+    ret = f_close( file );\r
+    if ( ret )\r
+    {\r
+      return _f_result( 4, ret );\r
+    }\r
+\r
+    size = (unsigned short)f_filelength( "ap.bin" );\r
+    if ( size != tsize )\r
+    {\r
+      return _f_result( 5, size );\r
+    }\r
+  }\r
+\r
+  file = f_open( "ap.bin", "r" );\r
+  if ( !file )\r
+  {\r
+    return _f_result( 6, 0 );\r
+  }\r
+\r
+  for ( tsize = 0, a = 0 ; a < 16 ; a++ )\r
+  {\r
+    if ( checkfilecontent( a + 128, (char)a, file ) )\r
+    {\r
+      return _f_result( 7, a );\r
+    }\r
+  }\r
+\r
+  ret = f_close( file );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 8, ret );\r
+  }\r
+\r
+  for ( tsize = 0, a = 0 ; a < 16 ; a++ )\r
+  {\r
+    file = f_open( "ap.bin", "r" );\r
+    if ( !file )\r
+    {\r
+      return _f_result( 9, 0 );\r
+    }\r
+\r
+    ret = f_seek( file, tsize, F_SEEK_SET );\r
+    if ( ret )\r
+    {\r
+      return _f_result( 10, ret );\r
+    }\r
+\r
+    pos = (unsigned short)f_tell( file );\r
+    if ( pos != tsize )\r
+    {\r
+      return _f_result( 11, pos );\r
+    }\r
+\r
+    size = (unsigned short)f_read( testbuffer, 1, a + 128, file );\r
+    if ( size != a + 128 )\r
+    {\r
+      return _f_result( 12, size );\r
+    }\r
+\r
+    for ( b = 0 ; b < a + 128 ; b++ )\r
+    {\r
+      if ( testbuffer[b] != (char)a )\r
+      {\r
+        return _f_result( 13, a );\r
+      }\r
+    }\r
+\r
+    tsize += a + 128;\r
+\r
+    pos = (unsigned short)f_tell( file );\r
+    if ( pos != tsize )\r
+    {\r
+      return _f_result( 13, pos );\r
+    }\r
+\r
+    ret = f_close( file );\r
+    if ( ret )\r
+    {\r
+      return _f_result( 14, ret );\r
+    }\r
+  }\r
+\r
+  ret = f_close( file );\r
+  if ( ret != F_ERR_NOTOPEN )\r
+  {\r
+    return _f_result( 9, ret );\r
+  }\r
+\r
+  ret = f_delete( "ap.bin" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 14, ret );\r
+  }\r
+\r
+  _f_dump( "passed..." );\r
+  return 0;\r
+} /* f_appending */\r
+\r
+static unsigned char f_writing ( void )\r
+{\r
+  F_FILE        * file;\r
+  unsigned short  size;\r
+  unsigned char   a, ret;\r
+  F_SPACE         before, after;\r
+\r
+  _f_dump( "f_writing" );\r
+\r
+  ret = f_getfreespace( &before );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 0, ret );\r
+  }\r
+\r
+  for ( a = 0 ; a < 4 ; a++ )\r
+  {\r
+    file = f_open( "wr.bin", "w" );\r
+    if ( !file )\r
+    {\r
+      return _f_result( 1, 0 );\r
+    }\r
+\r
+    psp_memset( testbuffer, a, sizeof( testbuffer ) );\r
+    size = (unsigned short)f_write( testbuffer, 1, a * 128, file );\r
+    if ( size != a * 128 )\r
+    {\r
+      return _f_result( 2, size );\r
+    }\r
+\r
+    ret = f_close( file );\r
+    if ( ret )\r
+    {\r
+      return _f_result( 3, ret );\r
+    }\r
+\r
+    size = (unsigned short)f_filelength( "wr.bin" );\r
+    if ( size != a * 128 )\r
+    {\r
+      return _f_result( 4, size );\r
+    }\r
+\r
+    file = f_open( "wr.bin", "r" );\r
+    if ( !file )\r
+    {\r
+      return _f_result( 5, 0 );\r
+    }\r
+\r
+    if ( checkfilecontent( a * 128, (char)a, file ) )\r
+    {\r
+      return _f_result( 6, a );\r
+    }\r
+\r
+    ret = f_close( file );\r
+    if ( ret )\r
+    {\r
+      return _f_result( 7, ret );\r
+    }\r
+  }\r
+\r
+\r
+  for ( a = 0 ; a < 4 ; a++ )\r
+  {\r
+    file = f_open( "wr.bin", "w+" );\r
+    if ( !file )\r
+    {\r
+      return _f_result( 8, 0 );\r
+    }\r
+\r
+    psp_memset( testbuffer, a, sizeof( testbuffer ) );\r
+    size = (unsigned short)f_write( testbuffer, 1, a * 128, file );\r
+    if ( size != a * 128 )\r
+    {\r
+      return _f_result( 9, size );\r
+    }\r
+\r
+    ret = f_close( file );\r
+    if ( ret )\r
+    {\r
+      return _f_result( 10, ret );\r
+    }\r
+\r
+    size = (unsigned short)f_filelength( "wr.bin" );\r
+    if ( size != a * 128 )\r
+    {\r
+      return _f_result( 11, size );\r
+    }\r
+\r
+    file = f_open( "wr.bin", "r+" );\r
+    if ( !file )\r
+    {\r
+      return _f_result( 12, 0 );\r
+    }\r
+\r
+    if ( checkfilecontent( a * 128, (char)a, file ) )\r
+    {\r
+      return _f_result( 13, a );\r
+    }\r
+\r
+    ret = f_close( file );\r
+    if ( ret )\r
+    {\r
+      return _f_result( 14, ret );\r
+    }\r
+  }\r
+\r
+  ret = f_getfreespace( &after );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 15, ret );\r
+  }\r
+\r
+  if ( before.bad != after.bad )\r
+  {\r
+    return _f_result( 16, 0 );\r
+  }\r
+\r
+  if ( before.free == after.free )\r
+  {\r
+    return _f_result( 17, 0 );\r
+  }\r
+\r
+  if ( before.used == after.used )\r
+  {\r
+    return _f_result( 18, 0 );\r
+  }\r
+\r
+  if ( before.total != after.total )\r
+  {\r
+    return _f_result( 19, 0 );\r
+  }\r
+\r
+  if ( before.used + before.free != after.used + after.free )\r
+  {\r
+    return _f_result( 20, 0 );\r
+  }\r
+\r
+  ret = f_delete( "wr.bin" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 21, ret );\r
+  }\r
+\r
+  ret = f_getfreespace( &after );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 22, ret );\r
+  }\r
+\r
+  if ( before.bad != after.bad )\r
+  {\r
+    return _f_result( 23, 0 );\r
+  }\r
+\r
+  if ( before.free != after.free )\r
+  {\r
+    return _f_result( 24, 0 );\r
+  }\r
+\r
+  if ( before.used != after.used )\r
+  {\r
+    return _f_result( 25, 0 );\r
+  }\r
+\r
+  if ( before.total != after.total )\r
+  {\r
+    return _f_result( 26, 0 );\r
+  }\r
+\r
+  _f_dump( "passed..." );\r
+  return 0;\r
+} /* f_writing */\r
+\r
+static unsigned char f_dots ( void )\r
+{\r
+  unsigned char  ret;\r
+  unsigned char  a, size;\r
+  F_FILE       * file;\r
+\r
+  _f_dump( "f_dots" );\r
+\r
+  ret = f_mkdir( "/tt" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 0, ret );\r
+  }\r
+\r
+  ret = f_chdir( "/tt" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 1, ret );\r
+  }\r
+\r
+  ret = f_rmdir( "." );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 4, ret );\r
+  }\r
+\r
+  ret = f_rmdir( ".." );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 5, ret );\r
+  }\r
+\r
+  ret = f_chdir( "." );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 6, ret );\r
+  }\r
+\r
+  ret = _f_checkcwd( f_nameconv( "/tt" ) );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 7, ret );\r
+  }\r
+\r
+  ret = f_delete( "." );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 8, ret );\r
+  }\r
+\r
+  ret = f_delete( ".." );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 9, ret );\r
+  }\r
+\r
+  ret = f_mkdir( "." );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 10, ret );\r
+  }\r
+\r
+  ret = f_mkdir( ".." );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 11, ret );\r
+  }\r
+\r
+  ret = f_mkdir( "..." );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 12, ret );\r
+  }\r
+\r
+  for ( a = 0 ; a < 6 ; a++ )\r
+  {\r
+    char * mode;\r
+    switch ( a )\r
+    {\r
+      case 0:\r
+        mode = "r";\r
+        break;\r
+\r
+      case 1:\r
+        mode = "r+";\r
+        break;\r
+\r
+      case 2:\r
+        mode = "w";\r
+        break;\r
+\r
+      case 3:\r
+        mode = "w+";\r
+        break;\r
+\r
+      case 4:\r
+        mode = "a";\r
+        break;\r
+\r
+      case 5:\r
+        mode = "a+";\r
+        break;\r
+\r
+      default:\r
+        return _f_result( 13, a );\r
+    } /* switch */\r
+\r
+    file = f_open( ".", mode );\r
+    if ( file )\r
+    {\r
+      return _f_result( 14, a );\r
+    }\r
+\r
+    file = f_open( "..", mode );\r
+    if ( file )\r
+    {\r
+      return _f_result( 15, a );\r
+    }\r
+\r
+    file = f_open( "...", mode );\r
+    if ( file )\r
+    {\r
+      return _f_result( 16, a );\r
+    }\r
+  }\r
+\r
+  size = (unsigned char)f_filelength( "." );\r
+  if ( size )\r
+  {\r
+    return _f_result( 17, size );\r
+  }\r
+\r
+  size = (unsigned char)f_filelength( ".." );\r
+  if ( size )\r
+  {\r
+    return _f_result( 18, size );\r
+  }\r
+\r
+  size = (unsigned char)f_filelength( "..." );\r
+  if ( size )\r
+  {\r
+    return _f_result( 19, size );\r
+  }\r
+\r
+\r
+  ret = f_chdir( "..." );\r
+  if ( ret != F_ERR_NOTFOUND )\r
+  {\r
+    return _f_result( 20, ret );\r
+  }\r
+\r
+  ret = f_chdir( ".." );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 21, ret );\r
+  }\r
+\r
+  ret = f_rmdir( "tt" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 27, ret );\r
+  }\r
+\r
+\r
+  _f_dump( "passed..." );\r
+  return 0;\r
+} /* f_dots */\r
+\r
+\r
+typedef struct\r
+{\r
+  unsigned char  MagicNum;\r
+  unsigned char  Line;\r
+  unsigned char  Buf[87];\r
+} struct_TestFileSysEntry;\r
+  #define NUM_OF_RECORDS 10\r
+static unsigned char f_rit ( void )\r
+{\r
+  unsigned char             i;\r
+  unsigned char             ret;\r
+  F_FILE                  * File;\r
+  struct_TestFileSysEntry * Entry = (struct_TestFileSysEntry *)( ( ( (long)testbuffer + 3 ) >> 2 ) << 2 );\r
+  unsigned short            Pos;\r
+  unsigned char             Ch;\r
+  unsigned char             Founded;\r
+\r
+  _f_dump( "f_rit" );\r
+\r
+  (void)f_delete( "MyTest" );\r
+  File = f_open( "MyTest", "a+" );\r
+  if ( !File )\r
+  {\r
+    return _f_result( 1, 0 );\r
+  }\r
+\r
+  /* add records  */\r
+  for ( i = 0 ; i < NUM_OF_RECORDS ; i++ )\r
+  {\r
+    Ch = (char)( i % 10 );\r
+    Entry->MagicNum = 0xbc;\r
+    Entry->Line = i;\r
+    Entry->Buf[0] = Ch;\r
+    Entry->Buf[10] = (unsigned char)( Ch + 1 );\r
+\r
+    if ( F_NO_ERROR != f_seek( File, 0, F_SEEK_END ) )\r
+    {\r
+      return _f_result( 2, 0 ); /* Fail, could not go to the end of the file */\r
+    }\r
+\r
+    if ( sizeof( struct_TestFileSysEntry ) != f_write( (void *)Entry, 1, sizeof( struct_TestFileSysEntry ), File ) )\r
+    {\r
+      return _f_result( 3, 0 ); /* Fail, could not write new entry */\r
+    }\r
+\r
+    Pos = (unsigned short)f_tell( File );\r
+    if ( ( ( Pos / sizeof( struct_TestFileSysEntry ) ) - 1 ) != i )\r
+    {\r
+      return _f_result( 4, 0 ); /* Fail, wrong file position */\r
+    }\r
+\r
+    if ( F_NO_ERROR != f_seek( File, (long)( Pos - sizeof( struct_TestFileSysEntry ) ), F_SEEK_SET ) )\r
+    {\r
+      return _f_result( 5, 0 ); /* Fail, could not go to new entry position */\r
+    }\r
+\r
+    if ( sizeof( struct_TestFileSysEntry ) != f_read( (void *)Entry, 1, sizeof( struct_TestFileSysEntry ), File ) )\r
+    {\r
+      return _f_result( 6, 0 ); /* Fail, could not read the new entry */\r
+    }\r
+\r
+    if ( ( Entry->MagicNum != 0xbc ) || ( Entry->Line != (int)i ) || ( Entry->Buf[0] != Ch ) || ( Entry->Buf[10] != Ch + 1 ) )\r
+    {\r
+      return _f_result( 7, 0 ); /*Fail, the new entry is corrupted"*/\r
+    }\r
+  }\r
+\r
+  ret = f_close( File );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 8, ret );\r
+  }\r
+\r
+\r
+  /*Open file again*/\r
+  File = f_open( "MyTest", "a+" );\r
+  if ( !File )\r
+  {\r
+    return _f_result( 9, 0 );\r
+  }\r
+\r
+  /* read records  */\r
+  for ( i = 0 ; i < NUM_OF_RECORDS ; i++ )\r
+  {\r
+    Ch = (char)( i % 10 );\r
+\r
+    if ( F_NO_ERROR != f_seek( File, 0, F_SEEK_SET ) )\r
+    {\r
+      return _f_result( 10, 0 ); /* Fail, could not go to the start of the file */\r
+    }\r
+\r
+    Founded = 0;\r
+    while ( sizeof( struct_TestFileSysEntry ) == f_read( (void *)Entry, 1, sizeof( struct_TestFileSysEntry ), File ) )\r
+    {\r
+      if ( ( Entry->MagicNum == 0xbc )\r
+          && ( Entry->Line == (int)i )\r
+          && ( Entry->Buf[0] == Ch )\r
+          && ( Entry->Buf[10] == Ch + 1 ) )\r
+      {\r
+        Founded = 1;\r
+        break;\r
+      }\r
+    }\r
+\r
+    if ( !Founded )\r
+    {\r
+      return _f_result( 11, i );      /* Entry not founded */\r
+    }\r
+  }\r
+\r
+  ret = f_close( File );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 12, ret );\r
+  }\r
+\r
+\r
+  ret = f_delete( "MyTest" );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 13, ret );\r
+  }\r
+\r
+  _f_dump( "passed..." );\r
+\r
+  return 0;\r
+} /* f_rit */\r
+\r
+\r
+\r
+\r
+static unsigned char f_truncating ( void )\r
+{\r
+  F_FILE       * file;\r
+  unsigned long  size;\r
+  unsigned char  ret;\r
+\r
+  _f_dump( "f_truncating" );\r
+\r
+  file = f_open( "test.bin", "w+" );\r
+  if ( !file )\r
+  {\r
+    return _f_result( 0, 0 );\r
+  }\r
+\r
+  (void)psp_memset( testbuffer, 1, F_MAX_SEEK_TEST );\r
+  size = (unsigned long)f_write( testbuffer, 1, F_MAX_SEEK_TEST, file );\r
+  if ( size != F_MAX_SEEK_TEST )\r
+  {\r
+    return _f_result( 1, size );\r
+  }\r
+\r
+  ret = f_close( file );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 2, ret );\r
+  }\r
+\r
+  file = f_truncate( "test.bin", F_MAX_SEEK_TEST - 4 );\r
+  if ( !file )\r
+  {\r
+    return _f_result( 3, 0 );\r
+  }\r
+\r
+  ret = f_close( file );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 4, ret );\r
+  }\r
+\r
+  size = (unsigned long)f_filelength( "test.bin" );\r
+  if ( size != F_MAX_SEEK_TEST - 4 )\r
+  {\r
+    return _f_result( 5, size );\r
+  }\r
+\r
+\r
+  file = f_truncate( "test.bin", F_MAX_SEEK_TEST );\r
+  if ( !file )\r
+  {\r
+    return _f_result( 3, 0 );\r
+  }\r
+\r
+  ret = f_close( file );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 4, ret );\r
+  }\r
+\r
+  size = (unsigned long)f_filelength( "test.bin" );\r
+  if ( size != F_MAX_SEEK_TEST )\r
+  {\r
+    return _f_result( 5, size );\r
+  }\r
+\r
+\r
+  file = f_truncate( "test.bin", ( F_MAX_SEEK_TEST / 2 ) - 92 );\r
+  if ( !file )\r
+  {\r
+    return _f_result( 6, 0 );\r
+  }\r
+\r
+  (void)psp_memset( testbuffer, 2, 92 );\r
+  size = (unsigned long)f_write( testbuffer, 1, 92, file );\r
+  if ( size != 92 )\r
+  {\r
+    return _f_result( 7, size );\r
+  }\r
+\r
+  ret = f_close( file );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 8, ret );\r
+  }\r
+\r
+  size = (unsigned long)f_filelength( "test.bin" );\r
+  if ( size != ( F_MAX_SEEK_TEST / 2 ) )\r
+  {\r
+    return _f_result( 9, size );\r
+  }\r
+\r
+\r
+  file = f_truncate( "test.bin", 1 );\r
+  if ( !file )\r
+  {\r
+    return _f_result( 10, 0 );\r
+  }\r
+\r
+  (void)psp_memset( testbuffer, 3, 2 );\r
+  size = (unsigned long)f_write( testbuffer, 1, 2, file );\r
+  if ( size != 2 )\r
+  {\r
+    return _f_result( 11, size );\r
+  }\r
+\r
+  ret = f_close( file );\r
+  if ( ret )\r
+  {\r
+    return _f_result( 12, ret );\r
+  }\r
+\r
+  size = (unsigned long)f_filelength( "test.bin" );\r
+  if ( size != 3 )\r
+  {\r
+    return _f_result( 13, size );\r
+  }\r
+\r
+\r
+\r
+  _f_dump( "passed..." );\r
+  return 0;\r
+} /* f_truncating */\r
+\r
+\r
+void f_dotest ( unsigned char t )\r
+{\r
+  _f_dump( "File system test started..." );\r
+  _f_dump( "WARNING: The contents of your drive will be destroyed!\n" );\r
+\r
+  (void)_f_poweron();\r
+\r
+  switch ( t )\r
+  {\r
+    case 0:\r
+    case 1:\r
+      (void)f_formatting();\r
+      if ( t )\r
+      {\r
+        break;\r
+      }\r
+\r
+\r
+    /* fall through */\r
+    case 2:\r
+      (void)f_dirtest();\r
+      if ( t )\r
+      {\r
+        break;\r
+      }\r
+\r
+\r
+    /* fall through */\r
+    case 3:\r
+      (void)f_findingtest();\r
+      if ( t )\r
+      {\r
+        break;\r
+      }\r
+\r
+\r
+    /* fall through */\r
+    case 4:\r
+      (void)f_powerfail();\r
+      if ( t )\r
+      {\r
+        break;\r
+      }\r
+\r
+\r
+    /* fall through */\r
+    case 5:\r
+      (void)f_seeking( 128 );\r
+      if ( t )\r
+      {\r
+        break;\r
+      }\r
+\r
+  #if ( F_MAX_SEEK_TEST > 128 )\r
+\r
+    /* fall through */\r
+    case 6:\r
+      (void)f_seeking( 256 );\r
+      if ( t )\r
+      {\r
+        break;\r
+      }\r
+\r
+  #endif\r
+  #if ( F_MAX_SEEK_TEST > 256 )\r
+\r
+    /* fall through */\r
+    case 7:\r
+      (void)f_seeking( 512 );\r
+      if ( t )\r
+      {\r
+        break;\r
+      }\r
+\r
+  #endif\r
+  #if ( F_MAX_SEEK_TEST > 512 )\r
+\r
+    /* fall through */\r
+    case 8:\r
+      (void)f_seeking( 1024 );\r
+      if ( t )\r
+      {\r
+        break;\r
+      }\r
+\r
+  #endif\r
+  #if ( F_MAX_SEEK_TEST > 1024 )\r
+\r
+    /* fall through */\r
+    case 9:\r
+      (void)f_seeking( 2048 );\r
+      if ( t )\r
+      {\r
+        break;\r
+      }\r
+\r
+  #endif\r
+  #if ( F_MAX_SEEK_TEST > 2048 )\r
+\r
+    /* fall through */\r
+    case 10:\r
+      (void)f_seeking( 4096 );\r
+      if ( t )\r
+      {\r
+        break;\r
+      }\r
+\r
+  #endif\r
+  #if ( F_MAX_SEEK_TEST > 4096 )\r
+\r
+    /* fall through */\r
+    case 11:\r
+      (void)f_seeking( 8192 );\r
+      if ( t )\r
+      {\r
+        break;\r
+      }\r
+\r
+  #endif\r
+  #if ( F_MAX_SEEK_TEST > 8192 )\r
+\r
+    /* fall through */\r
+    case 12:\r
+      (void)f_seeking( 16384 );\r
+      if ( t )\r
+      {\r
+        break;\r
+      }\r
+\r
+  #endif\r
+  #if ( F_MAX_SEEK_TEST > 16384 )\r
+\r
+    /* fall through */\r
+    case 13:\r
+      (void)f_seeking( 32768 );\r
+      if ( t )\r
+      {\r
+        break;\r
+      }\r
+\r
+  #endif\r
+\r
+    /* fall through */\r
+    case 14:\r
+      (void)f_opening();\r
+      if ( t )\r
+      {\r
+        break;\r
+      }\r
+\r
+\r
+    /* fall through */\r
+    case 15:\r
+      (void)f_appending();\r
+      if ( t )\r
+      {\r
+        break;\r
+      }\r
+\r
+\r
+    /* fall through */\r
+    case 16:\r
+      (void)f_writing();\r
+      if ( t )\r
+      {\r
+        break;\r
+      }\r
+\r
+\r
+    /* fall through */\r
+    case 17:\r
+      (void)f_dots();\r
+      if ( t )\r
+      {\r
+        break;\r
+      }\r
+\r
+\r
+    /* fall through */\r
+    case 18:\r
+      (void)f_rit();\r
+      if ( t )\r
+      {\r
+        break;\r
+      }\r
+\r
+    case 19:\r
+      (void)f_truncating();\r
+      if ( t )\r
+      {\r
+        break;\r
+      }\r
+\r
+      break;\r
+  } /* switch */\r
+\r
+  _f_dump( "End of tests..." );\r
+} /* f_dotest */\r
+\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * end of test.c\r
+ *\r
+ ***************************************************************************/\r
+#endif  /*_TEST_C_*/\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/test/test.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/fat_sl/test/test.h
new file mode 100644 (file)
index 0000000..cc62749
--- /dev/null
@@ -0,0 +1,116 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef __TEST_H\r
+#define __TEST_H\r
+\r
+#include "../../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3 || VER_FAT_SL_MINOR != 2\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+\r
+#ifdef __cplusplus\r
+extern "C" {\r
+#endif\r
+\r
+\r
+/*\r
+** Maximum size for seek test.\r
+** Options: 128, 256, 512, 1024, 2048, 4096, 8192, 16384, 32768\r
+*/\r
+#define F_MAX_SEEK_TEST 16384\r
+\r
+\r
+/*\r
+** Defines media type for testing.\r
+** Options: F_FAT12_MEDIA, F_FAT16_MEDIA\r
+*/\r
+#define F_FAT_TYPE      F_FAT12_MEDIA\r
+\r
+\r
+/*\r
+** Start filesystem test.\r
+** Parameter:\r
+**     0  - run all the tests\r
+**\r
+**     2  - directory\r
+**     3  - find\r
+**\r
+**     5* - seek 128\r
+**     6* - seek 256\r
+**     7* - seek 512\r
+**     8* - seek 1024\r
+**     9* - seek 2048\r
+**     10*- seek 4096\r
+**     11*- seek 8192\r
+**     12*- seek 16384\r
+**     13*- seek 32768\r
+**     14 - open\r
+**     15 - append\r
+**     16 - write\r
+**     17 - dots\r
+**     18 - rit\r
+**  *Note that only seek tests allowed by F_MAX_SEEK_TEST are executed.\r
+**\r
+**  The following defines are required for the specific test:\r
+**                                       1 1 1 1 1 1 1 1 1\r
+**                       2 3   5 6 7 8 9 0 1 2 3 4 5 6 7 8\r
+** F_CHDIR               x x   - - - - - - - - - - x - x -\r
+** F_MKDIR               x x   - - - - - - - - - - - - x -\r
+** F_RMDIR               x x   - - - - - - - - - - x - x -\r
+** F_DELETE              x x   x x x x x x x x x x x x x x\r
+** F_FILELENGTH                  - -   x x x x x x x x x x x x - -\r
+** F_FINDING             x x   - - - - - - - - - - x - - -\r
+** F_TELL                - -   x x x x x x x x x x x x - x\r
+** F_REWIND              - -   - - - - - - - - - x - - - -\r
+** F_EOF                 - -   x x x x x x x x x - - x - -\r
+** F_SEEK                - -   x x x x x x x x x - x x - x\r
+** F_WRITE               - -   x x x x x x x x x x x x - x\r
+** F_WRITING             x x   x x x x x x x x x x x x x x\r
+** F_DIRECTORIES         x x   - - - - - - - - - - x - x -\r
+** F_CHECKNAME           x -   - - - - - - - - - - - - x -\r
+*/\r
+void f_dotest ( unsigned char );\r
+\r
+#ifdef __cplusplus\r
+}\r
+#endif\r
+\r
+#endif /* ifndef __TEST_H */\r
+\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/media-drv/ram/ramdrv_f.c b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/media-drv/ram/ramdrv_f.c
new file mode 100644 (file)
index 0000000..5d1d49f
--- /dev/null
@@ -0,0 +1,247 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#include "../../api/api_mdriver_ram.h"\r
+#include "config_mdriver_ram.h"\r
+#include "../../psp/include/psp_string.h"\r
+\r
+#include "../../version/ver_mdriver_ram.h"\r
+#if VER_MDRIVER_RAM_MAJOR != 1 || VER_MDRIVER_RAM_MINOR != 2\r
+ #error Incompatible MDRIVER_RAM version number!\r
+#endif\r
+\r
+\r
+char  ramdrv0[MDRIVER_RAM_VOLUME0_SIZE];\r
+\r
+typedef struct\r
+{\r
+  char         * ramdrv;\r
+  unsigned long  maxsector;\r
+  int            use;\r
+  F_DRIVER     * driver;\r
+} t_RamDrv;\r
+\r
+static F_DRIVER  t_drivers[1];\r
+\r
+static t_RamDrv  RamDrv[1] =\r
+{\r
+  { ramdrv0, ( MDRIVER_RAM_VOLUME0_SIZE / MDRIVER_RAM_SECTOR_SIZE ), 0, &t_drivers[0] }\r
+};\r
+\r
+\r
+/****************************************************************************\r
+ * Read one sector\r
+ ***************************************************************************/\r
+static int ram_readsector ( F_DRIVER * driver, void * data, unsigned long sector )\r
+{\r
+  long       len;\r
+  char     * d = (char *)data;\r
+  char     * s;\r
+  t_RamDrv * p = (t_RamDrv *)( driver->user_ptr );\r
+\r
+  if ( sector >= p->maxsector )\r
+  {\r
+    return MDRIVER_RAM_ERR_SECTOR;\r
+  }\r
+\r
+  s = p->ramdrv;\r
+  s += sector * MDRIVER_RAM_SECTOR_SIZE;\r
+  len = MDRIVER_RAM_SECTOR_SIZE;\r
+\r
+#if MDRIVER_MEM_LONG_ACCESS\r
+  if ( ( !( len & 3 ) ) && ( !( ( (long)d ) & 3 ) ) && ( !( ( (long)s ) & 3 ) ) )\r
+  {\r
+    long * dd = (long *)d;\r
+    long * ss = (long *)s;\r
+    len >>= 2;\r
+    while ( len-- )\r
+    {\r
+      *dd++ = *ss++;\r
+    }\r
+\r
+    return MDRIVER_RAM_NO_ERROR;\r
+  }\r
+\r
+#endif /* if MDRIVER_MEM_LONG_ACCESS */\r
+\r
+  while ( len-- )\r
+  {\r
+    *d++ = *s++;\r
+  }\r
+\r
+  return MDRIVER_RAM_NO_ERROR;\r
+}\r
+\r
+/****************************************************************************\r
+ * Write one sector\r
+ ***************************************************************************/\r
+static int ram_writesector ( F_DRIVER * driver, void * data, unsigned long sector )\r
+{\r
+  long       len;\r
+  char     * s = (char *)data;\r
+  char     * d;\r
+  t_RamDrv * p = (t_RamDrv *)( driver->user_ptr );\r
+\r
+  if ( sector >= p->maxsector )\r
+  {\r
+    return MDRIVER_RAM_ERR_SECTOR;\r
+  }\r
+\r
+  d = p->ramdrv;\r
+  d += sector * MDRIVER_RAM_SECTOR_SIZE;\r
+  len = MDRIVER_RAM_SECTOR_SIZE;\r
+\r
+#if MDRIVER_MEM_LONG_ACCESS\r
+  if ( ( !( len & 3 ) ) && ( !( ( (long)d ) & 3 ) ) && ( !( ( (long)s ) & 3 ) ) )\r
+  {\r
+    long * dd = (long *)d;\r
+    long * ss = (long *)s;\r
+    len >>= 2;\r
+    while ( len-- )\r
+    {\r
+      *dd++ = *ss++;\r
+    }\r
+\r
+    return MDRIVER_RAM_NO_ERROR;\r
+  }\r
+\r
+#endif /* if MDRIVER_MEM_LONG_ACCESS */\r
+\r
+  while ( len-- )\r
+  {\r
+    *d++ = *s++;\r
+  }\r
+\r
+  return MDRIVER_RAM_NO_ERROR;\r
+}\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * ram_getphy\r
+ *\r
+ * determinate ramdrive physicals\r
+ *\r
+ * INPUTS\r
+ *\r
+ * driver - driver structure\r
+ * phy - this structure has to be filled with physical information\r
+ *\r
+ * RETURNS\r
+ *\r
+ * error code or zero if successful\r
+ *\r
+ ***************************************************************************/\r
+static int ram_getphy ( F_DRIVER * driver, F_PHY * phy )\r
+{\r
+  t_RamDrv * p = (t_RamDrv *)( driver->user_ptr );\r
+\r
+  phy->number_of_sectors = p->maxsector;\r
+  phy->bytes_per_sector = MDRIVER_RAM_SECTOR_SIZE;\r
+\r
+  return MDRIVER_RAM_NO_ERROR;\r
+}\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * ram_release\r
+ *\r
+ * Releases a drive\r
+ *\r
+ * INPUTS\r
+ *\r
+ * driver_param - driver parameter\r
+ *\r
+ ***************************************************************************/\r
+static void ram_release ( F_DRIVER * driver )\r
+{\r
+  t_RamDrv * p = (t_RamDrv *)( driver->user_ptr );\r
+\r
+  if ( p == RamDrv )\r
+  {\r
+    p->use = 0;\r
+  }\r
+}\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * ram_initfunc\r
+ *\r
+ * this init function has to be passed for highlevel to initiate the\r
+ * driver functions\r
+ *\r
+ * INPUTS\r
+ *\r
+ * driver_param - driver parameter\r
+ *\r
+ * RETURNS\r
+ *\r
+ * driver structure pointer\r
+ *\r
+ ***************************************************************************/\r
+F_DRIVER * ram_initfunc ( unsigned long driver_param )\r
+{\r
+  t_RamDrv    * p;\r
+\r
+  p = RamDrv + driver_param;\r
+\r
+  if ( p != RamDrv )\r
+  {\r
+    return 0;\r
+  }\r
+\r
+  if ( p->use )\r
+  {\r
+    return 0;\r
+  }\r
+\r
+  (void)psp_memset( p->driver, 0, sizeof( F_DRIVER ) );\r
+\r
+  p->driver->readsector = ram_readsector;\r
+  p->driver->writesector = ram_writesector;\r
+  p->driver->getphy = ram_getphy;\r
+  p->driver->release = ram_release;\r
+  p->driver->user_ptr = p;\r
+\r
+  p->use = 1;\r
+\r
+  return p->driver;\r
+} /* ram_initfunc */\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/psp/include/psp_rtc.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/psp/include/psp_rtc.h
new file mode 100644 (file)
index 0000000..7f1d560
--- /dev/null
@@ -0,0 +1,71 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef _PSP_RTC_H\r
+#define _PSP_RTC_H\r
+\r
+#include <stdint.h>\r
+\r
+#include "../../version/ver_psp_rtc.h"\r
+#if VER_PSP_RTC_MAJOR != 1\r
+ #error "VER_PSP_RTC_MAJOR invalid"\r
+#endif\r
+\r
+#ifdef __cplusplus\r
+extern "C" {\r
+#endif\r
+\r
+typedef struct\r
+{\r
+  uint8_t   sec;\r
+  uint8_t   min;\r
+  uint8_t   hour;\r
+  uint8_t   day;\r
+  uint8_t   month;\r
+  uint16_t  year;\r
+} t_psp_timedate;\r
+\r
+void psp_getcurrenttimedate ( t_psp_timedate * p_timedate );\r
+\r
+#ifdef __cplusplus\r
+}\r
+#endif\r
+\r
+\r
+#endif /* _PSP_RTC_H */\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/psp/include/psp_string.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/psp/include/psp_string.h
new file mode 100644 (file)
index 0000000..310e439
--- /dev/null
@@ -0,0 +1,60 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef _PSP_STRING_H_\r
+#define _PSP_STRING_H_\r
+\r
+#include <stddef.h>\r
+#include <string.h>\r
+\r
+#include "../../version/ver_psp_string.h"\r
+#if VER_PSP_STRING_MAJOR != 1 || VER_PSP_STRING_MINOR != 4\r
+ #error Incompatible PSP_STRING version number!\r
+#endif\r
+\r
+#define psp_memcpy( d, s, l )    memcpy( ( d ), ( s ), (size_t)( l ) )\r
+#define psp_memmove( d, s, l )   memmove( ( d ), ( s ), (size_t)( l ) )\r
+#define psp_memset( d, c, l )    memset( ( d ), ( c ), (size_t)( l ) )\r
+#define psp_memcmp( s1, s2, l )  memcmp( ( s1 ), ( s2 ), (size_t)( l ) )\r
+#define psp_strnlen( s, l )      strnlen( ( s ), ( size_t )( l ) )\r
+#define psp_strncat( d, s, l )   strncat( ( d ), ( s ), (size_t)( l ) )\r
+#define psp_strncpy( d, s, l )   strncpy( ( d ), ( s ), (size_t)( l ) )\r
+#define psp_strncmp( s1, s2, l ) strncmp( ( s1 ), ( s2 ), (size_t)( l ) )\r
+\r
+#endif /* ifndef _PSP_STRING_H_ */\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/psp/target/fat_sl/psp_test.c b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/psp/target/fat_sl/psp_test.c
new file mode 100644 (file)
index 0000000..62446fe
--- /dev/null
@@ -0,0 +1,86 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#include <stdio.h>\r
+#include "psp_test.h"\r
+#include "config_fat_sl.h"\r
+#include "config_mdriver_ram.h"\r
+#include "../../../api/fat_sl.h"\r
+#include "../../../api/api_mdriver_ram.h"\r
+\r
+#include "../../../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+#include "../../../version/ver_psp_fat_sl.h"\r
+#if VER_PSP_FAT_FAT_SL_MAJOR != 1 || VER_PSP_FAT_FAT_SL_MINOR != 1\r
+ #error Incompatible PSP_FAT_FAT_SL version number!\r
+#endif\r
+\r
+uint8_t  all_tests_passed = 1u;\r
+\r
+/* Use to display text (printf). */\r
+void _f_dump ( char * s )\r
+{\r
+  printf( "%s\r\n", s );\r
+}\r
+\r
+/* Use to display test result (printf). */\r
+uint8_t _f_result ( uint8_t testnum, uint32_t result )\r
+{\r
+  (void)testnum;\r
+  if ( result == 0 )\r
+  {\r
+    printf( "Passed\r\n" );\r
+  }\r
+  else\r
+  {\r
+    printf( "FAILED! Error code: %u\r\n", result );\r
+    all_tests_passed = 0u;\r
+  }\r
+\r
+  return 0;\r
+}\r
+\r
+/* Use to build file system (mount). */\r
+uint8_t _f_poweron ( void )\r
+{\r
+  f_delvolume();\r
+  return f_initvolume( ram_initfunc );\r
+}\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/psp/target/fat_sl/psp_test.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/psp/target/fat_sl/psp_test.h
new file mode 100644 (file)
index 0000000..630c60f
--- /dev/null
@@ -0,0 +1,75 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef _PSP_FAT_FAT_SL_H\r
+#define _PSP_FAT_FAT_SL_H\r
+\r
+#include <stdint.h>\r
+#include "../../../psp/include/psp_string.h"\r
+\r
+#include "../../../version/ver_fat_sl.h"\r
+#if VER_FAT_SL_MAJOR != 3\r
+ #error Incompatible FAT_SL version number!\r
+#endif\r
+#include "../../../version/ver_psp_fat_sl.h"\r
+#if VER_PSP_FAT_FAT_SL_MAJOR != 1 || VER_PSP_FAT_FAT_SL_MINOR != 1\r
+ #error Incompatible PSP_FAT_FAT_SL version number!\r
+#endif\r
+\r
+#ifdef __cplusplus\r
+extern "C" {\r
+#endif\r
+\r
+extern uint8_t  all_tests_passed;\r
+\r
+/* Use to display text (printf). */\r
+void _f_dump ( char * s );\r
+\r
+/* Use to display test result (printf). */\r
+uint8_t _f_result ( uint8_t testnum, uint32_t result );\r
+\r
+/* Use to build file system (mount). */\r
+uint8_t _f_poweron ( void );\r
+\r
+#ifdef __cplusplus\r
+}\r
+#endif\r
+\r
+\r
+#endif /* _PSP_FAT_FAT_SL_H */\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/psp/target/rtc/psp_rtc.c b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/psp/target/rtc/psp_rtc.c
new file mode 100644 (file)
index 0000000..45b3a99
--- /dev/null
@@ -0,0 +1,80 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#include <stdint.h>\r
+#include <stddef.h>\r
+#include "../../include/psp_rtc.h"\r
+\r
+#include "../../../version/ver_psp_rtc.h"\r
+#if VER_PSP_RTC_MAJOR != 1\r
+ #error "VER_PSP_RTC_MAJOR invalid"\r
+#endif\r
+#if VER_PSP_RTC_MINOR != 0\r
+ #error "VER_PSP_RTC_MINOR invalid"\r
+#endif\r
+\r
+\r
+/****************************************************************************\r
+ *\r
+ * psp_getcurrenttimedate\r
+ *\r
+ * Need to be ported depending on system, it retreives the\r
+ * current time and date.\r
+ * Please take care of correct roll-over handling.\r
+ * Roll-over problem is to read a date at 23.59.59 and then reading time at\r
+ * 00:00.00.\r
+ *\r
+ * INPUT\r
+ *\r
+ * p_timedate - pointer where to store time and date\r
+ *\r
+ ***************************************************************************/\r
+void psp_getcurrenttimedate ( t_psp_timedate * p_timedate )\r
+{\r
+  if ( p_timedate != NULL )\r
+  {\r
+    p_timedate->sec = 0;\r
+    p_timedate->min = 0;\r
+    p_timedate->hour = 12u;\r
+\r
+    p_timedate->day = 1u;\r
+    p_timedate->month = 1u;\r
+    p_timedate->year = 1980u;\r
+  }\r
+} /* psp_getcurrenttimedate */\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/version/ver_fat_sl.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/version/ver_fat_sl.h
new file mode 100644 (file)
index 0000000..f521ffb
--- /dev/null
@@ -0,0 +1,46 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef _VER_FAT_SL_H\r
+#define _VER_FAT_SL_H\r
+\r
+#define VER_FAT_SL_MAJOR 3\r
+#define VER_FAT_SL_MINOR 2\r
+\r
+#endif\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/version/ver_mdriver.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/version/ver_mdriver.h
new file mode 100644 (file)
index 0000000..4a9468d
--- /dev/null
@@ -0,0 +1,46 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef _VER_MDRIVER_H\r
+#define _VER_MDRIVER_H\r
+\r
+#define VER_MDRIVER_MAJOR 1\r
+#define VER_MDRIVER_MINOR 0\r
+\r
+#endif\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/version/ver_mdriver_ram.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/version/ver_mdriver_ram.h
new file mode 100644 (file)
index 0000000..384a091
--- /dev/null
@@ -0,0 +1,46 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef _VER_MDRIVER_RAM_H\r
+#define _VER_MDRIVER_RAM_H\r
+\r
+#define VER_MDRIVER_RAM_MAJOR 1\r
+#define VER_MDRIVER_RAM_MINOR 2\r
+\r
+#endif\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/version/ver_psp_fat_sl.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/version/ver_psp_fat_sl.h
new file mode 100644 (file)
index 0000000..98a22e1
--- /dev/null
@@ -0,0 +1,46 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef _VER_PSP_FAT_FAT_SL_H\r
+#define _VER_PSP_FAT_FAT_SL_H\r
+\r
+#define VER_PSP_FAT_FAT_SL_MAJOR 1\r
+#define VER_PSP_FAT_FAT_SL_MINOR 1\r
+\r
+#endif  /* _VER_PSP_FAT_FAT_SL_H */\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/version/ver_psp_rtc.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/version/ver_psp_rtc.h
new file mode 100644 (file)
index 0000000..8a65db0
--- /dev/null
@@ -0,0 +1,46 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef _VER_PSP_RTC_H\r
+#define _VER_PSP_RTC_H\r
+\r
+#define VER_PSP_RTC_MAJOR 1\r
+#define VER_PSP_RTC_MINOR 0\r
+\r
+#endif\r
+\r
diff --git a/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/version/ver_psp_string.h b/FreeRTOS-Plus/Source/FreeRTOS-Plus-FAT-SL/version/ver_psp_string.h
new file mode 100644 (file)
index 0000000..2ed0415
--- /dev/null
@@ -0,0 +1,46 @@
+/*\r
+ * FreeRTOS+FAT FS V1.0.0 (C) 2013 HCC Embedded\r
+ *\r
+ * The FreeRTOS+FAT SL license terms are different to the FreeRTOS license \r
+ * terms.\r
+ * \r
+ * FreeRTOS+FAT SL uses a dual license model that allows the software to be used\r
+ * under a pure GPL open source license (as opposed to the modified GPL licence\r
+ * under which FreeRTOS is distributed) or a commercial license.  Details of \r
+ * both license options follow:\r
+ * \r
+ * - Open source licensing -\r
+ * FreeRTOS+FAT SL is a free download and may be used, modified, evaluated and\r
+ * distributed without charge provided the user adheres to version two of the \r
+ * GNU General Public License (GPL) and does not remove the copyright notice or \r
+ * this text.  The GPL V2 text is available on the gnu.org web site, and on the\r
+ * following URL: http://www.FreeRTOS.org/gpl-2.0.txt.\r
+ * \r
+ * - Commercial licensing -\r
+ * Businesses and individuals who for commercial or other reasons cannot comply\r
+ * with the terms of the GPL V2 license must obtain a commercial license before \r
+ * incorporating FreeRTOS+FAT SL into proprietary software for distribution in \r
+ * any form.  Commercial licenses can be purchased from \r
+ * http://shop.freertos.org/fat_sl and do not require any source files to be \r
+ * changed.\r
+ *\r
+ * FreeRTOS+FAT SL is distributed in the hope that it will be useful.  You\r
+ * cannot use FreeRTOS+FAT SL unless you agree that you use the software 'as\r
+ * is'.  FreeRTOS+FAT SL is provided WITHOUT ANY WARRANTY; without even the\r
+ * implied warranties of NON-INFRINGEMENT, MERCHANTABILITY or FITNESS FOR A\r
+ * PARTICULAR PURPOSE. Real Time Engineers Ltd. and HCC Embedded disclaims all\r
+ * conditions and terms, be they implied, expressed, or statutory.\r
+ *\r
+ * http://www.FreeRTOS.org\r
+ * http://www.FreeRTOS.org/FreeRTOS-Plus\r
+ *\r
+ */\r
+\r
+#ifndef _VER_PSP_STRING_H\r
+#define _VER_PSP_STRING_H\r
+\r
+#define VER_PSP_STRING_MAJOR 1\r
+#define VER_PSP_STRING_MINOR 4\r
+\r
+#endif\r
+\r
index 64cb0bbfaf9ee5f4140eb58b4164505e68dd3d91..e6aabb8d4456f2a5e0da8f8a3fe6b98793be429c 100644 (file)
@@ -568,10 +568,6 @@ typedef portBASE_TYPE (*pdTASK_HOOK_CODE)( void * );
        #define configUSE_QUEUE_SETS 0\r
 #endif\r
 \r
-#ifndef portTASK_USES_FLOATING_POINT\r
-       #defeine portTASK_USES_FLOATING_POINT()\r
-#endif\r
-\r
 /* For backward compatability. */\r
 #define eTaskStateGet eTaskGetState\r
 \r