/*
 *
 * honggfuzz - file operations
 * -----------------------------------------
 *
 * Author: Robert Swiecki <swiecki@google.com>
 *
 * Copyright 2010-2018 by Google Inc. All Rights Reserved.
 *
 * Licensed under the Apache License, Version 2.0 (the "License"); you may
 * not use this file except in compliance with the License. You may obtain
 * a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
 * implied. See the License for the specific language governing
 * permissions and limitations under the License.
 *
 */

#include "files.h"

#include <arpa/inet.h>
#include <dirent.h>
#include <errno.h>
#include <fcntl.h>
#include <inttypes.h>
#include <limits.h>
#if defined(_HF_ARCH_LINUX)
#include <linux/memfd.h>
#endif /* defined(_HF_ARCH_LINUX) */
#include <netinet/in.h>
#include <netinet/ip.h>
#include <stddef.h>
#include <stdint.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/mman.h>
#include <sys/socket.h>
#include <sys/stat.h>
#include <sys/un.h>
#if defined(_HF_ARCH_LINUX)
#include <sys/syscall.h>
#endif /* defined(_HF_ARCH_LINUX) */
#include <sys/time.h>
#include <sys/types.h>
#include <unistd.h>

#include "common.h"
#include "log.h"
#include "util.h"

ssize_t files_readFileToBufMax(const char* fname, uint8_t* buf, size_t fileMaxSz) {
    int fd = TEMP_FAILURE_RETRY(open(fname, O_RDONLY | O_CLOEXEC));
    if (fd == -1) {
        PLOG_W("Couldn't open '%s' for R/O", fname);
        return -1;
    }

    ssize_t readSz = files_readFromFd(fd, buf, fileMaxSz);
    if (readSz < 0) {
        PLOG_W("Couldn't read '%s' to a buf (size=%zu)", fname, fileMaxSz);
    }
    close(fd);

    LOG_D("Read %zu bytes (%zu requested) from '%s'", (size_t)readSz, fileMaxSz, fname);
    return readSz;
}

bool files_writeBufToFile(const char* fname, const uint8_t* buf, size_t fileSz, int flags) {
    int fd = TEMP_FAILURE_RETRY(open(fname, flags, 0644));
    if (fd == -1) {
        PLOG_W("Couldn't create/open '%s' for R/W", fname);
        return false;
    }

    bool ret = files_writeToFd(fd, buf, fileSz);
    if (!ret) {
        PLOG_W("Couldn't write '%zu' bytes to file '%s' (fd='%d')", fileSz, fname, fd);
        unlink(fname);
    } else {
        LOG_D("Written '%zu' bytes to '%s'", fileSz, fname);
    }

    close(fd);
    return ret;
}

bool files_writeStrToFile(const char* fname, const char* str, int flags) {
    return files_writeBufToFile(fname, (uint8_t*)str, strlen(str), flags);
}

int files_writeBufToTmpFile(const char* dir, const uint8_t* buf, size_t fileSz, int flags) {
    char template[PATH_MAX];
    snprintf(template, sizeof(template), "%s/hfuzz.XXXXXX", dir);
    int fd = mkostemp(template, flags);
    if (fd == -1) {
        PLOG_W("mkostemp('%s') failed", template);
        return -1;
    }
    if (unlink(template) == -1) {
        PLOG_W("unlink('%s')", template);
    }
    if (!files_writeToFd(fd, buf, fileSz)) {
        PLOG_W("Couldn't save data to the temporary file");
        close(fd);
        return -1;
    }
    if (lseek(fd, (off_t)0, SEEK_SET) == (off_t)-1) {
        PLOG_W("Couldn't rewind file '%s' fd=%d", template, fd);
        close(fd);
        return -1;
    }
    return fd;
}

bool files_writeToFd(int fd, const uint8_t* buf, size_t fileSz) {
    size_t writtenSz = 0;
    while (writtenSz < fileSz) {
        ssize_t sz = TEMP_FAILURE_RETRY(write(fd, &buf[writtenSz], fileSz - writtenSz));
        if (sz < 0) {
            return false;
        }
        writtenSz += sz;
    }
    return true;
}

bool files_writeStrToFd(int fd, const char* str) {
    return files_writeToFd(fd, (const uint8_t*)str, strlen(str));
}

ssize_t files_readFromFd(int fd, uint8_t* buf, size_t fileSz) {
    size_t readSz = 0;
    while (readSz < fileSz) {
        ssize_t sz = TEMP_FAILURE_RETRY(read(fd, &buf[readSz], fileSz - readSz));
        if (sz == 0) {
            break;
        }
        if (sz < 0) {
            return -1;
        }
        readSz += sz;
    }
    return (ssize_t)readSz;
}

