#include <arpa/inet.h>
#include <iostream>
#include <chrono>
#include <cutils/sockets.h>
#include <hardware/gralloc.h>
#include <vector>
#include <tuple>
#include <algorithm>
#include <tuple>
#include <numeric>
#include <fcntl.h>
#include <string>
#include <fstream>
#include <sys/stat.h>
#include <sys/wait.h>
#include <unistd.h>

using namespace std;

#define ASSERT_TRUE(cond) \
do { \
    if (!(cond)) {\
       cerr << __func__ << "( " << getpid() << "):" << __LINE__ << " condition:" << #cond << " failed\n" << endl; \
       exit(EXIT_FAILURE); \
    } \
} while (0)

class Pipe {
    int m_readFd;
    int m_writeFd;
    Pipe(const Pipe &) = delete;
    Pipe& operator=(const Pipe &) = delete;
    Pipe& operator=(const Pipe &&) = delete;
public:
    Pipe(int readFd, int writeFd) : m_readFd{readFd}, m_writeFd{writeFd} {
        fcntl(m_readFd, F_SETFD, FD_CLOEXEC);
        fcntl(m_writeFd, F_SETFD, FD_CLOEXEC);
    }
    Pipe(Pipe&& rval) noexcept {
        m_readFd = rval.m_readFd;
        m_writeFd = rval.m_writeFd;
        rval.m_readFd = 0;
        rval.m_writeFd = 0;
    }
    ~Pipe() {
        if (m_readFd)
            close(m_readFd);
        if (m_writeFd)
            close(m_writeFd);
    }
    void preserveOverFork(bool preserve) {
        if (preserve) {
            fcntl(m_readFd, F_SETFD, 0);
            fcntl(m_writeFd, F_SETFD,0);
        } else {
            fcntl(m_readFd, F_SETFD, FD_CLOEXEC);
            fcntl(m_writeFd, F_SETFD, FD_CLOEXEC);
        }
    }
    int getReadFd() {
        return m_readFd;
    }
    int getWriteFd() {
        return m_writeFd;
    }
    void signal() {
        bool val = true;
        int error = write(m_writeFd, &val, sizeof(val));
        ASSERT_TRUE(error == sizeof(val));
    };
    void wait() {
        bool val = false;
        int error = read(m_readFd, &val, sizeof(val));
        ASSERT_TRUE(error == sizeof(val));
    }
    bool wait_ret_error() {
        bool val = false;
        int error = read(m_readFd, &val, sizeof(val));
        return (error != 1);
    }
    template <typename T> void send(const T& v) {
        int error = write(m_writeFd, &v, sizeof(T));
        ASSERT_TRUE(error >= 0);
    }
    template <typename T> void recv(T& v) {
        int error = read(m_readFd, &v, sizeof(T));
        ASSERT_TRUE(error >= 0);
    }
    static Pipe makePipeFromFds(int readFd, int writeFd) {
        return Pipe(readFd, writeFd);
    }
    static tuple<Pipe, Pipe> createPipePair() {
        int a[2];
        int b[2];

        int error1 = pipe(a);
        int error2 = pipe(b);
        ASSERT_TRUE(error1 >= 0);
        ASSERT_TRUE(error2 >= 0);

        return make_tuple(Pipe(a[0], b[1]), Pipe(b[0], a[1]));
    }
};

void createProcess(Pipe pipe, const char *exName, const char *arg)
{
    pipe.preserveOverFork(true);
    pid_t pid = fork();
    // child proc
    if (pid == 0) {
        char readFdStr[16];
        char writeFdStr[16];
        snprintf(readFdStr, sizeof(readFdStr), "%d", pipe.getReadFd());
        snprintf(writeFdStr, sizeof(writeFdStr), "%d", pipe.getWriteFd());
        execl(exName, exName, "--worker", arg, readFdStr, writeFdStr, nullptr);
        ASSERT_TRUE(0);
    }
    // parent process
    else if (pid > 0) {
        pipe.preserveOverFork(false);
        return;
    }
    else {
        ASSERT_TRUE(0);
    }
}


static void write_oomadj_to_lmkd(int oomadj) {
    // Connect to lmkd and store our oom_adj
    int lmk_procprio_cmd[4];
    int sock;
    int tries = 10;
    while ((sock = socket_local_client("lmkd",
                    ANDROID_SOCKET_NAMESPACE_RESERVED,
                    SOCK_SEQPACKET)) < 0) {
        usleep(100000);
        if (tries-- < 0) break;
    }
    if (sock < 0) {
        cout << "Failed to connect to lmkd, errno " << errno << endl;
        exit(1);
    }
    lmk_procprio_cmd[0] = htonl(1);
    lmk_procprio_cmd[1] = htonl(getpid());
    lmk_procprio_cmd[2] = htonl(getuid());
    lmk_procprio_cmd[3] = htonl(oomadj);

    int written = write(sock, lmk_procprio_cmd, sizeof(lmk_procprio_cmd));
    cout << "Wrote " << written << " bytes to lmkd control socket." << endl;
}

#ifdef ENABLE_MEM_CGROUPS
static void create_memcg() {
    char buf[256];
    pid_t pid = getpid();
    snprintf(buf, sizeof(buf), "/dev/memctl/apps/%u", pid);

    int tasks = mkdir(buf, S_IRWXU | S_IRWXG | S_IROTH | S_IXOTH);
    if (tasks < 0) {
        cout << "Failed to create memory cgroup" << endl;
        return;
    }
    snprintf(buf, sizeof(buf), "/dev/memctl/apps/%u/tasks", pid);
    tasks = open(buf, O_WRONLY);
    if (tasks < 0) {
        cout << "Unable to add process to memory cgroup" << endl;
        return;
    }
    snprintf(buf, sizeof(buf), "%u", pid);
    write(tasks, buf, strlen(buf));
    close(tasks);
}
#endif

size_t s = 4 * (1 << 20);
void *gptr;
int main(int argc, char *argv[])
{
    if ((argc > 1) && (std::string(argv[1]) == "--worker")) {
#ifdef ENABLE_MEM_CGROUPS
        create_memcg();
#endif
        write_oomadj_to_lmkd(atoi(argv[2]));
        Pipe p{atoi(argv[3]), atoi(argv[4])};

        long long allocCount = 0;
        while (1) {
            p.wait();
            char *ptr = (char*)malloc(s);
            memset(ptr, (int)allocCount >> 10, s);
            for (int i = 0; i < s; i+= 4096) {
                *((long long*)&ptr[i]) = allocCount + i;
            }
            usleep(10 * 1000);
            gptr = ptr;
            //cout << "total alloc: " << allocCount / (1<<20)<< " adj: " << argv[2]<< endl;;
            //cout << "ptr: " << (long long)(void*)ptr << endl;;
            p.signal();
            allocCount += s;
        }
    } else {
        cout << "parent:" << argc << endl;

        write_oomadj_to_lmkd(-1000);
        for (int i = 1000; i >= 0; i -= 100) {
            auto pipes = Pipe::createPipePair();
            char arg[16];
            snprintf(arg, sizeof(arg), "%d", i);
            createProcess(std::move(std::get<1>(pipes)), argv[0], arg);
            Pipe &p = std::get<0>(pipes);

            size_t t = 0;
            while (1) {
                //;cout << getpid() << ":" << "parent signal" << endl;
                p.signal();
                if (p.wait_ret_error()) {
                    int status;
                    waitpid(0, &status, 0);
                    break;
                }
                t += s;
            }
            cout << "adj: " << i << " sz: " << t / (1 << 20) << endl;
        }
    }
    return 0;
}
