| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252 |
- /*
- * FreeRTOS+FAT V2.3.3
- * Copyright (C) 2021 Amazon.com, Inc. or its affiliates. All Rights Reserved.
- *
- * Permission is hereby granted, free of charge, to any person obtaining a copy of
- * this software and associated documentation files (the "Software"), to deal in
- * the Software without restriction, including without limitation the rights to
- * use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of
- * the Software, and to permit persons to whom the Software is furnished to do so,
- * subject to the following conditions:
- *
- * The above copyright notice and this permission notice shall be included in all
- * copies or substantial portions of the Software.
- *
- * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
- * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS
- * FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR
- * COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER
- * IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
- * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
- *
- * https://www.FreeRTOS.org
- * https://github.com/FreeRTOS
- *
- */
- #include <stdio.h>
- #include <string.h>
- /* FreeRTOS includes. */
- #include "FreeRTOS.h"
- #include "task.h"
- #include "portable.h"
- #include "ff_headers.h"
- #include "ff_devices.h"
- #ifndef ARRAY_SIZE
- #define ARRAY_SIZE( x ) ( int ) ( sizeof( x ) / sizeof( x )[ 0 ] )
- #endif
- #if ( ffconfigDEV_SUPPORT == 0 )
- #error No use to include this module if ffconfigDEV_SUPPORT is disabled
- #endif /* ffconfigDEV_SUPPORT == 0 */
- struct SFileCache
- {
- char pcFileName[ 16 ];
- uint32_t ulFileLength;
- uint32_t ulFilePointer;
- };
- struct SFileCache xFiles[ 16 ];
- enum eCACHE_ACTION
- {
- eCACHE_LOOKUP,
- eCACHE_ADD,
- eCACHE_REMOVE,
- };
- const char pcDevicePath[] = ffconfigDEV_PATH;
- struct SFileCache * pxFindFile( const char * pcFname,
- enum eCACHE_ACTION eAction )
- {
- BaseType_t xIndex, xFreeIndex = -1;
- struct SFileCache * pxResult = NULL;
- for( xIndex = 0; xIndex < ARRAY_SIZE( xFiles ); xIndex++ )
- {
- if( xFiles[ xIndex ].pcFileName[ 0 ] == '\0' )
- {
- if( xFreeIndex < 0 )
- {
- xFreeIndex = xIndex;
- }
- }
- else if( strcmp( xFiles[ xIndex ].pcFileName, pcFname ) == 0 )
- {
- if( eAction == eCACHE_REMOVE )
- {
- xFiles[ xIndex ].pcFileName[ 0 ] = '\0';
- }
- pxResult = xFiles + xIndex;
- break;
- }
- }
- if( ( pxResult == NULL ) && ( eAction == eCACHE_ADD ) && ( xFreeIndex >= 0 ) )
- {
- pxResult = xFiles + xFreeIndex;
- snprintf( pxResult->pcFileName, sizeof( pxResult->pcFileName ), "%s", pcFname );
- pxResult->ulFileLength = 0;
- pxResult->ulFilePointer = 0;
- }
- return pxResult;
- }
- BaseType_t xCheckDevicePath( const char * pcPath )
- {
- BaseType_t xDevLength;
- BaseType_t xPathLength;
- BaseType_t xIsDevice;
- xDevLength = sizeof( pcDevicePath ) - 1;
- xPathLength = strlen( pcPath );
- /* System "/dev" should not match with "/device/etc". */
- if( ( xPathLength >= xDevLength ) &&
- ( memcmp( pcDevicePath, pcPath, xDevLength ) == 0 ) &&
- ( ( pcPath[ xDevLength ] == '\0' ) || ( pcPath[ xDevLength ] == '/' ) ) )
- {
- xIsDevice = FF_DEV_CHAR_DEV;
- }
- else
- {
- xIsDevice = FF_DEV_NO_DEV;
- }
- return xIsDevice;
- }
- BaseType_t FF_Device_Open( const char * pcPath,
- FF_FILE * pxStream )
- {
- uint8_t ucIsDevice;
- ucIsDevice = xCheckDevicePath( pcPath );
- if( ucIsDevice != pdFALSE )
- {
- const char * pcBaseName = pcPath;
- if( memcmp( pcBaseName, pcDevicePath, sizeof( pcDevicePath ) - 1 ) == 0 )
- {
- pcBaseName = pcBaseName + sizeof( pcDevicePath );
- }
- pxStream->pxDevNode = pxFindFile( pcBaseName, eCACHE_ADD );
- if( pxStream->pxDevNode != NULL )
- {
- pxStream->pxDevNode->ulFilePointer = 0;
- if( ( pxStream->ucMode & ( FF_MODE_WRITE | FF_MODE_APPEND | FF_MODE_CREATE ) ) == 0 )
- {
- pxStream->ulFileSize = pxStream->pxDevNode->ulFileLength;
- }
- }
- }
- return ucIsDevice;
- }
- void FF_Device_Close( FF_FILE * pxStream )
- {
- if( pxStream->pxDevNode != NULL )
- {
- pxStream->ulFileSize = 0ul;
- pxStream->ulFilePointer = 0ul;
- }
- }
- size_t FF_Device_Read( void * pvBuf,
- size_t lSize,
- size_t lCount,
- FF_FILE * pxStream )
- {
- lCount *= lSize;
- return lCount;
- }
- size_t FF_Device_Write( const void * pvBuf,
- size_t lSize,
- size_t lCount,
- FF_FILE * pxStream )
- {
- lCount *= lSize;
- if( pxStream->pxDevNode != NULL )
- {
- pxStream->pxDevNode->ulFilePointer += lCount;
- if( pxStream->pxDevNode->ulFileLength < pxStream->pxDevNode->ulFilePointer )
- {
- pxStream->pxDevNode->ulFileLength = pxStream->pxDevNode->ulFilePointer;
- }
- }
- return lCount;
- }
- int FF_Device_Seek( FF_FILE * pxStream,
- long lOffset,
- int iWhence )
- {
- if( pxStream->pxDevNode != NULL )
- {
- if( iWhence == FF_SEEK_SET )
- {
- pxStream->pxDevNode->ulFilePointer = lOffset;
- }
- else if( iWhence == FF_SEEK_END )
- {
- pxStream->pxDevNode->ulFilePointer = pxStream->pxDevNode->ulFileLength - lOffset;
- }
- }
- return 0;
- }
- int FF_Device_GetDirEnt( const char * pcPath,
- FF_DirEnt_t * pxDirEnt )
- {
- BaseType_t xIsDotDir = 0;
- if( pxDirEnt->pcFileName[ 0 ] == '.' )
- {
- if( ( pxDirEnt->pcFileName[ 1 ] == '.' ) &&
- ( pxDirEnt->pcFileName[ 2 ] == '\0' ) )
- {
- xIsDotDir = 2;
- }
- else if( pxDirEnt->pcFileName[ 1 ] == '\0' )
- {
- xIsDotDir = 1;
- }
- }
- if( xIsDotDir == 0 )
- {
- struct SFileCache * pxDevNode;
- pxDevNode = pxFindFile( pxDirEnt->pcFileName, eCACHE_LOOKUP );
- pxDirEnt->ucIsDeviceDir = FF_DEV_CHAR_DEV;
- if( pxDevNode != NULL )
- {
- pxDirEnt->ulFileSize = pxDevNode->ulFileLength;
- }
- else if( pxDirEnt->ulFileSize < 2048 )
- {
- pxDirEnt->ulFileSize = 2048;
- }
- }
- return 1024;
- }
|