Jump to content

    
Sign in to follow this  
bnb62

FATFS

Recommended Posts

if(f_mount(&SDFatFs,(TCHAR const*)USERPath,0)!=FR_OK)
	{
		Error_Handler();
	}
//	else
//	{
	
//		FRESULT f_stat (const TCHAR* path, FILINFO* fno);					/* Get file status */
	
			//read dir
//		fileInfo.fname = (char *)sect;
		fileInfo.fsize = sizeof(sect);
			
		res = f_opendir(&dir, "/");
		if (res == FR_OK)
		{
			
			while(1)
			{
				res = f_readdir(&dir, &fileInfo);
				if (res==FR_OK && fileInfo.fname[0])
				{
					fn = fileInfo.fname;
					if(strlen(fn)) HAL_UART_Transmit(&huart2,(uint8_t*)fn,strlen(fn),0x1000);
					//else
					//	HAL_UART_Transmit(&huart2,(uint8_t*)fileInfo.lfname,strlen((char*)fileInfo.lfname),0x1000);
					

					DWORD size = fileInfo.fsize;
					WORD data_f = fileInfo.fdate;
					WORD time_f = fileInfo.ftime;
					
					if(data_f >= prev_data_f ){
						if(time_f >prev_time_f){
							
								prev_time_f = time_f;
								prev_data_f = data_f;
								fn = fileInfo.fname; // (char *)! save name current file
								//names[12] = {'L','o','g','_',in/100%10+0x30,in/10%10+0x30,in%10+0x30,'.','t','x','t',NULL};
								for(uint8_t i=0;i<12;i++){
									names[i] = dir.fn[i]; //fileInfo.fname[i]; //fn[i];//
								}
						 }
					 }
					
//						sprintf(str1," : %1u %1u ",dat,tim);
//						HAL_UART_Transmit(&huart2,(uint8_t*)str1,strlen(str1),0x1000);
					
//					sprintf(str1,"  size: %1u",fileInfo.fsize);
//					HAL_UART_Transmit(&huart2,(uint8_t*)str1,strlen(str1),0x1000);
					
				if(fileInfo.fattrib&AM_DIR)
					{
						HAL_UART_Transmit(&huart2,(uint8_t*)"  [DIR]",7,0x1000);
					}					
				}
				else break;
				HAL_UART_Transmit(&huart2,(uint8_t*)"\r\n",2,0x1000);
			}
			
//			f_getfree("/", &fre_clust, &fs);
//			sprintf(str1,"fre_clust: %lu\r\n",fre_clust);
//			HAL_UART_Transmit(&huart2,(uint8_t*)str1,strlen(str1),0x1000);
//			sprintf(str1,"n_fatent: %lu\r\n",fs->n_fatent);
//			HAL_UART_Transmit(&huart2,(uint8_t*)str1,strlen(str1),0x1000);
//			sprintf(str1,"fs_csize: %d\r\n",fs->csize);
//			HAL_UART_Transmit(&huart2,(uint8_t*)str1,strlen(str1),0x1000);
//			tot_sect = (fs->n_fatent - 2) * fs->csize;
//			sprintf(str1,"tot_sect: %lu\r\n",tot_sect);
//			HAL_UART_Transmit(&huart2,(uint8_t*)str1,strlen(str1),0x1000);
//			fre_sect = fre_clust * fs->csize;
//			sprintf(str1,"fre_sect: %lu\r\n",fre_sect);
//			HAL_UART_Transmit(&huart2,(uint8_t*)str1,strlen(str1),0x1000);
//			sprintf(str1, "%lu KB total drive space.\r\n%lu KB available.\r\n",	fre_sect/2, tot_sect/2);
//			HAL_UART_Transmit(&huart2,(uint8_t*)str1,strlen(str1),0x1000);
//			
//			sprintf(str1,"Total: %u MB.", (uint32_t)(tot_sect/2000));
//				SSD1306_GotoXY(0,39);
//				SSD1306_Puts(str1, &Font_7x10, SSD1306_COLOR_WHITE);
//			sprintf(str1," Free: %u MB.", (uint32_t)(fre_sect/2000));
//				SSD1306_GotoXY(0,50);
//				SSD1306_Puts(str1, &Font_7x10, SSD1306_COLOR_WHITE);
//				SSD1306_UpdateScreen();
				//HAL_Delay(5000);
			//FATFS_UnLinkDriver(USERPath);
									
		f_closedir(&dir);
		}
		//FATFS_UnLinkDriver(USERPath);	
		
