/**************************************************************/ /* tpax: a topological pax implementation */ /* Copyright (C) 2020--2024 SysDeer Technologies, LLC */ /* Released under GPLv2 and GPLv3; see COPYING.TPAX. */ /**************************************************************/ #include #include #include #include #include #include #include "tpax_driver_impl.h" #include "tpax_errinfo_impl.h" static int tpax_io_seek_fileio( struct tpax_driver_ctx * dctx, off_t offset, int whence) { int fdin; fdin = tpax_driver_fdin(dctx); if ((offset = lseek(fdin,offset,whence)) < 0) return TPAX_SYSTEM_ERROR(dctx); tpax_set_driver_cpos(dctx,offset); return 0; } static int tpax_io_seek_mapped( struct tpax_driver_ctx * dctx, off_t offset, int whence) { struct tpax_driver_ctx_impl * ictx; size_t aoffset; ictx = tpax_get_driver_ictx(dctx); if (whence == SEEK_CUR) { offset += tpax_get_driver_cpos(dctx); } else if (whence == SEEK_END) { offset += ictx->mapsize; } if ((offset < 0) || ((aoffset = offset) > ictx->mapsize)) return TPAX_CUSTOM_ERROR( dctx, TPAX_ERR_FLOW_ERROR); tpax_set_driver_cpos(dctx,offset); return 0; } int tpax_io_seek(struct tpax_driver_ctx * dctx, off_t offset, int whence) { switch (whence) { case SEEK_SET: case SEEK_CUR: case SEEK_END: break; default: return TPAX_CUSTOM_ERROR( dctx, TPAX_ERR_FLOW_ERROR); } if (dctx->cctx->srcflags & TPAX_SOURCE_DATA_FILEIO) { return tpax_io_seek_fileio(dctx,offset,whence); } else if (dctx->cctx->srcflags & TPAX_SOURCE_DATA_MAPPED) { return tpax_io_seek_mapped(dctx,offset,whence); } return TPAX_CUSTOM_ERROR( dctx, TPAX_ERR_FLOW_ERROR); }