ssize_t files_readFromFdSeek(int fd, uint8_t* buf, size_t fileSz, off_t off) {
    size_t readSz = 0;
    while (readSz < fileSz) {
        ssize_t sz =
            TEMP_FAILURE_RETRY(pread(fd, &buf[readSz], fileSz - readSz, off + (off_t)readSz));
        if (sz == 0) {
            break;
        }
        if (sz < 0) {
            return -1;
        }
        readSz += sz;
    }
    return (ssize_t)readSz;
}

bool files_exists(const char* fname) {
    return (access(fname, F_OK) != -1);
}

bool files_writePatternToFd(int fd, off_t size, unsigned char p) {
    void* buf = malloc(size);
    if (!buf) {
        PLOG_W("Couldn't allocate memory");
        return false;
    }

    memset(buf, p, (size_t)size);
    int ret = files_writeToFd(fd, buf, size);
    free(buf);

    return ret;
}

bool files_sendToSocketNB(int fd, const uint8_t* buf, size_t fileSz) {
    size_t writtenSz = 0;
    while (writtenSz < fileSz) {
        ssize_t sz =
            TEMP_FAILURE_RETRY(send(fd, &buf[writtenSz], fileSz - writtenSz, MSG_DONTWAIT));
        if (sz < 0) {
            return false;
        }
        writtenSz += sz;
    }
    return true;
}

bool files_sendToSocket(int fd, const uint8_t* buf, size_t fileSz) {
    int sendFlags = 0;
#ifdef _HF_ARCH_DARWIN
    sendFlags |= SO_NOSIGPIPE;
#else
    sendFlags |= MSG_NOSIGNAL;
#endif

    size_t writtenSz = 0;
    while (writtenSz < fileSz) {
        ssize_t sz = send(fd, &buf[writtenSz], fileSz - writtenSz, sendFlags);
        if (sz < 0 && errno == EINTR) continue;

        if (sz < 0) return false;

        writtenSz += sz;
    }
    return true;
}

const char* files_basename(const char* path) {
    const char* base = strrchr(path, '/');
    return base ? base + 1 : path;
}

/* Zero all bytes in the file */
bool files_resetFile(int fd, size_t sz) {
#if defined(_HF_ARCH_LINUX)
    if (fallocate(fd, FALLOC_FL_PUNCH_HOLE | FALLOC_FL_KEEP_SIZE, (off_t)0, (off_t)sz) != -1) {
        return true;
    }
    PLOG_W("fallocate(fd=%d, FALLOC_FL_PUNCH_HOLE | FALLOC_FL_KEEP_SIZE, sz=%zu)", fd, sz);
#endif /* defined(_HF_ARCH_LINUX) */

    /* Fallback mode */
    if (TEMP_FAILURE_RETRY(ftruncate(fd, (off_t)0)) == -1) {
        PLOG_W("ftruncate(fd=%d, sz=0)", fd);
        return false;
    }
    if (TEMP_FAILURE_RETRY(ftruncate(fd, (off_t)sz)) == -1) {
        PLOG_W("ftruncate(fd=%d, sz=%zu)", fd, sz);
        return false;
    }
    return true;
}

/*
 * Reads symbols from src file (one per line) and append them to filterList. The
 * total number of added symbols is returned.
 *
 * Simple wildcard strings are also supported (e.g. mem*)
 */
size_t files_parseSymbolFilter(const char* srcFile, char*** filterList) {
    FILE* f = fopen(srcFile, "rb");
    if (f == NULL) {
        PLOG_W("Couldn't open '%s' - R/O mode", srcFile);
        return 0;
    }

    char*  lineptr     = NULL;
    size_t symbolsRead = 0, n = 0;
    for (;;) {
        if (getline(&lineptr, &n, f) == -1) {
            break;
        }

        if (strlen(lineptr) < 3) {
            LOG_F("Input symbol '%s' too short (strlen < 3)", lineptr);
            symbolsRead = 0;
            break;
        }
        if ((*filterList = (char**)util_Realloc(
                 *filterList, (symbolsRead + 1) * sizeof((*filterList)[0]))) == NULL) {
            PLOG_W("realloc failed (sz=%zu)", (symbolsRead + 1) * sizeof((*filterList)[0]));
            symbolsRead = 0;
            break;
        }
        (*filterList)[symbolsRead] = malloc(strlen(lineptr));
        if (!(*filterList)[symbolsRead]) {
            PLOG_E("malloc(%zu) failed", strlen(lineptr));
            symbolsRead = 0;
            break;
        }
        snprintf((*filterList)[symbolsRead], strlen(lineptr), "%s", lineptr);
        symbolsRead++;
    }

    LOG_I("%zu filter symbols added to list", symbolsRead);
    fclose(f);
    free(lineptr);
    return symbolsRead;
}

