2019-10-09 18:06:43 +02:00
|
|
|
#include <libcbd.h>
|
|
|
|
|
|
|
|
#include <libdevmapper.h>
|
|
|
|
|
|
|
|
#include <cbdutil.h>
|
|
|
|
|
|
|
|
static uint64_t
|
2019-11-15 19:30:47 +01:00
|
|
|
device_logical_sectors(const char* dev)
|
2019-10-09 18:06:43 +02:00
|
|
|
{
|
|
|
|
int fd;
|
2019-11-12 22:25:46 +01:00
|
|
|
uint8_t buf[SECTOR_SIZE];
|
2019-10-09 18:06:43 +02:00
|
|
|
struct cbd_header header;
|
2019-11-12 22:25:46 +01:00
|
|
|
uint64_t lblk_total;
|
2019-10-09 18:06:43 +02:00
|
|
|
|
|
|
|
fd = open(dev, O_RDONLY);
|
|
|
|
if (fd < 0) {
|
|
|
|
error("Cannot open device\n");
|
|
|
|
}
|
2019-11-12 22:25:46 +01:00
|
|
|
if (read(fd, buf, sizeof(buf)) != sizeof(buf)) {
|
2019-10-09 18:06:43 +02:00
|
|
|
error("Cannot read device\n");
|
|
|
|
}
|
|
|
|
close(fd);
|
2019-11-12 22:25:46 +01:00
|
|
|
cbd_header_get(buf, &header);
|
2019-10-10 22:21:36 +02:00
|
|
|
if (memcmp(header.magic, CBD_MAGIC, sizeof(header.magic)) != 0) {
|
|
|
|
error("Bad magic\n");
|
|
|
|
}
|
2019-11-12 22:25:46 +01:00
|
|
|
lblk_total = header.params.lblk_per_zone * header.params.nr_zones;
|
2019-10-09 18:06:43 +02:00
|
|
|
|
2019-11-15 19:30:47 +01:00
|
|
|
return lblk_total << (header.params.lblk_shift + header.params.pblk_shift);
|
2019-10-09 18:06:43 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
int
|
|
|
|
cbd_open(const char* dev,
|
2019-11-14 18:51:46 +01:00
|
|
|
const char* name,
|
|
|
|
uint64_t cache_pages, bool sync)
|
2019-10-09 18:06:43 +02:00
|
|
|
{
|
|
|
|
int ret;
|
|
|
|
struct stat st;
|
2019-11-15 19:30:47 +01:00
|
|
|
uint64_t nr_logical_sectors;
|
2019-11-14 18:51:46 +01:00
|
|
|
char optbuf[80];
|
|
|
|
char params[256];
|
2019-10-09 18:06:43 +02:00
|
|
|
struct dm_task* dmt;
|
|
|
|
uint32_t cookie = 0;
|
|
|
|
|
|
|
|
ret = stat(dev, &st);
|
|
|
|
if (ret) {
|
|
|
|
error("Failed to stat device\n");
|
|
|
|
}
|
|
|
|
if (!S_ISBLK(st.st_mode)) {
|
|
|
|
error("Not a block device\n");
|
|
|
|
}
|
2019-11-15 19:30:47 +01:00
|
|
|
nr_logical_sectors = device_logical_sectors(dev);
|
2019-10-09 18:06:43 +02:00
|
|
|
|
2019-11-14 18:51:46 +01:00
|
|
|
strcpy(params, dev);
|
|
|
|
if (cache_pages) {
|
|
|
|
sprintf(optbuf, " cache_pages=%lu", (unsigned long)cache_pages);
|
|
|
|
strcat(params, optbuf);
|
|
|
|
}
|
|
|
|
if (sync) {
|
|
|
|
strcat(params, " sync");
|
|
|
|
}
|
|
|
|
|
2019-10-09 18:06:43 +02:00
|
|
|
dmt = dm_task_create(DM_DEVICE_CREATE);
|
|
|
|
if (!dmt) {
|
|
|
|
error("dm_task_create failed\n");
|
|
|
|
}
|
|
|
|
ret = dm_task_set_name(dmt, name);
|
|
|
|
if (ret == 0) {
|
|
|
|
error("dm_task_set_name failed\n");
|
|
|
|
}
|
2019-10-10 22:21:36 +02:00
|
|
|
printf("%s: start_sector=0 num_sectors=%lu\n", __func__,
|
2019-11-15 19:30:47 +01:00
|
|
|
(unsigned long)nr_logical_sectors);
|
2019-10-09 18:06:43 +02:00
|
|
|
ret = dm_task_add_target(dmt,
|
2019-10-10 22:21:36 +02:00
|
|
|
0,
|
2019-11-15 19:30:47 +01:00
|
|
|
nr_logical_sectors,
|
2019-10-09 18:06:43 +02:00
|
|
|
"compress",
|
2019-11-14 18:51:46 +01:00
|
|
|
params);
|
2019-10-09 18:06:43 +02:00
|
|
|
if (ret == 0) {
|
|
|
|
error("dm_task_add_target failed\n");
|
|
|
|
}
|
|
|
|
ret = dm_task_set_cookie(dmt, &cookie, 0);
|
|
|
|
if (ret == 0) {
|
|
|
|
error("dm_task_set_cookie failed\n");
|
|
|
|
}
|
|
|
|
|
|
|
|
ret = dm_task_run(dmt);
|
|
|
|
if (ret == 0) {
|
|
|
|
error("dm_task_run failed\n");
|
|
|
|
}
|
|
|
|
dm_udev_wait(cookie);
|
|
|
|
|
|
|
|
dm_task_destroy(dmt);
|
|
|
|
|
|
|
|
return 0;
|
|
|
|
}
|