From 0f9f9744d71f902054aa844bd2f136d8307a13dc Mon Sep 17 00:00:00 2001 From: midipix Date: Wed, 27 Jun 2018 20:12:56 -0400 Subject: internals: added slbt_map_file(), slbt_unmap_file(). --- src/internal/slibtool_mapfile_impl.c | 78 ++++++++++++++++++++++++++++++++++++ 1 file changed, 78 insertions(+) create mode 100644 src/internal/slibtool_mapfile_impl.c (limited to 'src/internal/slibtool_mapfile_impl.c') diff --git a/src/internal/slibtool_mapfile_impl.c b/src/internal/slibtool_mapfile_impl.c new file mode 100644 index 0000000..e5d40d1 --- /dev/null +++ b/src/internal/slibtool_mapfile_impl.c @@ -0,0 +1,78 @@ +#include +#include +#include +#include +#include +#include +#include +#include "slibtool_mapfile_impl.h" + +static void slbt_munmap(void * addr, size_t size) +{ + if (addr) { + munmap(addr,size); + } +} + +struct slbt_map_info * slbt_map_file( + int fdat, + const char * path, + uint32_t flags) +{ + int fd; + void * addr; + struct stat st; + uint32_t oflag; + uint32_t mprot; + struct slbt_map_info * mapinfo; + + if ((flags & SLBT_MAP_INPUT) && (flags & SLBT_MAP_OUTPUT)) { + oflag = O_RDWR; + mprot = PROT_READ|PROT_WRITE; + } else if (flags & SLBT_MAP_INPUT) { + oflag = O_RDONLY; + mprot = PROT_READ; + } else if (flags & SLBT_MAP_OUTPUT) { + oflag = O_WRONLY; + mprot = PROT_WRITE; + } else { + errno = EINVAL; + return 0; + } + + if ((fd = openat(fdat,path,oflag,0)) < 0) + return 0; + + if (fstat(fd,&st) < 0) { + close(fd); + return 0; + } + + addr = st.st_size + ? mmap(0,st.st_size,mprot,MAP_SHARED,fd,0) + : 0; + + if (addr == MAP_FAILED) { + close(fd); + return 0; + } + + if (!(mapinfo = malloc(sizeof(*mapinfo)))) { + close(fd); + slbt_munmap(addr,st.st_size); + return 0; + } + + close(fd); + + mapinfo->addr = addr; + mapinfo->size = st.st_size; + + return mapinfo; +} + +void slbt_unmap_file(struct slbt_map_info * mapinfo) +{ + slbt_munmap(mapinfo->addr,mapinfo->size); + free(mapinfo); +} -- cgit v1.2.3