uint8_t* files_mapFile(const char* fname, off_t* fileSz, int* fd, bool isWritable) {
    int mmapProt = PROT_READ;
    if (isWritable) {
        mmapProt |= PROT_WRITE;
    }

    if ((*fd = TEMP_FAILURE_RETRY(open(fname, O_RDONLY))) == -1) {
        PLOG_W("Couldn't open() '%s' file in R/O mode", fname);
        return NULL;
    }

    struct stat st;
    if (fstat(*fd, &st) == -1) {
        PLOG_W("Couldn't stat() the '%s' file", fname);
        close(*fd);
        return NULL;
    }

    uint8_t* buf;
    if ((buf = mmap(NULL, st.st_size, mmapProt, MAP_PRIVATE, *fd, 0)) == MAP_FAILED) {
        PLOG_W("Couldn't mmap() the '%s' file", fname);
        close(*fd);
        return NULL;
    }

    *fileSz = st.st_size;
    return buf;
}

/* mmap flags for various OSs, when mmap'ing a temporary file or a shared mem */
int files_getTmpMapFlags(int flag, bool nocore) {
#if defined(MAP_NOSYNC)
    /*
     * Some kind of bug in FreeBSD kernel. Without this flag, the shm_open() memory will cause a lot
     * of troubles to the calling process when mmap()'d
     */
    flag |= MAP_NOSYNC;
#endif /* defined(MAP_NOSYNC) */
#if defined(MAP_HASSEMAPHORE)
    /* Our shared/mmap'd pages can have mutexes in them */
    flag |= MAP_HASSEMAPHORE;
#endif /* defined(MAP_HASSEMAPHORE) */
    if (nocore) {
#if defined(MAP_CONCEAL)
        flag |= MAP_CONCEAL;
#endif /* defined(MAP_CONCEAL) */
#if defined(MAP_NOCORE)
        flag |= MAP_NOCORE;
#endif /* defined(MAP_NOCORE) */
    }
    return flag;
}

int files_createSharedMem(size_t sz, const char* name, bool exportmap) {
    int fd = -1;

    if (exportmap) {
        char path[PATH_MAX];
        snprintf(path, sizeof(path), "./%s", name);
        if ((fd = open(path, O_RDWR | O_CREAT | O_TRUNC | O_CLOEXEC, 0644)) == -1) {
            PLOG_W("open('%s')", path);
            return -1;
        }
    }

#if defined(_HF_ARCH_LINUX)
    if (fd == -1) {
        fd = syscall(__NR_memfd_create, name, (uintptr_t)(MFD_CLOEXEC));
    }
#endif /* defined(_HF_ARCH_LINUX) */

/* SHM_ANON is available with some *BSD OSes */
#if defined(SHM_ANON)
    if (fd == -1) {
        if ((fd = shm_open(SHM_ANON, O_RDWR, 0600)) == -1) {
            PLOG_W("shm_open(SHM_ANON, O_RDWR, 0600)");
        }
    }
#endif /* defined(SHM_ANON) */

/* Use regular shm_open */
#if !defined(_HF_ARCH_DARWIN) && !defined(__ANDROID__)
    /* shm objects under MacOSX are 'a-typical' */
    if (fd == -1) {
        char           tmpname[PATH_MAX];
        struct timeval tv;
        gettimeofday(&tv, NULL);
        snprintf(tmpname, sizeof(tmpname), "/%s%lx%lx%d", name, (unsigned long)tv.tv_sec,
            (unsigned long)tv.tv_usec, (int)getpid());
        if ((fd = shm_open(tmpname, O_RDWR | O_CREAT | O_EXCL, 0600)) == -1) {
            PLOG_W("shm_open('%s', O_RDWR|O_CREAT|O_EXCL, 0600)", tmpname);
        } else {
            shm_unlink(tmpname);
        }
    }
#endif /* !defined(_HF_ARCH_DARWIN) && !defined(__ANDROID__) */

    /* As the last resort, create a file in /tmp */
    if (fd == -1) {
        char template[PATH_MAX];
        snprintf(template, sizeof(template), "/tmp/%s.XXXXXX", name);
        if ((fd = mkostemp(template, O_CLOEXEC)) == -1) {
            PLOG_W("mkstemp('%s')", template);
            return -1;
        }
        unlink(template);
    }

    if (TEMP_FAILURE_RETRY(ftruncate(fd, sz)) == -1) {
        PLOG_W("ftruncate(%d, %zu)", fd, sz);
        close(fd);
        return -1;
    }

    return fd;
}