//		uint8_t in = ((names[4]-0x30)*100) + ((names[5]-0x30)*10) + (names[6]-0x30);
//		in++;
//		names[4] = in/100%10+0x30;
//		names[5] = in/10%10+0x30;
//		names[6] = in%10+0x30;
		HAL_UART_Transmit(&huart2,(uint8_t*)"\r\n",2,0x1000);
		HAL_UART_Transmit(&huart2,(uint8_t*)names,strlen(names),0x1000);
		
//			File_create();
			
	}	
	
	
		HAL_TIM_Encoder_Start(&htim4, TIM_CHANNEL_ALL);

Здравствуйте! 
Обращаюсь с надеждой получить информацию по работе с именами файлов в актуальной версии FATFS/ +stm32f7. Творю логгер данных с сохранением на microСD карточку HC, с перспективой  XC (128GB). STM32F765 (3 channels CAN). Реализовал всё: создание файлов, Time Stamp RTC. Сортировку файлов после включении или RST для продолжения записи в самый свежий файл... И, вот, в этой процедуре застрял. Не могу получить из структуры имя файла в байтовый массив, чтобы работать с ним - изменить порядковый номер в имени при достижении назначенного размера для создания нового файла или замены в самого старого. Всё как в видеорегистраторах. В ascii имени через преобразование сделал. Но не могу никак получить имя файла в массив. Имена Лонг не требуются. Достаточно и старого формата 8.3 - имена короткие и однообразные. Но... если выключаю поддержку длинных имен, то имя и расширение преобразуются в прописные символы... -заглавные. В библиотеке есть такое преобразование... но оно почему-то работает странно. Буду рад получить исходники примеров или уроки.   

Edited by bnb62
add code

Share this post


Link to post
Share on other sites

Здравствуйте.

Так вроде там структура FILINFO в которой массив с именем файла.

 

typedef struct {
	FSIZE_t	fsize;			/* File size */
	WORD	fdate;			/* Modified date */
	WORD	ftime;			/* Modified time */
	BYTE	fattrib;		/* File attribute */
#if _USE_LFN != 0
	TCHAR	altname[13];			/* Alternative file name */
	TCHAR	fname[_MAX_LFN + 1];	/* Primary file name */
#else
	TCHAR	fname[13];		/* File name */
#endif
} FILINFO;

Достаточно просто скопировать данные через memcpy или по элементно.

Edited by VladimirG

Share this post


Link to post
Share on other sites

Благодарю за отклик и путеуказание. Мне скоро 59, из них 50 с паяльником.   memcpy ? и как элементарно?  

Вот тут я копирую элементарно?

 

for(uint8_t i=0;i<12;i++){
									names[i] = dir.fn[i]; //fileInfo.fname[i]; //fn[i];//
								}

Только в имени файла не имя, а текст "System Volume Information". вернее его первые 12 символов.

Впрочем, спасибо! Займусь изучением структур указателей и ссылок. И указателей на указателей указателей ... блть, что-ж нам в асме не жилось? :-).

Share this post


Link to post
Share on other sites
2 hours ago, bnb62 said:

if (res==FR_OK && fileInfo.fname[0])

Тут лучше так

if (res==FR_OK && fileInfo.fname[0] != '\0')

 

 

2 hours ago, bnb62 said:

