Browse code

Add source code of the firmware for the IO Board

Pawel Jablonski authored on 05/06/2023 17:01:27
Showing 1 changed files
1 1
new file mode 100644
... ...
@@ -0,0 +1,283 @@
1
+/*
2
+ * Author: Pawel Jablonski
3
+ * E-mail: pj@xirx.net
4
+ * WWW: xirx.net
5
+ * GIT: git.xirx.net
6
+ *
7
+ * License: You can use this code however you like
8
+ * but leave information about the original author.
9
+ * Code is free for non-commercial and commercial use.
10
+ */
11
+
12
+#include "fatfs/ff_gen_drv.h"
13
+
14
+#include "type.h"
15
+#include "flash.h"
16
+
17
+#include "fs.h"
18
+
19
+//! File system block type list
20
+enum FSReadBlockType
21
+{
22
+	FS_READ_BLOCK_UNKNOWN = 0, //!< Unknown type
23
+	FS_READ_BLOCK_FILE, //!< File type
24
+	FS_READ_BLOCK_DIR, //!< Directory type
25
+};
26
+
27
+static void fsMakePath(char *path, const char *dirName, const char *fileName);
28
+
29
+static DSTATUS fsFatInit(BYTE pdrv);
30
+static DSTATUS fsFatGetStatus(BYTE pdrv);
31
+static DRESULT fsFatRead(BYTE pdrv, BYTE *buf, DWORD sector, UINT count);
32
+
33
+//! File system handlers to functions
34
+static Diskio_drvTypeDef fatDriver =
35
+{
36
+	fsFatInit,
37
+	fsFatGetStatus,
38
+	fsFatRead
39
+};
40
+
41
+static char fatDiskPath[4]; //!< Path to the FAT file system
42
+static FATFS fatFS; //!< Descriptor of the FAT file system
43
+
44
+static FRESULT fatMountStatus = FR_NOT_READY; //!< Mount status of the physical drive
45
+static FRESULT fatOpenStatus = FR_NOT_READY; //!< Open status of the file
46
+
47
+static FIL fatFile; //!< Descriptor of the file
48
+
49
+static int readBlockType = FS_READ_BLOCK_UNKNOWN; //!< Type of reading block
50
+
51
+static unsigned char dirBuffer[FS_DIR_ENTRY_SIZE * FS_DIR_MAX_QUANTITY]; //!< Directory entrys buffer
52
+
53
+//! Init file system and set up the FAT
54
+void fsInit(void)
55
+{
56
+	if(!FATFS_LinkDriver(&fatDriver, fatDiskPath))
57
+	{
58
+		fatMountStatus = f_mount(&fatFS, fatDiskPath, 1);
59
+	}
60
+}
61
+
62
+/**
63
+ * Open a file from the file system
64
+ *
65
+ * @param dirName Name of the directory. "app" or "file".
66
+ * @param fileName Name of the file to open
67
+ * @param size Struct where size of the file will be written
68
+ *
69
+ * @return Status of the open operation
70
+ */
71
+bool fsOpen(const char *dirName, const struct FSName *fileName, struct FSSize *size)
72
+{
73
+	size->low = 0;
74
+	size->high = 0;
75
+	
76
+	readBlockType = FS_READ_BLOCK_FILE;
77
+	
78
+	if(!fatMountStatus)
79
+	{
80
+		char path[FS_PATH_MAX_LENGTH + 1];
81
+		
82
+		fsMakePath(path, dirName, (const char *)(fileName->data));
83
+		
84
+		fatOpenStatus = f_open(&fatFile, path, FA_READ);
85
+		
86
+		if(!fatOpenStatus)
87
+		{
88
+			DWORD fileSize = f_size(&fatFile);
89
+			
90
+			size->low = (fileSize % 256);
91
+			size->high = ((fileSize / 256) & 0xff);
92
+			
93
+			return(TRUE);
94
+		}
95
+	}
96
+
97
+	return(FALSE);
98
+}
99
+
100
+/**
101
+ * Create a list of files in the directory from the file system
102
+ *
103
+ * @param dirName Name of the directory. "app" or "file".
104
+ * @param size Struct where size of the buffer with description of the files will be written
105
+ *
106
+ * @return Status of the list operation
107
+ */
108
+bool fsList(const char *dirName, struct FSSize *size)
109
+{
110
+	size->low = 0;
111
+	size->high = 0;
112
+	
113
+	readBlockType = FS_READ_BLOCK_DIR;
114
+	
115
+	if(!fatMountStatus)
116
+	{
117
+		char path[FS_PATH_MAX_LENGTH + 1];
118
+		DIR dir;
119
+		FILINFO info;
120
+		
121
+		fsMakePath(path, dirName, NULL);
122
+		
123
+		if(!f_opendir(&dir, path))
124
+		{
125
+			int dirSize = 0;
126
+			
127
+			while(1)
128
+			{
129
+				if(f_readdir(&dir, &info) != FR_OK)
130
+				{
131
+					break;
132
+				}
133
+				
134
+				if(info.fname[0] == 0)
135
+				{
136
+					break;
137
+				}
138
+				
139
+				for(int i = 0; i < FS_NAME_MAX_LENGTH; i++)
140
+				{
141
+					dirBuffer[dirSize + i] = info.fname[i];
142
+				}
143
+				
144
+				dirBuffer[dirSize + FS_NAME_MAX_LENGTH] = 0;
145
+				
146
+				dirBuffer[dirSize + FS_DIR_ENTRY_SIZE - 2] = (info.fsize % 256);
147
+				dirBuffer[dirSize + FS_DIR_ENTRY_SIZE - 1] = ((info.fsize / 256) & 0xff);
148
+				
149
+				dirSize += FS_DIR_ENTRY_SIZE;
150
+				
151
+				if(dirSize >= (FS_DIR_ENTRY_SIZE * FS_DIR_MAX_QUANTITY))
152
+				{
153
+					break;
154
+				}
155
+			}
156
+			
157
+			size->low = ((dirSize) % 256);
158
+			size->high = (((dirSize) / 256) & 0xff);
159
+			
160
+			return(TRUE);
161
+		}
162
+	}
163
+	
164
+	return(FALSE);
165
+}
166
+
167
+/**
168
+ * Read data from buffer to block based on offset
169
+ *
170
+ * @param block Struct where the data from the buffer will be written
171
+ * @param number Number of the block selected to read
172
+ */
173
+void fsReadBlock(struct FSBlock *block, int number)
174
+{
175
+	if((!fatMountStatus) && (!fatOpenStatus))
176
+	{
177
+		if(readBlockType == FS_READ_BLOCK_FILE)
178
+		{
179
+			if(!f_lseek(&fatFile, (number * FS_BLOCK_SIZE)))
180
+			{
181
+				UINT read;
182
+				
183
+				f_read(&fatFile, block->data, 256, &read);
184
+			}
185
+		}
186
+		else if(readBlockType == FS_READ_BLOCK_DIR)
187
+		{
188
+			for(int i = 0; i < FS_BLOCK_SIZE; i++)
189
+			{
190
+				block->data[i] = 0;
191
+			}
192
+			
193
+			if(((number * FS_BLOCK_SIZE) / FS_DIR_ENTRY_SIZE) < (FS_DIR_MAX_QUANTITY))
194
+			{
195
+				int offset = (number * FS_BLOCK_SIZE);
196
+				
197
+				for(int i = 0; i < FS_BLOCK_SIZE; i++)
198
+				{
199
+					block->data[i] = dirBuffer[offset + i];
200
+				}
201
+			}	
202
+		}
203
+	}
204
+}
205
+
206
+/**
207
+ * Generate a full path to file
208
+ *
209
+ * @param path Buffer to write
210
+ * @param dirName 
211
+ * @param fileName
212
+ */
213
+static void fsMakePath(char *path, const char *dirName, const char *fileName)
214
+{
215
+	path[0] = '/';
216
+	
217
+	int i = 1;
218
+	
219
+	for(int j = 0; dirName[j]; j++, i++)
220
+	{
221
+		path[i] = dirName[j];
222
+	}
223
+
224
+	if(fileName)
225
+	{
226
+		path[i] = '/';
227
+		i++;
228
+		
229
+		for(int j = 0; fileName[j]; j++, i++)
230
+		{
231
+			path[i] = fileName[j];
232
+		}
233
+	}
234
+
235
+	path[i] = 0;
236
+}
237
+
238
+/**
239
+ * Get status of init
240
+ *
241
+ * @param pdrv Physical drive number
242
+ *
243
+ * @return Status of init
244
+ */
245
+static DSTATUS fsFatInit(BYTE pdrv)
246
+{
247
+	return(0);
248
+}
249
+
250
+/**
251
+ * Get status of the physical drive
252
+ *
253
+ * @param pdrv Physical drive number
254
+ *
255
+ * @return Status of the physical drive
256
+ */
257
+static DSTATUS fsFatGetStatus(BYTE pdrv)
258
+{
259
+	return(0);
260
+}
261
+
262
+/**
263
+ * Read sector of the physical drive
264
+ *
265
+ * @param pdrv Physical drive number
266
+ * @param buf Buffer to write
267
+ * @param sector Sector number to read
268
+ * @param count Count of sectors to read
269
+ *
270
+ * @return Status of the reading process
271
+ */
272
+static DRESULT fsFatRead(BYTE pdrv, BYTE *buf, DWORD sector, UINT count)
273
+{
274
+	for(uint32_t i = 0; i < count; i++)
275
+	{
276
+		if(!flashRead((sector + i), (buf + (FLASH_SECTOR_SIZE * i))))
277
+		{
278
+			return(RES_ERROR);
279
+		}
280
+	}
281
+	
282
+	return(RES_OK);
283
+}