/* SPDX-License-Identifier: GPL-2.0-or-later */ /* * Copyright (C) 2020 Hyunchul Lee */ #ifndef _FSCK_H #define _FSCK_H #include "list.h" typedef __u32 clus_t; struct exfat_inode { struct exfat_inode *parent; struct list_head children; struct list_head sibling; struct list_head list; clus_t first_clus; clus_t last_lclus; clus_t last_pclus; __u16 attr; uint64_t size; bool is_contiguous; __le16 name[0]; /* only for directory */ }; #define EXFAT_NAME_MAX 255 #define NAME_BUFFER_SIZE ((EXFAT_NAME_MAX+1)*2) struct buffer_desc { clus_t p_clus; unsigned int offset; char *buffer; char *dirty; }; struct exfat_de_iter { struct exfat *exfat; struct exfat_inode *parent; struct buffer_desc *buffer_desc; /* cluster * 2 */ clus_t ra_next_clus; unsigned int ra_begin_offset; unsigned int ra_partial_size; unsigned int read_size; /* cluster size */ unsigned int write_size; /* sector size */ off_t de_file_offset; off_t next_read_offset; int max_skip_dentries; }; enum fsck_ui_options { FSCK_OPTS_REPAIR_ASK = 0x01, FSCK_OPTS_REPAIR_YES = 0x02, FSCK_OPTS_REPAIR_NO = 0x04, FSCK_OPTS_REPAIR_AUTO = 0x08, FSCK_OPTS_REPAIR_WRITE = 0x0b, FSCK_OPTS_REPAIR_ALL = 0x0f, }; struct exfat { enum fsck_ui_options options; bool dirty:1; bool dirty_fat:1; struct exfat_blk_dev *blk_dev; struct pbr *bs; char volume_label[VOLUME_LABEL_BUFFER_SIZE]; struct exfat_inode *root; struct list_head dir_list; clus_t clus_count; unsigned int clus_size; unsigned int sect_size; struct exfat_de_iter de_iter; struct buffer_desc buffer_desc[2]; /* cluster * 2 */ char *alloc_bitmap; char *disk_bitmap; clus_t disk_bitmap_clus; unsigned int disk_bitmap_size; }; #define EXFAT_CLUSTER_SIZE(pbr) (1 << ((pbr)->bsx.sect_size_bits + \ (pbr)->bsx.sect_per_clus_bits)) #define EXFAT_SECTOR_SIZE(pbr) (1 << (pbr)->bsx.sect_size_bits) /* fsck.c */ off_t exfat_c2o(struct exfat *exfat, unsigned int clus); int get_next_clus(struct exfat *exfat, struct exfat_inode *node, clus_t clus, clus_t *next); /* de_iter.c */ int exfat_de_iter_init(struct exfat_de_iter *iter, struct exfat *exfat, struct exfat_inode *dir); int exfat_de_iter_get(struct exfat_de_iter *iter, int ith, struct exfat_dentry **dentry); int exfat_de_iter_get_dirty(struct exfat_de_iter *iter, int ith, struct exfat_dentry **dentry); int exfat_de_iter_flush(struct exfat_de_iter *iter); int exfat_de_iter_advance(struct exfat_de_iter *iter, int skip_dentries); off_t exfat_de_iter_file_offset(struct exfat_de_iter *iter); #endif