Norimasa Okamoto / F32RFileSystem

Fork of F12RFileSystem by Norimasa Okamoto

Committer:
va009039
Date:
Wed Nov 11 19:47:04 2015 +0900
Revision:
7:f9f52d9c0c57
Parent:
6:3c5b3606e019
first commit F12RFileSystem

Who changed what in which revision?

UserRevisionLine numberNew contents of line
va009039 7:f9f52d9c0c57 1 /* mbed Microcontroller Library
va009039 7:f9f52d9c0c57 2 * Copyright (c) 2006-2016 ARM Limited
va009039 7:f9f52d9c0c57 3 *
va009039 7:f9f52d9c0c57 4 * Permission is hereby granted, free of charge, to any person obtaining a copy
va009039 7:f9f52d9c0c57 5 * of this software and associated documentation files (the "Software"), to deal
va009039 7:f9f52d9c0c57 6 * in the Software without restriction, including without limitation the rights
va009039 7:f9f52d9c0c57 7 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
va009039 7:f9f52d9c0c57 8 * copies of the Software, and to permit persons to whom the Software is
va009039 7:f9f52d9c0c57 9 * furnished to do so, subject to the following conditions:
va009039 7:f9f52d9c0c57 10 *
va009039 7:f9f52d9c0c57 11 * The above copyright notice and this permission notice shall be included in
va009039 7:f9f52d9c0c57 12 * all copies or substantial portions of the Software.
va009039 7:f9f52d9c0c57 13 *
va009039 7:f9f52d9c0c57 14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
va009039 7:f9f52d9c0c57 15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
va009039 7:f9f52d9c0c57 16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
va009039 7:f9f52d9c0c57 17 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
va009039 7:f9f52d9c0c57 18 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
va009039 7:f9f52d9c0c57 19 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
va009039 7:f9f52d9c0c57 20 * SOFTWARE.
va009039 7:f9f52d9c0c57 21 */
va009039 7:f9f52d9c0c57 22 #include "F12RFileSystem.h"
va009039 7:f9f52d9c0c57 23 #include "F12RFileHandle.h"
va009039 7:f9f52d9c0c57 24 #include "F12RDirHandle.h"
va009039 7:f9f52d9c0c57 25 #include "fsdebug.h"
va009039 7:f9f52d9c0c57 26
va009039 7:f9f52d9c0c57 27 F12RFileSystem::F12RFileSystem(StorageInterface* storage_, const char* n)
va009039 7:f9f52d9c0c57 28 : FileSystemLike(n), storage(storage_), mounted(false) {
va009039 7:f9f52d9c0c57 29 }
va009039 7:f9f52d9c0c57 30
va009039 7:f9f52d9c0c57 31 F12RFileSystem::~F12RFileSystem() {
va009039 7:f9f52d9c0c57 32 }
va009039 7:f9f52d9c0c57 33
va009039 7:f9f52d9c0c57 34 static bool to_sfn(const char* name, uint8_t* buf) {
va009039 7:f9f52d9c0c57 35 memset(buf, '\x20', 8+3);
va009039 7:f9f52d9c0c57 36 for(int i = 0; i < 8; i++) {
va009039 7:f9f52d9c0c57 37 char c = *name++;
va009039 7:f9f52d9c0c57 38 if (c == '\0') {
va009039 7:f9f52d9c0c57 39 return true;
va009039 7:f9f52d9c0c57 40 } else if (c == '.') {
va009039 7:f9f52d9c0c57 41 break;
va009039 7:f9f52d9c0c57 42 } else {
va009039 7:f9f52d9c0c57 43 buf[i] = toupper(c);
va009039 7:f9f52d9c0c57 44 }
va009039 7:f9f52d9c0c57 45 }
va009039 7:f9f52d9c0c57 46 for(int i = 8; i < 11; i++) {
va009039 7:f9f52d9c0c57 47 char c = *name++;
va009039 7:f9f52d9c0c57 48 if (c == '\0') {
va009039 7:f9f52d9c0c57 49 break;
va009039 7:f9f52d9c0c57 50 } else {
va009039 7:f9f52d9c0c57 51 buf[i] = toupper(c);
va009039 7:f9f52d9c0c57 52 }
va009039 7:f9f52d9c0c57 53 }
va009039 7:f9f52d9c0c57 54 return true;
va009039 7:f9f52d9c0c57 55 }
va009039 7:f9f52d9c0c57 56
va009039 7:f9f52d9c0c57 57 FileHandle *F12RFileSystem::open(const char* name, int flags) {
va009039 7:f9f52d9c0c57 58 FS_DBG("name=[%s] flags=%d", name, flags);
va009039 7:f9f52d9c0c57 59 if (mount() != 0) {
va009039 7:f9f52d9c0c57 60 return NULL;
va009039 7:f9f52d9c0c57 61 }
va009039 7:f9f52d9c0c57 62
va009039 7:f9f52d9c0c57 63 #if 1
va009039 7:f9f52d9c0c57 64 uint8_t fat12[16];
va009039 7:f9f52d9c0c57 65 storage->storage_read(base_fat * 512, fat12, sizeof(fat12));
va009039 7:f9f52d9c0c57 66 FS_DBG_HEX(fat12, sizeof(fat12));
va009039 7:f9f52d9c0c57 67 #endif
va009039 7:f9f52d9c0c57 68
va009039 7:f9f52d9c0c57 69 uint8_t sfn[8+3];
va009039 7:f9f52d9c0c57 70 to_sfn(name, sfn);
va009039 7:f9f52d9c0c57 71 for(int i = 0; i < max_root_dir_entries; i++) {
va009039 7:f9f52d9c0c57 72 uint8_t buf[sizeof(sfn)];
va009039 7:f9f52d9c0c57 73 storage->storage_read(base_dir * 512 + i * 32, buf, sizeof(buf));
va009039 7:f9f52d9c0c57 74 FS_DBG_HEX(buf, sizeof(buf));
va009039 7:f9f52d9c0c57 75 if (buf[0] == 0x00) {
va009039 7:f9f52d9c0c57 76 return NULL;
va009039 7:f9f52d9c0c57 77 } else if (memcmp(buf, sfn, sizeof(sfn)) == 0) {
va009039 7:f9f52d9c0c57 78 return new F12RFileHandle(*this, base_dir * 512 + i * 32);
va009039 7:f9f52d9c0c57 79 }
va009039 7:f9f52d9c0c57 80 }
va009039 7:f9f52d9c0c57 81 return NULL;
va009039 7:f9f52d9c0c57 82 }
va009039 7:f9f52d9c0c57 83
va009039 7:f9f52d9c0c57 84 int F12RFileSystem::remove(const char *filename) {
va009039 7:f9f52d9c0c57 85 return -1;
va009039 7:f9f52d9c0c57 86 }
va009039 7:f9f52d9c0c57 87
va009039 7:f9f52d9c0c57 88 int F12RFileSystem::rename(const char *oldname, const char *newname) {
va009039 7:f9f52d9c0c57 89 return -1;
va009039 7:f9f52d9c0c57 90 }
va009039 7:f9f52d9c0c57 91
va009039 7:f9f52d9c0c57 92 int F12RFileSystem::format() {
va009039 7:f9f52d9c0c57 93 return -1;
va009039 7:f9f52d9c0c57 94 }
va009039 7:f9f52d9c0c57 95
va009039 7:f9f52d9c0c57 96 DirHandle *F12RFileSystem::opendir(const char *name) {
va009039 7:f9f52d9c0c57 97 FS_DBG("name=[%s]", name);
va009039 7:f9f52d9c0c57 98
va009039 7:f9f52d9c0c57 99 if (mount() != 0) {
va009039 7:f9f52d9c0c57 100 return NULL;
va009039 7:f9f52d9c0c57 101 }
va009039 7:f9f52d9c0c57 102 return new F12RDirHandle(*this);
va009039 7:f9f52d9c0c57 103 }
va009039 7:f9f52d9c0c57 104
va009039 7:f9f52d9c0c57 105 int F12RFileSystem::mkdir(const char *name, mode_t mode) {
va009039 7:f9f52d9c0c57 106 return -1;
va009039 7:f9f52d9c0c57 107 }
va009039 7:f9f52d9c0c57 108
va009039 7:f9f52d9c0c57 109 int F12RFileSystem::mount() {
va009039 7:f9f52d9c0c57 110 #if 1
va009039 7:f9f52d9c0c57 111 uint8_t buf[512];
va009039 7:f9f52d9c0c57 112 storage->storage_read(0, buf, sizeof(buf));
va009039 7:f9f52d9c0c57 113 FS_DBG_HEX(buf, sizeof(buf));
va009039 7:f9f52d9c0c57 114 #endif
va009039 7:f9f52d9c0c57 115
va009039 7:f9f52d9c0c57 116 if (storage_peek(0 * 512 + 510, 2) != 0xaa55) {
va009039 7:f9f52d9c0c57 117 return -1;
va009039 7:f9f52d9c0c57 118 }
va009039 7:f9f52d9c0c57 119 uint32_t lba_offset = 0;
va009039 7:f9f52d9c0c57 120 struct { // +446
va009039 7:f9f52d9c0c57 121 uint8_t flag; // +0
va009039 7:f9f52d9c0c57 122 uint8_t first_sector_chs[3]; // +1
va009039 7:f9f52d9c0c57 123 uint8_t type; // +4
va009039 7:f9f52d9c0c57 124 uint8_t last_sector_chs[3]; // +5
va009039 7:f9f52d9c0c57 125 uint32_t sector_start; // +8
va009039 7:f9f52d9c0c57 126 uint32_t sector_count; // +12
va009039 7:f9f52d9c0c57 127 } partition_entry;
va009039 7:f9f52d9c0c57 128 storage->storage_read(446, (uint8_t*)&partition_entry, sizeof(partition_entry));
va009039 7:f9f52d9c0c57 129 if (partition_entry.type == 0x01) {
va009039 7:f9f52d9c0c57 130 lba_offset = partition_entry.sector_start;
va009039 7:f9f52d9c0c57 131 if (storage_peek(lba_offset * 512 + 510, 2) != 0xaa55) {
va009039 7:f9f52d9c0c57 132 return -1;
va009039 7:f9f52d9c0c57 133 }
va009039 7:f9f52d9c0c57 134 }
va009039 7:f9f52d9c0c57 135
va009039 7:f9f52d9c0c57 136 #if 1
va009039 7:f9f52d9c0c57 137 FS_DBG("lba_offset=%d", lba_offset);
va009039 7:f9f52d9c0c57 138 storage->storage_read(lba_offset * 512, buf, sizeof(buf));
va009039 7:f9f52d9c0c57 139 FS_DBG_HEX(buf, sizeof(buf));
va009039 7:f9f52d9c0c57 140 #endif
va009039 7:f9f52d9c0c57 141
va009039 7:f9f52d9c0c57 142 if (storage_peek(lba_offset * 512 + 11, 2) != 512) {
va009039 7:f9f52d9c0c57 143 return -1;
va009039 7:f9f52d9c0c57 144 }
va009039 7:f9f52d9c0c57 145 cluster_size = storage_peek(lba_offset * 512 + 13, 1) * 512;
va009039 7:f9f52d9c0c57 146 sector_t number_of_reserved_sectors = storage_peek(lba_offset * 512 + 14, 2);
va009039 7:f9f52d9c0c57 147 base_fat = lba_offset + number_of_reserved_sectors;
va009039 7:f9f52d9c0c57 148 int number_of_fats = storage_peek(lba_offset * 512 + 16, 2);
va009039 7:f9f52d9c0c57 149 max_root_dir_entries = storage_peek(lba_offset * 512 + 17, 2);
va009039 7:f9f52d9c0c57 150 sector_t total_logical_sectors = storage_peek(lba_offset * 512 + 19, 2);
va009039 7:f9f52d9c0c57 151 sector_t logical_sectors_per_fat = storage_peek(lba_offset * 512 + 22, 2);
va009039 7:f9f52d9c0c57 152 base_dir = base_fat + logical_sectors_per_fat * number_of_fats;
va009039 7:f9f52d9c0c57 153 base_data = base_dir + (max_root_dir_entries * 32 + 511) / 512;
va009039 7:f9f52d9c0c57 154
va009039 7:f9f52d9c0c57 155 FS_DBG("number_of_reserved_sectors=%d", number_of_reserved_sectors);
va009039 7:f9f52d9c0c57 156 FS_DBG("number_of_fats=%d", number_of_fats);
va009039 7:f9f52d9c0c57 157 FS_DBG("max_root_dir_entries=%d", max_root_dir_entries);
va009039 7:f9f52d9c0c57 158 FS_DBG("total_logical_sectors=%d", total_logical_sectors);
va009039 7:f9f52d9c0c57 159 FS_DBG("logical_sectors_per_fat=%d", logical_sectors_per_fat);
va009039 7:f9f52d9c0c57 160
va009039 7:f9f52d9c0c57 161 FS_DBG("cluster_size=%d", cluster_size);
va009039 7:f9f52d9c0c57 162 FS_DBG("base_fat=%d", base_fat);
va009039 7:f9f52d9c0c57 163 FS_DBG("base_dir=%d", base_dir);
va009039 7:f9f52d9c0c57 164 FS_DBG("base_data=%d", base_data);
va009039 7:f9f52d9c0c57 165
va009039 7:f9f52d9c0c57 166 mounted = true;
va009039 7:f9f52d9c0c57 167 return 0;
va009039 7:f9f52d9c0c57 168 }
va009039 7:f9f52d9c0c57 169
va009039 7:f9f52d9c0c57 170 int F12RFileSystem::unmount() {
va009039 7:f9f52d9c0c57 171 mounted = false;
va009039 7:f9f52d9c0c57 172 return 0;
va009039 7:f9f52d9c0c57 173 }
va009039 7:f9f52d9c0c57 174
va009039 7:f9f52d9c0c57 175 uint32_t F12RFileSystem::storage_peek(uint32_t offset, int n) {
va009039 7:f9f52d9c0c57 176 uint8_t buf[n];
va009039 7:f9f52d9c0c57 177 storage->storage_read(offset, buf, sizeof(buf));
va009039 7:f9f52d9c0c57 178 uint32_t val = 0;
va009039 7:f9f52d9c0c57 179 for(int i = 0; i < n; i++) {
va009039 7:f9f52d9c0c57 180 val |= buf[i]<<(i*8);
va009039 7:f9f52d9c0c57 181 }
va009039 7:f9f52d9c0c57 182 return val;
va009039 7:f9f52d9c0c57 183 }
va009039 7:f9f52d9c0c57 184
va009039 7:f9f52d9c0c57 185 cluster_t F12RFileSystem::fat_read(cluster_t index) {
va009039 7:f9f52d9c0c57 186 int i = index / 2 * 3 + (index&1);
va009039 7:f9f52d9c0c57 187 cluster_t next = storage_peek(base_fat*512 + i, 2);
va009039 7:f9f52d9c0c57 188 if (index & 1) {
va009039 7:f9f52d9c0c57 189 next >>= 4;
va009039 7:f9f52d9c0c57 190 } else {
va009039 7:f9f52d9c0c57 191 next &= 0xfff;
va009039 7:f9f52d9c0c57 192 }
va009039 7:f9f52d9c0c57 193 return next;
va009039 7:f9f52d9c0c57 194 }
va009039 7:f9f52d9c0c57 195