static PedDisk* bsd_alloc (const PedDevice* dev) { PedDisk* disk; BSDDiskData* bsd_specific; BSDRawLabel* label; PED_ASSERT(dev->sector_size % PED_SECTOR_SIZE_DEFAULT == 0); disk = _ped_disk_alloc ((PedDevice*)dev, &bsd_disk_type); if (!disk) goto error; disk->disk_specific = bsd_specific = ped_malloc (sizeof (BSDDiskData)); if (!bsd_specific) goto error_free_disk; /* Initialize the first byte to zero, so that the code in bsd_write knows to call _probe_and_add_boot_code. Initializing all of the remaining buffer is a little wasteful, but the alternative is to figure out why a block at offset 340 would otherwise be used uninitialized. */ memset(bsd_specific->boot_code, 0, sizeof (bsd_specific->boot_code)); label = (BSDRawLabel*) (bsd_specific->boot_code + BSD_LABEL_OFFSET); label->d_magic = PED_CPU_TO_LE32 (BSD_DISKMAGIC); label->d_type = PED_CPU_TO_LE16 (BSD_DTYPE_SCSI); label->d_flags = 0; label->d_secsize = PED_CPU_TO_LE16 (dev->sector_size); label->d_nsectors = PED_CPU_TO_LE32 (dev->bios_geom.sectors); label->d_ntracks = PED_CPU_TO_LE32 (dev->bios_geom.heads); label->d_ncylinders = PED_CPU_TO_LE32 (dev->bios_geom.cylinders); label->d_secpercyl = PED_CPU_TO_LE32 (dev->bios_geom.sectors * dev->bios_geom.heads); label->d_secperunit = PED_CPU_TO_LE32 (dev->bios_geom.sectors * dev->bios_geom.heads * dev->bios_geom.cylinders); label->d_rpm = PED_CPU_TO_LE16 (3600); label->d_interleave = PED_CPU_TO_LE16 (1);; label->d_trackskew = 0; label->d_cylskew = 0; label->d_headswitch = 0; label->d_trkseek = 0; label->d_magic2 = PED_CPU_TO_LE32 (BSD_DISKMAGIC); label->d_bbsize = PED_CPU_TO_LE32 (BSD_BBSIZE); label->d_sbsize = PED_CPU_TO_LE32 (BSD_SBSIZE); label->d_npartitions = 0; label->d_checksum = xbsd_dkcksum (label); return disk; error_free_disk: free (disk); error: return NULL; }
int _gen_pmbr(legacy_mbr *pmbr) { memset(pmbr->partition_record, 0, sizeof(pmbr->partition_record)); *(unsigned short int*)pmbr->signature = PED_CPU_TO_LE16(MSDOS_MBR_SIGNATURE); _gen_pmbr_part(&pmbr->partition_record[0]); return 1; }
void fat_dir_entry_set_first_cluster (FatDirEntry* dir_entry, PedFileSystem* fs, FatCluster cluster) { FatSpecific* fs_info = FAT_SPECIFIC (fs); switch (fs_info->fat_type) { case FAT_TYPE_FAT12: PED_ASSERT (0); break; case FAT_TYPE_FAT16: dir_entry->first_cluster = PED_CPU_TO_LE16 (cluster); break; case FAT_TYPE_FAT32: dir_entry->first_cluster = PED_CPU_TO_LE16 (cluster & 0xffff); dir_entry->first_cluster_high = PED_CPU_TO_LE16 (cluster / 0x10000); break; } }
static int bsd_write (const PedDisk* disk) { BSDDiskData* bsd_specific; BSDRawLabel* label; BSDPartitionData* bsd_data; PedPartition* part; int i; int max_part = 0; PED_ASSERT (disk != NULL); PED_ASSERT (disk->dev != NULL); bsd_specific = (BSDDiskData*) disk->disk_specific; label = (BSDRawLabel *) (bsd_specific->boot_code + BSD_LABEL_OFFSET); if (!bsd_specific->boot_code [0]) _probe_and_add_boot_code (disk); memset (label->d_partitions, 0, sizeof (BSDRawPartition) * BSD_MAXPARTITIONS); for (i = 1; i <= BSD_MAXPARTITIONS; i++) { part = ped_disk_get_partition (disk, i); if (!part) continue; bsd_data = part->disk_specific; label->d_partitions[i - 1].p_fstype = bsd_data->type; label->d_partitions[i - 1].p_offset = PED_CPU_TO_LE32 (part->geom.start); label->d_partitions[i - 1].p_size = PED_CPU_TO_LE32 (part->geom.length); max_part = i; } label->d_npartitions = PED_CPU_TO_LE16 (max_part) + 1; label->d_checksum = xbsd_dkcksum (label); alpha_bootblock_checksum (bsd_specific->boot_code); if (!ptt_write_sector (disk, bsd_specific->boot_code, sizeof (BSDDiskData))) goto error; return ped_device_sync (disk->dev); error: return 0; }
int fat_info_sector_generate (FatInfoSector* is, const PedFileSystem* fs) { FatSpecific* fs_info = FAT_SPECIFIC (fs); PED_ASSERT (is != NULL); fat_table_count_stats (fs_info->fat); memset (is, 0, 512); is->signature_1 = PED_CPU_TO_LE32 (FAT32_INFO_MAGIC1); is->signature_2 = PED_CPU_TO_LE32 (FAT32_INFO_MAGIC2); is->free_clusters = PED_CPU_TO_LE32 (fs_info->fat->free_cluster_count); is->next_cluster = PED_CPU_TO_LE32 (fs_info->fat->last_alloc); is->signature_3 = PED_CPU_TO_LE16 (FAT32_INFO_MAGIC3); return 1; }
static int pc98_write (const PedDisk* disk) { PedPartition* part; int i; PED_ASSERT (disk != NULL); PED_ASSERT (disk->dev != NULL); void *s0; if (!ptt_read_sectors (disk->dev, 0, 2, &s0)) return 0; PC98RawTable *table = s0; if (!pc98_check_ipl_signature (table)) { memset (table->boot_code, 0, sizeof(table->boot_code)); memcpy (table->boot_code, MBR_BOOT_CODE, sizeof(MBR_BOOT_CODE)); } memset (table->partitions, 0, sizeof (table->partitions)); table->magic = PED_CPU_TO_LE16(PC9800_EXTFMT_MAGIC); for (i = 1; i <= MAX_PART_COUNT; i++) { part = ped_disk_get_partition (disk, i); if (!part) continue; if (!fill_raw_part (&table->partitions [i - 1], part)) return 0; } int write_ok = ped_device_write (disk->dev, table, 0, 2); free (s0); if (!write_ok) return 0; return ped_device_sync (disk->dev); }
unsigned int _gen_gpt_entry(int part_index , gpt_entry *g_entry,PARTITION_CFG *p_partition_cfg) { int i = 0; //maybe if( PARTITION_RAW == p_partition_cfg[part_index].partition_attr) g_entry->partition_type_guid = PARTITION_BASIC_DATA_GUID; else if( PARTITION_EXT4 == p_partition_cfg[part_index].partition_attr) g_entry->partition_type_guid = PARTITION_BASIC_DATA_GUID; else g_entry->partition_type_guid = PARTITION_BASIC_DATA_GUID; //gen guid g_entry->unique_partition_guid =_gen_guid(part_index+1) ; *(unsigned long long int*)g_entry->starting_lba = _cur_lba_num; //judge if user data partition if( MAX_SIZE_FLAG == p_partition_cfg[part_index].partition_size) { _cur_lba_num = _cur_lba_num + (emmc_part_device.total_sector-STARTING_LBA_OF_FIRST_PARTITION-MAX_PARTITION_INFO/4-1-all_used_size*2); _cur_lba_num = (_cur_lba_num/STARTING_LBA_OF_FIRST_PARTITION)*STARTING_LBA_OF_FIRST_PARTITION; *(unsigned long long int*)g_entry->ending_lba = _cur_lba_num-1; }else { _cur_lba_num = _cur_lba_num + p_partition_cfg[part_index].partition_size * 2; *(unsigned long long int*)g_entry->ending_lba = _cur_lba_num - 1; } memset (&g_entry->attributes, 0, sizeof (gpt_entry_attributes)); for (i = 0; i < MAX_UTF_PARTITION_NAME_LEN; i++) g_entry->partition_name[i] = (efi_char16_t) PED_CPU_TO_LE16 (p_partition_cfg[part_index].partition_name[i]); return 1; }
int fat_boot_sector_generate (FatBootSector** bsp, const PedFileSystem* fs) { FatSpecific* fs_info = FAT_SPECIFIC (fs); PED_ASSERT (bsp != NULL); FatBootSector *bs = *bsp; PED_ASSERT (bs != NULL); memcpy (bs->system_id, "MSWIN4.1", 8); bs->sector_size = PED_CPU_TO_LE16 (fs_info->logical_sector_size * 512); bs->cluster_size = fs_info->cluster_sectors / fs_info->logical_sector_size; bs->reserved = PED_CPU_TO_LE16 (fs_info->fat_offset / fs_info->logical_sector_size); bs->fats = fs_info->fat_table_count; bs->dir_entries = (fs_info->fat_type == FAT_TYPE_FAT16) ? PED_CPU_TO_LE16 (fs_info->root_dir_entry_count) : 0; if (fs_info->sector_count / fs_info->logical_sector_size > 0xffff || fs_info->fat_type == FAT_TYPE_FAT32) { bs->sectors = 0; bs->sector_count = PED_CPU_TO_LE32 (fs_info->sector_count / fs_info->logical_sector_size); } else { bs->sectors = PED_CPU_TO_LE16 (fs_info->sector_count / fs_info->logical_sector_size); bs->sector_count = 0; } bs->media = 0xf8; bs->secs_track = PED_CPU_TO_LE16 (fs_info->sectors_per_track); bs->heads = PED_CPU_TO_LE16 (fs_info->heads); bs->hidden = PED_CPU_TO_LE32 (fs->geom->start); if (fs_info->fat_type == FAT_TYPE_FAT32) { bs->fat_length = 0; bs->u.fat32.fat_length = PED_CPU_TO_LE32 (fs_info->fat_sectors / fs_info->logical_sector_size); bs->u.fat32.flags = 0; /* FIXME: what the hell are these? */ bs->u.fat32.version = 0; /* must be 0, for Win98 bootstrap */ bs->u.fat32.root_dir_cluster = PED_CPU_TO_LE32 (fs_info->root_cluster); bs->u.fat32.info_sector = PED_CPU_TO_LE16 (fs_info->info_sector_offset / fs_info->logical_sector_size); bs->u.fat32.backup_sector = PED_CPU_TO_LE16 (fs_info->boot_sector_backup_offset / fs_info->logical_sector_size); bs->u.fat32.drive_num = 0x80; /* _ALWAYS_ 0x80. silly DOS */ memset (bs->u.fat32.empty_1, 0, 12); bs->u.fat32.ext_signature = 0x29; bs->u.fat32.serial_number = PED_CPU_TO_LE32 (fs_info->serial_number); memcpy (bs->u.fat32.volume_name, "NO NAME ", 11); memcpy (bs->u.fat32.fat_name, "FAT32 ", 8); } else { bs->fat_length = PED_CPU_TO_LE16 (fs_info->fat_sectors / fs_info->logical_sector_size); bs->u.fat16.drive_num = 0x80; /* _ALWAYS_ 0x80. silly DOS */ bs->u.fat16.ext_signature = 0x29; bs->u.fat16.serial_number = PED_CPU_TO_LE32 (fs_info->serial_number); memcpy (bs->u.fat16.volume_name, "NO NAME ", 11); memcpy (bs->u.fat16.fat_name, "FAT16 ", 8); } bs->boot_sign = PED_CPU_TO_LE16 (0xaa55); return 1; }
/* Analyses the boot sector, and sticks appropriate numbers in fs->type_specific. Note: you need to subtract (2 * cluster_sectors) off cluster offset, because the first cluster is number 2. (0 and 1 are not real clusters, and referencing them is a bug) */ int fat_boot_sector_analyse (FatBootSector* bs, PedFileSystem* fs) { FatSpecific* fs_info = FAT_SPECIFIC (fs); int fat_entry_size; PED_ASSERT (bs != NULL); fs_info->logical_sector_size = PED_LE16_TO_CPU (bs->sector_size) / 512; fs_info->sectors_per_track = PED_LE16_TO_CPU (bs->secs_track); fs_info->heads = PED_LE16_TO_CPU (bs->heads); if (fs_info->sectors_per_track < 1 || fs_info->sectors_per_track > 63 || fs_info->heads < 1 || fs_info->heads > 255) { PedCHSGeometry* bios_geom = &fs->geom->dev->bios_geom; int cyl_count = 0; if (fs_info->heads > 0 && fs_info->sectors_per_track > 0) cyl_count = fs->geom->dev->length / fs_info->heads / fs_info->sectors_per_track; switch (ped_exception_throw ( PED_EXCEPTION_ERROR, PED_EXCEPTION_FIX + PED_EXCEPTION_IGNORE + PED_EXCEPTION_CANCEL, _("The file system's CHS geometry is (%d, %d, %d), " "which is invalid. The partition table's CHS " "geometry is (%d, %d, %d). If you select Ignore, " "the file system's CHS geometry will be left " "unchanged. If you select Fix, the file system's " "CHS geometry will be set to match the partition " "table's CHS geometry."), cyl_count, fs_info->heads, fs_info->sectors_per_track, bios_geom->cylinders, bios_geom->heads, bios_geom->sectors)) { case PED_EXCEPTION_FIX: fs_info->sectors_per_track = bios_geom->sectors; fs_info->heads = bios_geom->heads; bs->secs_track = PED_CPU_TO_LE16 (fs_info->sectors_per_track); bs->heads = PED_CPU_TO_LE16 (fs_info->heads); if (!fat_boot_sector_write (bs, fs)) return 0; break; case PED_EXCEPTION_CANCEL: return 0; case PED_EXCEPTION_IGNORE: break; default: break; } } if (bs->sectors) fs_info->sector_count = PED_LE16_TO_CPU (bs->sectors) * fs_info->logical_sector_size; else fs_info->sector_count = PED_LE32_TO_CPU (bs->sector_count) * fs_info->logical_sector_size; fs_info->fat_table_count = bs->fats; fs_info->root_dir_entry_count = PED_LE16_TO_CPU (bs->dir_entries); fs_info->fat_offset = PED_LE16_TO_CPU (bs->reserved) * fs_info->logical_sector_size; fs_info->cluster_sectors = bs->cluster_size * fs_info->logical_sector_size; fs_info->cluster_size = fs_info->cluster_sectors * 512; if (fs_info->logical_sector_size == 0) { ped_exception_throw (PED_EXCEPTION_ERROR, PED_EXCEPTION_CANCEL, _("FAT boot sector says logical sector size is 0. " "This is weird. ")); return 0; } if (fs_info->fat_table_count == 0) { ped_exception_throw (PED_EXCEPTION_ERROR, PED_EXCEPTION_CANCEL, _("FAT boot sector says there are no FAT tables. This " "is weird. ")); return 0; } if (fs_info->cluster_sectors == 0) { ped_exception_throw (PED_EXCEPTION_ERROR, PED_EXCEPTION_CANCEL, _("FAT boot sector says clusters are 0 sectors. This " "is weird. ")); return 0; } fs_info->fat_type = fat_boot_sector_probe_type (bs, fs->geom); if (fs_info->fat_type == FAT_TYPE_FAT12) { ped_exception_throw ( PED_EXCEPTION_NO_FEATURE, PED_EXCEPTION_CANCEL, _("File system is FAT12, which is unsupported.")); return 0; } if (fs_info->fat_type == FAT_TYPE_FAT16) { fs_info->fat_sectors = PED_LE16_TO_CPU (bs->fat_length) * fs_info->logical_sector_size; fs_info->serial_number = PED_LE32_TO_CPU (bs->u.fat16.serial_number); fs_info->root_cluster = 0; fs_info->root_dir_offset = fs_info->fat_offset + fs_info->fat_sectors * fs_info->fat_table_count; fs_info->root_dir_sector_count = fs_info->root_dir_entry_count * sizeof (FatDirEntry) / (512 * fs_info->logical_sector_size); fs_info->cluster_offset = fs_info->root_dir_offset + fs_info->root_dir_sector_count; } if (fs_info->fat_type == FAT_TYPE_FAT32) { fs_info->fat_sectors = PED_LE32_TO_CPU (bs->u.fat32.fat_length) * fs_info->logical_sector_size; fs_info->serial_number = PED_LE32_TO_CPU (bs->u.fat32.serial_number); fs_info->info_sector_offset = PED_LE16_TO_CPU (fs_info->boot_sector->u.fat32.info_sector) * fs_info->logical_sector_size; fs_info->boot_sector_backup_offset = PED_LE16_TO_CPU (fs_info->boot_sector->u.fat32.backup_sector) * fs_info->logical_sector_size; fs_info->root_cluster = PED_LE32_TO_CPU (bs->u.fat32.root_dir_cluster); fs_info->root_dir_offset = 0; fs_info->root_dir_sector_count = 0; fs_info->cluster_offset = fs_info->fat_offset + fs_info->fat_sectors * fs_info->fat_table_count; } fs_info->cluster_count = (fs_info->sector_count - fs_info->cluster_offset) / fs_info->cluster_sectors; fat_entry_size = fat_table_entry_size (fs_info->fat_type); if (fs_info->cluster_count + 2 > fs_info->fat_sectors * 512 / fat_entry_size) fs_info->cluster_count = fs_info->fat_sectors * 512 / fat_entry_size - 2; fs_info->dir_entries_per_cluster = fs_info->cluster_size / sizeof (FatDirEntry); return 1; }
static int fill_raw_part (PC98RawPartition* raw_part, const PedPartition* part) { PC98PartitionData* pc98_data; int c, h, s; const char* name; PED_ASSERT (raw_part != NULL); PED_ASSERT (part != NULL); PED_ASSERT (part->disk_specific != NULL); pc98_data = part->disk_specific; raw_part->mid = (pc98_data->system >> 8) & 0xFF; raw_part->sid = pc98_data->system & 0xFF; SET_BIT(raw_part->mid, 7, pc98_data->boot); SET_BIT(raw_part->sid, 7, !pc98_data->hidden); memset (raw_part->name, ' ', sizeof(raw_part->name)); name = ped_partition_get_name (part); PED_ASSERT (name != NULL); PED_ASSERT (strlen (name) <= 16); if (!strlen (name) && part->fs_type) name = part->fs_type->name; memcpy (raw_part->name, name, strlen (name)); sector_to_chs (part->disk->dev, part->geom.start, &c, &h, &s); raw_part->cyl = PED_CPU_TO_LE16(c); raw_part->head = h; raw_part->sector = s; if (pc98_data->ipl_sector) { sector_to_chs (part->disk->dev, pc98_data->ipl_sector, &c, &h, &s); raw_part->ipl_cyl = PED_CPU_TO_LE16(c); raw_part->ipl_head = h; raw_part->ipl_sect = s; } else { raw_part->ipl_cyl = raw_part->cyl; raw_part->ipl_head = raw_part->head; raw_part->ipl_sect = raw_part->sector; } sector_to_chs (part->disk->dev, part->geom.end, &c, &h, &s); if (h != part->disk->dev->hw_geom.heads - 1 || s != part->disk->dev->hw_geom.sectors - 1) { ped_exception_throw ( PED_EXCEPTION_NO_FEATURE, PED_EXCEPTION_CANCEL, _("Partition %d isn't aligned to cylinder " "boundaries. This is still unsupported."), part->num); return 0; } raw_part->end_cyl = PED_CPU_TO_LE16(c); #if 0 raw_part->end_head = h; raw_part->end_sector = s; #else raw_part->end_head = 0; raw_part->end_sector = 0; #endif return 1; }