vdisk: use file descriptors instead of FILE*s

This should help with io_uring later.
This commit is contained in:
2023-01-16 03:14:48 +00:00
parent 99c50bd258
commit f1b6893e4d
3 changed files with 31 additions and 33 deletions

View File

@@ -24,9 +24,9 @@ else
$(error your compiler is not supported) $(error your compiler is not supported)
endif endif
CFLAGS=$(WARNINGS) $(NOWARNINGS) -std=c11 -g -O0 -D_FILE_OFFSET_BITS=64 \ CFLAGS=$(WARNINGS) $(NOWARNINGS) -std=c11 -g -O0 -DNDEBUG -masm=intel \
-DNDEBUG -masm=intel -D_POSIX_C_SOURCE=200809L -I$(HOST) -fno-pie -D_POSIX_C_SOURCE=200809L -I$(HOST) -fno-pie
CFLAGS_32=$(CFLAGS) -m32 -D__USE_TIME_BITS64 CFLAGS_32=$(CFLAGS) -m32 -D_FILE_OFFSET_BITS=64 -D__USE_TIME_BITS64
LDFLAGS=-no-pie LDFLAGS=-no-pie
LDFLAGS_32=$(LDFLAGS) -m32 LDFLAGS_32=$(LDFLAGS) -m32

View File