void* files_mapSharedMem(size_t sz, int* fd, const char* name, bool nocore, bool exportmap) {
    *fd = files_createSharedMem(sz, name, exportmap);
    if (*fd == -1) {
        return NULL;
    }

    int   mflags = files_getTmpMapFlags(MAP_SHARED, /* nocore= */ true);
    void* ret    = mmap(NULL, sz, PROT_READ | PROT_WRITE, mflags, *fd, 0);
    if (ret == MAP_FAILED) {
        PLOG_W("mmap(sz=%zu, fd=%d)", sz, *fd);
        *fd = -1;
        close(*fd);
        return NULL;
    }
    if (posix_madvise(ret, sz, POSIX_MADV_RANDOM) == -1) {
        PLOG_W("posix_madvise(sz=%zu, POSIX_MADV_RANDOM)", sz);
    }
    if (nocore) {
#if defined(MADV_DONTDUMP)
        if (madvise(ret, sz, MADV_DONTDUMP) == -1) {
            PLOG_W("madvise(sz=%zu, MADV_DONTDUMP)", sz);
        }
#endif /* defined(MADV_DONTDUMP) */
#if defined(MADV_NOCORE)
        if (madvise(ret, sz, MADV_NOCORE) == -1) {
            PLOG_W("madvise(sz=%zu, MADV_NOCORE)", sz);
        }
#endif /* defined(MADV_NOCORE) */
    }
    return ret;
}

sa_family_t files_sockFamily(int sock) {
    struct sockaddr addr;
    socklen_t       addrlen = sizeof(addr);

    if (getsockname(sock, &addr, &addrlen) == -1) {
        PLOG_W("getsockname(sock=%d)", sock);
        return AF_UNSPEC;
    }

    return addr.sa_family;
}

const char* files_sockAddrToStr(const struct sockaddr* sa, const socklen_t len) {
    static __thread char str[4096];

    if (sa->sa_family == AF_INET) {
        struct sockaddr_in* sin = (struct sockaddr_in*)sa;
        if (inet_ntop(sin->sin_family, &sin->sin_addr.s_addr, str, sizeof(str))) {
            util_ssnprintf(str, sizeof(str), "/%hd", ntohs(sin->sin_port));
        } else {
            snprintf(str, sizeof(str), "IPv4 addr conversion failed");
        }
        return str;
    }
    if (sa->sa_family == AF_INET6) {
        struct sockaddr_in6* sin6 = (struct sockaddr_in6*)sa;
        if (inet_ntop(sin6->sin6_family, sin6->sin6_addr.s6_addr, str, sizeof(str))) {
            util_ssnprintf(str, sizeof(str), "/%hd", ntohs(sin6->sin6_port));
        } else {
            snprintf(str, sizeof(str), "IPv6 addr conversion failed");
        }
        return str;
    }

    if (sa->sa_family == AF_UNIX) {
        if ((size_t)len <= offsetof(struct sockaddr_un, sun_path)) {
            snprintf(str, sizeof(str), "unix:<struct too short at %u bytes>", (unsigned)len);
            return str;
        }

        struct sockaddr_un* sun = (struct sockaddr_un*)sa;
        int                 pathlen;

        if (sun->sun_path[0] == '\0') {
            /* Abstract socket
             *
             * TODO: Handle null bytes in sun->sun_path (they have no
             * special significance unlike in C char arrays, see unix(7))
             */
            pathlen = strnlen(&sun->sun_path[1], len - offsetof(struct sockaddr_un, sun_path) - 1);

            snprintf(str, sizeof(str), "unix:abstract:%-*s", pathlen, &sun->sun_path[1]);
            return str;
        }

        pathlen = strnlen(sun->sun_path, len - offsetof(struct sockaddr_un, sun_path));

        snprintf(str, sizeof(str), "unix:%-*s", pathlen, sun->sun_path);
        return str;
    }

    snprintf(str, sizeof(str), "Unsupported sockaddr family=%d", (int)sa->sa_family);
    return str;
}
