fdisk: API: add write to label operations

[kzak@redhat.com: - rename functions
                  - use errno]

Signed-off-by: Karel Zak <kzak@redhat.com>
Signed-off-by: Davidlohr Bueso <dave@gnu.org>
This commit is contained in:
Davidlohr Bueso 2012-07-23 18:47:42 +02:00 committed by Karel Zak
parent 61c4cb8530
commit fae7b1bcb5
12 changed files with 104 additions and 64 deletions

View File

@ -1420,24 +1420,13 @@ static void new_partition(struct fdisk_context *cxt)
dos_new_partition(cxt);
}
static void
write_table(struct fdisk_context *cxt) {
int i;
static void write_table(struct fdisk_context *cxt)
{
int rc;
if (disklabel == DOS_LABEL)
dos_write_table(cxt);
else if (disklabel == SGI_LABEL)
/* no test on change? the printf below might be mistaken */
sgi_write_table(cxt);
else if (disklabel == SUN_LABEL) {
int needw = 0;
for (i=0; i<8; i++)
if (ptes[i].changed)
needw = 1;
if (needw)
sun_write_table(cxt);
}
rc = fdisk_write_disklabel(cxt);
if (rc)
err(EXIT_FAILURE, _("cannot write disk label"));
printf(_("The partition table has been altered!\n\n"));
reread_partition_table(cxt, 1);

View File

@ -137,6 +137,8 @@ struct fdisk_label {
/* probe disk label */
int (*probe)(struct fdisk_context *cxt);
/* write in-memory changes to disk */
int (*write)(struct fdisk_context *cxt);
/* delete partition */
void (*part_delete)(struct fdisk_context *cxt, int partnum);
};
@ -163,6 +165,7 @@ extern int fdisk_context_set_user_geometry(struct fdisk_context *cxt,
unsigned int sectors);
extern int fdisk_create_default_disklabel(struct fdisk_context *cxt);
extern int fdisk_delete_partition(struct fdisk_context *cxt, int partnum);
extern int fdisk_write_disklabel(struct fdisk_context *cxt);
/* prototypes for fdisk.c */
extern char *disk_device, *line_ptr;
@ -265,13 +268,6 @@ static inline void read_sector(struct fdisk_context *cxt, sector_t secno, unsign
fatal(cxt, unable_to_read);
}
static inline void write_sector(struct fdisk_context *cxt, sector_t secno, unsigned char *buf)
{
seek_sector(cxt, secno);
if (write(cxt->dev_fd, buf, cxt->sector_size) != (ssize_t) cxt->sector_size)
fatal(cxt, unable_to_write);
}
static inline sector_t get_start_sect(struct partition *p)
{
return read4_little_endian(p->start4);

View File

@ -69,5 +69,6 @@ const struct fdisk_label aix_label =
{
.name = "aix",
.probe = aix_probe_label,
.write = NULL,
.part_delete = NULL,
};

View File

@ -63,7 +63,6 @@
static void xbsd_delete_part (struct fdisk_context *cxt, int partnum);
static void xbsd_new_part (struct fdisk_context *cxt);
static void xbsd_write_disklabel (struct fdisk_context *cxt);
static int xbsd_create_disklabel (struct fdisk_context *cxt);
static void xbsd_edit_disklabel (void);
static void xbsd_write_bootstrap (struct fdisk_context *cxt);
@ -140,6 +139,21 @@ is_bsd_partition_type(int type) {
}
#endif
static int xbsd_write_disklabel (struct fdisk_context *cxt)
{
#if defined (__alpha__)
printf (_("Writing disklabel to %s.\n"), cxt->dev_path);
xbsd_writelabel (cxt, NULL, &xbsd_dlabel);
#else
printf (_("Writing disklabel to %s.\n"),
partname(cxt->dev_path, xbsd_part_index+1, 0));
xbsd_writelabel (cxt, xbsd_part, &xbsd_dlabel);
#endif
reread_partition_table(cxt, 0); /* no exit yet */
return 0;
}
void
bsd_command_prompt (struct fdisk_context *cxt)
{
@ -376,19 +390,6 @@ xbsd_print_disklabel (struct fdisk_context *cxt, int show_all) {
}
}
static void
xbsd_write_disklabel (struct fdisk_context *cxt) {
#if defined (__alpha__)
printf (_("Writing disklabel to %s.\n"), cxt->dev_path);
xbsd_writelabel (cxt, NULL, &xbsd_dlabel);
#else
printf (_("Writing disklabel to %s.\n"),
partname(cxt->dev_path, xbsd_part_index+1, 0));
xbsd_writelabel (cxt, xbsd_part, &xbsd_dlabel);
#endif
reread_partition_table(cxt, 0); /* no exit yet */
}
static int
xbsd_create_disklabel (struct fdisk_context *cxt) {
char c;
@ -846,5 +847,6 @@ const struct fdisk_label bsd_label =
{
.name = "bsd",
.probe = osf_probe_label,
.write = xbsd_write_disklabel,
.part_delete = xbsd_delete_part,
};

View File

@ -706,9 +706,18 @@ void dos_new_partition(struct fdisk_context *cxt)
}
}
void dos_write_table(struct fdisk_context *cxt)
static int write_sector(struct fdisk_context *cxt, sector_t secno,
unsigned char *buf)
{
int i;
seek_sector(cxt, secno);
if (write(cxt->dev_fd, buf, cxt->sector_size) != (ssize_t) cxt->sector_size)
return -errno;
return 0;
}
static int dos_write_disklabel(struct fdisk_context *cxt)
{
int i, rc = 0;
/* MBR (primary partitions) */
if (!MBRbuffer_changed) {
@ -718,7 +727,9 @@ void dos_write_table(struct fdisk_context *cxt)
}
if (MBRbuffer_changed) {
mbr_set_magic(cxt->firstsector);
write_sector(cxt, 0, cxt->firstsector);
rc = write_sector(cxt, 0, cxt->firstsector);
if (rc)
goto done;
}
/* EBR (logical partitions) */
for (i = 4; i < partitions; i++) {
@ -726,14 +737,20 @@ void dos_write_table(struct fdisk_context *cxt)
if (pe->changed) {
mbr_set_magic(pe->sectorbuffer);
write_sector(cxt, pe->offset, pe->sectorbuffer);
rc = write_sector(cxt, pe->offset, pe->sectorbuffer);
if (rc)
goto done;
}
}
done:
return rc;
}
const struct fdisk_label dos_label =
{
.name = "dos",
.probe = dos_probe_label,
.write = dos_write_disklabel,
.part_delete = dos_delete_partition,
};

View File

@ -44,7 +44,6 @@ extern int is_dos_partition(int t);
extern void dos_init(struct fdisk_context *cxt);
extern void dos_add_partition(struct fdisk_context *cxt, int n, int sys);
extern void dos_new_partition(struct fdisk_context *cxt);
extern void dos_write_table(struct fdisk_context *cxt);
extern int mbr_is_valid_magic(unsigned char *b);

View File

@ -84,5 +84,6 @@ const struct fdisk_label mac_label =
{
.name = "mac",
.probe = mac_probe_label,
.write = NULL,
.part_delete = NULL,
};

View File

@ -39,6 +39,8 @@ static int other_endian = 0;
static int debug = 0;
static short volumes=1;
static sgiinfo *fill_sgiinfo(void);
/*
* only dealing with free blocks here
*/
@ -328,10 +330,11 @@ create_sgiinfo(struct fdisk_context *cxt) {
strncpy((char *) sgilabel->directory[0].vol_file_name, "sgilabel", 8);
}
sgiinfo *fill_sgiinfo(void);
void
sgi_write_table(struct fdisk_context *cxt) {
static int sgi_write_disklabel(struct fdisk_context *cxt)
{
sgiinfo *info = NULL;
sgilabel->csum = 0;
sgilabel->csum = SSWAP32(two_s_complement_32bit_sum(
(unsigned int*)sgilabel,
@ -339,23 +342,34 @@ sgi_write_table(struct fdisk_context *cxt) {
assert(two_s_complement_32bit_sum(
(unsigned int*)sgilabel, sizeof(*sgilabel)) == 0);
if (lseek(cxt->dev_fd, 0, SEEK_SET) < 0)
fatal(cxt, unable_to_seek);
goto err;
if (write(cxt->dev_fd, sgilabel, SECTOR_SIZE) != SECTOR_SIZE)
fatal(cxt, unable_to_write);
if (! strncmp((char *) sgilabel->directory[0].vol_file_name, "sgilabel", 8)) {
goto err;
if (!strncmp((char *) sgilabel->directory[0].vol_file_name, "sgilabel", 8)) {
/*
* keep this habit of first writing the "sgilabel".
* I never tested whether it works without (AN 981002).
*/
sgiinfo *info = fill_sgiinfo();
int infostartblock = SSWAP32(sgilabel->directory[0].vol_file_start);
if (lseek(cxt->dev_fd, (off_t) infostartblock*
SECTOR_SIZE, SEEK_SET) < 0)
fatal(cxt, unable_to_seek);
int infostartblock
= SSWAP32(sgilabel->directory[0].vol_file_start);
if (lseek(cxt->dev_fd, (off_t) infostartblock *
SECTOR_SIZE, SEEK_SET) < 0)
goto err;
info = fill_sgiinfo();
if (!info)
goto err;
if (write(cxt->dev_fd, info, SECTOR_SIZE) != SECTOR_SIZE)
fatal(cxt, unable_to_write);
free(info);
goto err;
}
free(info);
return 0;
err:
free(info);
return -errno;
}
static int
@ -865,10 +879,13 @@ sgi_set_ncyl(void)
/* _____________________________________________________________
*/
sgiinfo *
fill_sgiinfo(void)
static sgiinfo *fill_sgiinfo(void)
{
sgiinfo *info=xcalloc(1, sizeof(sgiinfo));
sgiinfo *info = calloc(1, sizeof(sgiinfo));
if (!info)
return NULL;
info->magic=SSWAP32(SGI_INFO_MAGIC);
info->b1=SSWAP32(-1);
info->b2=SSWAP16(-1);
@ -885,5 +902,6 @@ const struct fdisk_label sgi_label =
{
.name = "sgi",
.probe = sgi_probe_label,
.write = sgi_write_disklabel,
.part_delete = sgi_delete_partition,
};

View File

@ -120,7 +120,6 @@ extern void sgi_add_partition( struct fdisk_context *cxt, int n, int sys );
extern void create_sgilabel( struct fdisk_context *cxt );
extern void create_sgiinfo(struct fdisk_context *cxt);
extern int verify_sgi(struct fdisk_context *cxt, int verbose );
extern void sgi_write_table( struct fdisk_context *cxt );
extern void sgi_set_ilfact( void );
extern void sgi_set_rspeed( void );
extern void sgi_set_pcylcount( void );

View File

@ -626,7 +626,7 @@ void sun_set_pcylcount(struct fdisk_context *cxt)
_("Number of physical cylinders")));
}
void sun_write_table(struct fdisk_context *cxt)
static int sun_write_disklabel(struct fdisk_context *cxt)
{
unsigned short *ush = (unsigned short *)sunlabel;
unsigned short csum = 0;
@ -635,9 +635,11 @@ void sun_write_table(struct fdisk_context *cxt)
csum ^= *ush++;
sunlabel->cksum = csum;
if (lseek(cxt->dev_fd, 0, SEEK_SET) < 0)
fatal(cxt, unable_to_seek);
return -errno;
if (write(cxt->dev_fd, sunlabel, SECTOR_SIZE) != SECTOR_SIZE)
fatal(cxt, unable_to_write);
return -errno;
return 0;
}
int sun_get_sysid(struct fdisk_context *cxt, int i)
@ -649,5 +651,6 @@ const struct fdisk_label sun_label =
{
.name = "sun",
.probe = sun_probe_label,
.write = sun_write_disklabel,
.part_delete = sun_delete_partition,
};

View File

@ -82,7 +82,6 @@ extern int sun_change_sysid(struct fdisk_context *cxt, int i, uint16_t sys);
extern void sun_list_table(struct fdisk_context *cxt, int xtra);
extern void verify_sun(struct fdisk_context *cxt);
extern void add_sun_partition(struct fdisk_context *cxt, int n, int sys);
extern void sun_write_table(struct fdisk_context *cxt);
extern void sun_set_alt_cyl(struct fdisk_context *cxt);
extern void sun_set_ncyl(struct fdisk_context *cxt, int cyl);
extern void sun_set_xcyl(struct fdisk_context *cxt);

View File

@ -47,6 +47,22 @@ static const struct fdisk_label *labels[] =
&mac_label,
};
/**
* fdisk_write_disklabel
* @cxt: fdisk context
*
* Write in-memory changes to disk
*
* Returns 0 on success, otherwise, a corresponding error.
*/
int fdisk_write_disklabel(struct fdisk_context *cxt)
{
if (!cxt)
return -EINVAL;
return cxt->label->write(cxt);
}
/**
* fdisk_delete_partition:
* @cxt: fdisk context