@@ -8,14 +8,16 @@
*/ */
#include <errno.h> #include <errno.h>
#include <fcntl.h>
#include <stdlib.h> #include <stdlib.h>
#include <unistd.h>
#include "../trace.h" #include "../trace.h"
#include "qcow2.h" #include "qcow2.h"
#include "miniz/miniz.h" #include "miniz/miniz.h"
struct vdisk_qcow2 { struct vdisk_qcow2 {
struct vdisk vdisk; struct vdisk vdisk;
FILE *file; int fd;
size_t cluster_bits; size_t cluster_bits;
size_t cluster_size; size_t cluster_size;
uint8_t *cluster; uint8_t *cluster;
@@ -93,8 +95,8 @@ qcow2_read_guest_sector(struct vdisk_qcow2 *d, uint64_t sector, uint8_t *buf) {
uint64_t l1_entry; uint64_t l1_entry;
uint64_t l2_entry; uint64_t l2_entry;
uint64_t l1_entry_offset = d->l1_table_offset + l1_index*sizeof(l1_entry); uint64_t l1_entry_offset = d->l1_table_offset + l1_index*sizeof(l1_entry);
fseeko(d->file, l1_entry_offset, SEEK_SET); lseek(d->fd, l1_entry_offset, SEEK_SET);
if (!fread(&l1_entry, 1, sizeof(l1_entry), d->file)) { if (!read(d->fd, &l1_entry, sizeof(l1_entry))) {
fprintf(stderr, "[vdisk.qcow2] can't read from image file: %s\n", fprintf(stderr, "[vdisk.qcow2] can't read from image file: %s\n",
strerror(errno)); strerror(errno));
return; return;
@@ -106,8 +108,8 @@ qcow2_read_guest_sector(struct vdisk_qcow2 *d, uint64_t sector, uint8_t *buf) {
memset(buf, 0, d->vdisk.sect_size); memset(buf, 0, d->vdisk.sect_size);
return; return;
} }
fseeko(d->file, l2_table_offset + l2_index*sizeof(l2_entry), SEEK_SET); lseek(d->fd, l2_table_offset + l2_index*sizeof(l2_entry), SEEK_SET);
if (!fread(&l2_entry, 1, sizeof(l2_entry), d->file)) { if (!read(d->fd, &l2_entry, sizeof(l2_entry))) {
fprintf(stderr, "[vdisk.qcow2] can't read from image file: %s\n", fprintf(stderr, "[vdisk.qcow2] can't read from image file: %s\n",
strerror(errno)); strerror(errno));
return; return;
@@ -121,8 +123,8 @@ qcow2_read_guest_sector(struct vdisk_qcow2 *d, uint64_t sector, uint8_t *buf) {
return; return;
} }
cluster_offset = l2_entry & L2_ENTRY_STD_OFFSET; cluster_offset = l2_entry & L2_ENTRY_STD_OFFSET;
fseeko(d->file, cluster_offset, SEEK_SET); lseek(d->fd, cluster_offset, SEEK_SET);
if (!fread(d->cluster, 1, d->cluster_size, d->file)) { if (!read(d->fd, d->cluster, d->cluster_size)) {
fprintf(stderr, "[vdisk.qcow2] can't read from image file: %s\n", fprintf(stderr, "[vdisk.qcow2] can't read from image file: %s\n",
strerror(errno)); strerror(errno));
return; return;
@@ -133,11 +135,11 @@ qcow2_read_guest_sector(struct vdisk_qcow2 *d, uint64_t sector, uint8_t *buf) {
} else { } else {
off_t cmp_offset = d->l2_entry_cmp_offset_mask & l2_entry; off_t cmp_offset = d->l2_entry_cmp_offset_mask & l2_entry;
printf("cmp_offset: 0x%" PRIx64 "\n", cmp_offset); printf("cmp_offset: 0x%" PRIx64 "\n", cmp_offset);
fseeko(d->file, cmp_offset, SEEK_SET); lseek(d->fd, cmp_offset, SEEK_SET);
size_t additional_sectors = (l2_entry & d->l2_entry_cmp_sect_cnt_mask) size_t additional_sectors = (l2_entry & d->l2_entry_cmp_sect_cnt_mask)
>> d->l2_entry_cmp_x; >> d->l2_entry_cmp_x;
size_t cmp_size = 512 - (cmp_offset & 511) + additional_sectors*512; size_t cmp_size = 512 - (cmp_offset & 511) + additional_sectors*512;
if (!fread(d->cmp_cluster, 1, d->cluster_size, d->file)) { if (!read(d->fd, d->cmp_cluster, d->cluster_size)) {
fprintf(stderr, "[vdisk.qcow2] can't read from image file: %s\n", fprintf(stderr, "[vdisk.qcow2] can't read from image file: %s\n",
strerror(errno)); strerror(errno));
return; return;
@@ -154,8 +156,8 @@ STDCALL void
vdisk_qcow2_close(void *userdata) { vdisk_qcow2_close(void *userdata) {
COVERAGE_OFF(); COVERAGE_OFF();
struct vdisk_qcow2 *d = userdata; struct vdisk_qcow2 *d = userdata;
if (d->file) { if (d->fd) {
fclose(d->file); close(d->fd);
} }
free(d->cluster); free(d->cluster);
free(d->cmp_cluster); free(d->cmp_cluster);
@@ -205,7 +207,7 @@ vdisk_init_qcow2(const char *fname) {
return NULL; return NULL;
} }
if (!(d->file = fopen(fname, "r+"))) { if (!(d->fd = open(fname, O_RDONLY))) {
fprintf(stderr, "[vdisk.qcow2] can't open file '%s': %s\n", fname, fprintf(stderr, "[vdisk.qcow2] can't open file '%s': %s\n", fname,
strerror(errno)); strerror(errno));
vdisk_qcow2_close(d); vdisk_qcow2_close(d);
@@ -217,7 +219,7 @@ vdisk_init_qcow2(const char *fname) {
} }
struct qcow2_header header; struct qcow2_header header;
if (!fread(&header, 1, sizeof(struct qcow2_header), d->file)) { if (!read(d->fd, &header, sizeof(struct qcow2_header))) {
fprintf(stderr, "[vdisk.qcow2] can't read from image file: %s\n", fprintf(stderr, "[vdisk.qcow2] can't read from image file: %s\n",
strerror(errno)); strerror(errno));
vdisk_qcow2_close(d); vdisk_qcow2_close(d);

View File

@@ -8,25 +8,22 @@
*/ */
#include <errno.h> #include <errno.h>
#include <fcntl.h>
#include <stdlib.h> #include <stdlib.h>
#include <unistd.h>
#include "../trace.h" #include "../trace.h"
#include "raw.h" #include "raw.h"
#ifdef _WIN32
#define fseeko _fseeki64
#define ftello _ftelli64
#endif
struct vdisk_raw { struct vdisk_raw {
struct vdisk vdisk; struct vdisk vdisk;
FILE *file; int fd;
}; };
STDCALL void STDCALL void
vdisk_raw_close(void *userdata) { vdisk_raw_close(void *userdata) {
COVERAGE_OFF(); COVERAGE_OFF();
struct vdisk_raw *disk = userdata; struct vdisk_raw *disk = userdata;
fclose(disk->file); close(disk->fd);
free(disk); free(disk);
COVERAGE_ON(); COVERAGE_ON();
} }
@@ -36,8 +33,8 @@ vdisk_raw_read(void *userdata, void *buffer, off_t startsector,
size_t *numsectors) { size_t *numsectors) {
COVERAGE_OFF(); COVERAGE_OFF();
struct vdisk_raw *disk = userdata; struct vdisk_raw *disk = userdata;
fseeko(disk->file, startsector * disk->vdisk.sect_size, SEEK_SET); lseek(disk->fd, startsector * disk->vdisk.sect_size, SEEK_SET);
fread(buffer, *numsectors * disk->vdisk.sect_size, 1, disk->file); read(disk->fd, buffer, *numsectors * disk->vdisk.sect_size);
COVERAGE_ON(); COVERAGE_ON();
return ERROR_SUCCESS; return ERROR_SUCCESS;
} }
@@ -47,22 +44,21 @@ vdisk_raw_write(void *userdata, void *buffer, off_t startsector,
size_t *numsectors) { size_t *numsectors) {
COVERAGE_OFF(); COVERAGE_OFF();
struct vdisk_raw *disk = userdata; struct vdisk_raw *disk = userdata;
fseeko(disk->file, startsector * disk->vdisk.sect_size, SEEK_SET); lseek(disk->fd, startsector * disk->vdisk.sect_size, SEEK_SET);
fwrite(buffer, *numsectors * disk->vdisk.sect_size, 1, disk->file); write(disk->fd, buffer, *numsectors * disk->vdisk.sect_size);
COVERAGE_ON(); COVERAGE_ON();
return ERROR_SUCCESS; return ERROR_SUCCESS;
} }
struct vdisk* struct vdisk*
vdisk_init_raw(const char *fname) { vdisk_init_raw(const char *fname) {
FILE *f = fopen(fname, "r+"); int fd = open(fname, O_RDWR);
if (!f) { if (!fd) {
printf("[vdisk.raw]: can't open file '%s': %s\n", fname, strerror(errno)); printf("[vdisk.raw]: can't open file '%s': %s\n", fname, strerror(errno));
return NULL; return NULL;
} }
fseeko(f, 0, SEEK_END); off_t fsize = lseek(fd, 0, SEEK_END);
off_t fsize = ftello(f); lseek(fd, 0, SEEK_SET);
fseeko(f, 0, SEEK_SET);
size_t sect_size = 512; size_t sect_size = 512;
if (strstr(fname, "s4096") != NULL || strstr(fname, "s4k") != NULL) { if (strstr(fname, "s4096") != NULL || strstr(fname, "s4k") != NULL) {
sect_size = 4096; sect_size = 4096;
@@ -77,7 +73,7 @@ vdisk_init_raw(const char *fname) {
.sect_size = sect_size, .sect_size = sect_size,
.sect_cnt = (uint64_t)fsize / sect_size, .sect_cnt = (uint64_t)fsize / sect_size,
}, },
.file = f, .fd = fd,
}; };
return (struct vdisk*)disk; return (struct vdisk*)disk;
} }