for(uint8_t i=0;i<12;i++){ names[i] = dir.fn[i]; //fileInfo.fname; //fn;// }

Тут как то так. С учётом того, что у вас не используються длинные имена.

uint8_t names[13];
for(uint8_t i=0;i<12;i++){
  names[i] = dir.fn[i];
}

 

2 hours ago, bnb62 said:

//names[12] = {'L','o','g','_',in/100%10+0x30,in/10%10+0x30,in%10+0x30,'.','t','x','t',NULL};

Этак конструкция мне не понятна, in/100%10+0x30, это вычисление символа?

тут не хватает обявления типа и размер не 12 а 13 байт.

 

23 minutes ago, bnb62 said:

Благодарю за отклик и путеуказание. Мне скоро 59, из них 50 с паяльником.   memcpy ? и как элементарно?  

Вот тут я копирую элементарно?

 


for(uint8_t i=0;i<12;i++){
									names[i] = dir.fn[i]; //fileInfo.fname[i]; //fn[i];//
								}

Только в имени файла не имя, а текст "System Volume Information". вернее его первые 12 символов.

Впрочем, спасибо! Займусь изучением структур указателей и ссылок. И указателей на указателей указателей ... блть, что-ж нам в асме не жилось? :-).

 
 
/* File attribute bits for directory entry (FILINFO.fattrib) */
#define AM_RDO 0x01 /* Read only */
#define AM_HID 0x02 /* Hidden */
#define AM_SYS 0x04 /* System */
#define AM_DIR 0x10 /* Directory */

#define AM_ARC 0x20 /* Archive */

Наверное вы забыли сравнить атрибут перед дейстивем с файлом, так как "System Volume Information" это директория.

Edited by VladimirG

Share this post


Link to post
Share on other sites

в последнем закомментированном фрагменте я явно присваивал имя файла с вставкой его переменной части in преобразованной в ascii. И это работало.

if (res==FR_OK && fileInfo.fname[0] != '\0')

Это мне непонятно. (обратный слэш). В копипасте откуда-то предполагалась проверка, что в нулевом байте массива имени не NULL. 

 

Edited by bnb62

Share this post


Link to post
Share on other sites
1 hour ago, VladimirG said:

 

Quote

Наверное вы забыли сравнить атрибут перед действием с файлом, так как "System Volume Information" это директория.

Это факт. Всё трудно даётся. Особенно когда надергал копипастом из чужих и устаревших "примеров", а библиотека-то обновилась... Придётся изучать... Огромное спасибо за ликбез! А так же, великому энтузиасту  http://microsin.net/programming/file-systems/fatfs-file-system.html

 

Edited by bnb62

Share this post


Link to post
Share on other sites
2 часа назад, bnb62 сказал:

Вот тут я копирую элементарно?


for(uint8_t i=0;i<12;i++){
									names[i] = dir.fn[i]; //fileInfo.fname[i]; //fn[i];//
								}

 

Зачем в счётчике цикла uint8_t? В счётчиках цикла на ARM лучше всего использовать int или uint.

Так оптимальнее:

#define ncell(m) (sizeof(m) / sizeof((m)[0]))
uint8_t names[ncell(dir.fn)];
int i = ncell(dir.fn) - 1;
do names[i] = dir.fn[i];
while (--i >= 0);

Share this post


Link to post
Share on other sites

Должен добавить для интересующихся темой, что актуальная библия FATFS обновилась так же в STM32 MX CUBE - добавлены полезные функции.

/* FatFs module application interface                           */

