* It's recommended to not change any alignment or device properties. All is
* initialized by default by fdisk_assign_device().
*
- * Note that terminology used by libfdisk is:
+ * Note that terminology used by libfdisk is:
* - device properties: I/O limits (topology), geometry, sector size, ...
* - alignment: first, last LBA, grain, ...
*
return 0;
}
+/**
+ * fdisk_save_user_grain:
+ * @cxt: context
+ * @grain: size in bytes (>= 512, multiple of 512)
+ *
+ * Save user define grain size. The size is used to align partitions.
+ *
+ * The default is 1MiB (or optimal I/O size if greater than 1MiB). It's strongly
+ * recommended to use the default.
+ *
+ * The smallest possible granularity for partitioning is physical sector size
+ * (or minimal I/O size; the bigger number win). If the user's @grain size is
+ * too small than the smallest possible granularity is used. It means
+ * fdisk_save_user_grain(cxt, 512) forces libfdisk to use grain as small as
+ * possible.
+ *
+ * The setting is applied by fdisk_assign_device() or
+ * fdisk_reset_device_properties().
+ *
+ * Returns: <0 on error, 0 on success.
+ */
+int fdisk_save_user_grain(struct fdisk_context *cxt, unsigned long grain)
+{
+ if (!cxt || grain % 512)
+ return -EINVAL;
+
+ cxt->user_grain = grain;
+ return 0;
+}
+
/**
* fdisk_has_user_device_properties:
* @cxt: context
int fdisk_has_user_device_properties(struct fdisk_context *cxt)
{
return (cxt->user_pyh_sector || cxt->user_log_sector ||
+ cxt->user_grain ||
fdisk_has_user_device_geometry(cxt));
}
recount_geometry(cxt);
fdisk_reset_alignment(cxt);
+
+ if (cxt->user_grain) {
+ unsigned long granularity = max(cxt->phy_sector_size, cxt->min_io_size);
+
+ cxt->grain = cxt->user_grain < granularity ? granularity : cxt->user_grain;
+ DBG(CXT, ul_debugobj(cxt, "new grain: %lu", cxt->grain));
+ }
+
if (cxt->firstsector_bufsz != cxt->sector_size)
fdisk_read_firstsector(cxt);