uint32_t volume_id_read_file( struct volume_id *id, struct volume_id_file *file, int outfd) { struct libfat_filesystem *fs = id->fat; libfat_sector_t s = libfat_clustertosector(fs, file->cluster); uint32_t size = file->size; while (size) { if (s == 0) return -2; /* Not found */ else if (s == (libfat_sector_t) -1) return -1; /* Error */ uint8_t * block = libfat_get_sector(fs, s); if (!block) return -1; /* Read error */ uint32_t data = size > LIBFAT_SECTOR_SIZE ? LIBFAT_SECTOR_SIZE : size; // printf("Writing %d\n", data); write(outfd, block, data); size -= data; s = libfat_nextsector(fs, s); } ftruncate(outfd, file->size - size); return size; }
int32_t libfat_searchdir(struct libfat_filesystem *fs, int32_t dirclust, const void *name, struct libfat_direntry *direntry) { struct fat_dirent *dep; int nent; libfat_sector_t s = libfat_clustertosector(fs, dirclust); while (1) { if (s == 0) return -2; /* Not found */ else if (s == (libfat_sector_t) - 1) return -1; /* Error */ dep = libfat_get_sector(fs, s); if (!dep) return -1; /* Read error */ for (nent = 0; nent < LIBFAT_SECTOR_SIZE; nent += sizeof(struct fat_dirent)) { if (!memcmp(dep->name, name, 11)) { if (direntry) { memcpy(direntry->entry, dep, sizeof(*dep)); direntry->sector = s; direntry->offset = nent; } if (read32(&dep->size) == 0) return 0; /* An empty file has no clusters */ else return read16(&dep->clustlo) + (read16(&dep->clusthi) << 16); } if (dep->name[0] == 0) return -2; /* Hit high water mark */ dep++; } s = libfat_nextsector(fs, s); } }
int32_t volume_id_read_dir( struct libfat_filesystem *fs, int32_t dirclust, struct volume_id_dir * dir) { struct fat_dirent *dep; int nent; libfat_sector_t s = libfat_clustertosector(fs, dirclust); struct volume_id_file file; memset(&file, 0, sizeof(file)); while (1) { if (s == 0) return -2; /* Not found */ else if (s == (libfat_sector_t) -1) return -1; /* Error */ dep = libfat_get_sector(fs, s); if (!dep) return -1; /* Read error */ for (nent = 0; nent < LIBFAT_SECTOR_SIZE; nent += sizeof(struct fat_dirent), dep++) { if (dep->name[0] == 0) return dir->count; /* Hit high water mark */ if (dep->name[0] == FAT_ENTRY_FREE) continue; /* long name */ if ((dep->attribute & FAT_ATTR_MASK) == FAT_ATTR_LONG_NAME) { longname_extract((uint8_t*)dep, file.longname); continue; } if ((dep->attribute & (FAT_ATTR_VOLUME_ID | FAT_ATTR_DIR)) == FAT_ATTR_VOLUME_ID) { /* labels do not have file data */ if (dep->clusthi != 0 || dep->clustlo != 0) continue; //res = dep->name; } shortname_extract((uint8_t*)dep, file.name); file.entry = *dep; file.sector = s; file.offset = nent; if ((file.size = read32(&dep->size)) == 0) file.cluster = 0; /* An empty file has no clusters */ else file.cluster = read16(&dep->clustlo) + (read16(&dep->clusthi) << 16); dir->entry = realloc(dir->entry, (dir->count+1) * sizeof(file)); dir->entry[dir->count++] = file; memset(&file, 0, sizeof(file)); } s = libfat_nextsector(fs, s); } return dir->count; }