FRESULT f_open (FIL* fp, const TCHAR* path, BYTE mode);				/* Open or create a file */
FRESULT f_close (FIL* fp);											/* Close an open file object */
FRESULT f_read (FIL* fp, void* buff, UINT btr, UINT* br);			/* Read data from the file */
FRESULT f_write (FIL* fp, const void* buff, UINT btw, UINT* bw);	/* Write data to the file */
FRESULT f_lseek (FIL* fp, FSIZE_t ofs);								/* Move file pointer of the file object */
FRESULT f_truncate (FIL* fp);										/* Truncate the file */
FRESULT f_sync (FIL* fp);											/* Flush cached data of the writing file */
FRESULT f_opendir (DIR* dp, const TCHAR* path);						/* Open a directory */
FRESULT f_closedir (DIR* dp);										/* Close an open directory */
FRESULT f_readdir (DIR* dp, FILINFO* fno);							/* Read a directory item */
FRESULT f_findfirst (DIR* dp, FILINFO* fno, const TCHAR* path, const TCHAR* pattern);	/* Find first file */
FRESULT f_findnext (DIR* dp, FILINFO* fno);							/* Find next file */
FRESULT f_mkdir (const TCHAR* path);								/* Create a sub directory */
FRESULT f_unlink (const TCHAR* path);								/* Delete an existing file or directory */
FRESULT f_rename (const TCHAR* path_old, const TCHAR* path_new);	/* Rename/Move a file or directory */
FRESULT f_stat (const TCHAR* path, FILINFO* fno);					/* Get file status */
FRESULT f_chmod (const TCHAR* path, BYTE attr, BYTE mask);			/* Change attribute of a file/dir */
FRESULT f_utime (const TCHAR* path, const FILINFO* fno);			/* Change timestamp of a file/dir */
FRESULT f_chdir (const TCHAR* path);								/* Change current directory */
FRESULT f_chdrive (const TCHAR* path);								/* Change current drive */
FRESULT f_getcwd (TCHAR* buff, UINT len);							/* Get current directory */
FRESULT f_getfree (const TCHAR* path, DWORD* nclst, FATFS** fatfs);	/* Get number of free clusters on the drive */
FRESULT f_getlabel (const TCHAR* path, TCHAR* label, DWORD* vsn);	/* Get volume label */
FRESULT f_setlabel (const TCHAR* label);							/* Set volume label */
FRESULT f_forward (FIL* fp, UINT(*func)(const BYTE*,UINT), UINT btf, UINT* bf);	/* Forward data to the stream */
FRESULT f_expand (FIL* fp, FSIZE_t szf, BYTE opt);					/* Allocate a contiguous block to the file */
FRESULT f_mount (FATFS* fs, const TCHAR* path, BYTE opt);			/* Mount/Unmount a logical drive */
FRESULT f_mkfs (const TCHAR* path, BYTE opt, DWORD au, void* work, UINT len);	/* Create a FAT volume */
FRESULT f_fdisk (BYTE pdrv, const DWORD* szt, void* work);			/* Divide a physical drive into some partitions */
int f_putc (TCHAR c, FIL* fp);										/* Put a character to the file */
int f_puts (const TCHAR* str, FIL* cp);								/* Put a string to the file */
int f_printf (FIL* fp, const TCHAR* str, ...);						/* Put a formatted string to the file */
TCHAR* f_gets (TCHAR* buff, int len, FIL* fp);						/* Get a string from the file */

#define f_eof(fp) ((int)((fp)->fptr == (fp)->obj.objsize))
#define f_error(fp) ((fp)->err)
#define f_tell(fp) ((fp)->fptr)
#define f_size(fp) ((fp)->obj.objsize)
#define f_rewind(fp) f_lseek((fp), 0)
#define f_rewinddir(dp) f_readdir((dp), 0)
#define f_rmdir(path) f_unlink(path)

#ifndef EOF
#define EOF (-1)
#endif

 

9 hours ago, bnb62 said:

 

 

 

Edited by bnb62

Share this post


Link to post
Share on other sites

Join the conversation

You can post now and register later. If you have an account, sign in now to post with your account.

Guest
Reply to this topic...

×   Pasted as rich text.   Paste as plain text instead

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   Your previous content has been restored.   Clear editor

×   You cannot paste images directly. Upload or insert images from URL.

Sign in to follow this