1. fat_fs_init

    fat_init()에서 호출하는 함수로 fat_length와 data_start를 수정해준다. sector_to_cluster는 디스크 섹터값을 클러스터 값으로 변환해 주는 함수이다. 아래에서 살펴 볼 cluster_to_sector의 반대 함수이다.

    /* fat.c */
    
    void
    fat_fs_init (void) {
    	/* TODO: Your code goes here. */
    	ASSERT(SECTORS_PER_CLUSTER == 1);
    
    	fat_fs ->data_start = fat_fs->bs.fat_start + fat_fs->bs.fat_sectors;
    	fat_fs->fat_length = sector_to_cluster(disk_size(filesys_disk)) - 1;
    }
    
    cluster_t 
    sector_to_cluster (disk_sector_t sector) {
    	ASSERT(sector >= fat_fs->data_start);
    
    	// sector 158 -> clst 1
    	return sector - fat_fs->data_start + 1;
    }
    
  2. fat_create_chain

    fat에 클러스터를 추가한다. 현재 클러스터들은 비트맵으로 관리하고 있다. get_empty_cluster를 통해 비어있는 클러스터를 할당 받아 fat에 추가해 준다. bitmap_scan_and_flip을 통해 연속된 사이즈만큼 할당 안된 비트를 찾아 값을 flip시키고 시작 번호를 반환한다. 1을 더해주는 이유는 클러스터가 1부터 시작이기 때문 인 것 같다.

    /* fat.c */
    
    cluster_t
    fat_create_chain (cluster_t clst) {
    	/* TODO: Your code goes here. */
    	cluster_t new_clst = get_empty_cluster();
    	if(new_clst != 0){
    		fat_put(new_clst,EOChain);
    		if(clst != 0){
    			fat_put(clst,new_clst);
    		}
    	}
    	return new_clst;
    }
    
    cluster_t get_empty_cluster(){
    	size_t clst = bitmap_scan_and_flip(fat_bitmap,0,1,false) + 1;
    
    	if(clst == BITMAP_ERROR)
    		return 0;
    	else
    		return (cluster_t) clst;
    }
    
  3. fat_remove_chain

    clst로 부터 시작하는 체인을 제거한다. 그래서 while 문을 돌며 비트맵의 해당 비트를 false로 설정해준다.

    void
    fat_remove_chain (cluster_t clst, cluster_t pclst) {
    	/* TODO: Your code goes here. */
    	while(clst && clst != EOChain){
    		bitmap_set(fat_bitmap, clst -1, false);
    		clst = fat_get(clst);
    	}
    	if(pclst != 0){
    		fat_put(pclst, EOChain);
    	}
    }
    
  4. fat_put

    fat 테이블의 값을 갱신한다. fat는 현재 비트맵으로 운용중이므로 비트를 확인 후 false라면 true로 갱신한다.

    void
    fat_put (cluster_t clst, cluster_t val) {
    	/* TODO: Your code goes here. */
    	ASSERT(clst >= 1);
    	if(!bitmap_test(fat_bitmap,clst-1)){
    		bitmap_mark(fat_bitmap,clst -1);
    	}
    	fat_fs->fat[clst -1] = val;
    }
    
  5. fat_get

    fat 테이블의 값을 반환한다.

    cluster_t
    fat_get (cluster_t clst) {
    	/* TODO: Your code goes here. */
    	ASSERT(clst >= 1);
    
    	if(clst > fat_fs->fat_length || !bitmap_test(fat_bitmap,clst-1)){
    		return 0;
    	}
    	return fat_fs->fat[clst-1];
    }
    
  6. cluster_to_sector

    클러스터 번호를 섹터 번호로 변환하여 반환한다.

    disk_sector_t
    cluster_to_sector (cluster_t clst) {
    	/* TODO: Your code goes here. */
    	ASSERT(clst >=1);
    
    	// clst 1 -> sector 158 (fat_fs->data_start)
    	return fat_fs->data_start + (clst - 1) * SECTORS_PER_CLUSTER;
    }