#!/usr/bin/env bash

set -x
set -e

PATH_OLD=$PATH
DATADIRS=/mnt/wd/data-prefetch

BUILDS=/home/tomas/builds
BUILDSHP=/home/tomas/builds-tmpfs

export MALLOC_TOP_PAD_=$((64*1024*1024))

RUNS=1

TS=$(date +%Y%m%d-%H%M%S)

killall -9 postgres || true
sleep 1

rm -Rf $DATADIRS

# copy all binaries into the huge-page tmpfs mount
rm -Rf $BUILDSHP/*
cp -R $BUILDS/* $BUILDSHP/

mkdir $TS

dir=$(pwd)


#for branch in master patched; do
for rows in 100; do

	for d in 1 10 100 1000; do

		for w in 8 4 1; do

			for dev in wd; do

				for branch in patched; do

					PATH=$BUILDSHP/$branch/bin:$PATH_OLD

					DATADIR=/mnt/$dev/data-prefetch/$branch

					rm -Rf $DATADIR

					pg_ctl -D $DATADIR init
					pg_checksums --disable $DATADIR
					pg_ctl -D $DATADIR start
					createdb test
					pg_ctl -D $DATADIR stop

					cp postgresql.conf $DATADIR

					pg_ctl -D $DATADIR -l $TS/pg.log start

					psql test -c "drop table if exists t1"
					psql test -c "drop table if exists t2"

					psql test -c "create unlogged table t1 (a bigint, b text)"
					psql test -c "create unlogged table t2 (a bigint, b text)"

					psql test -c "insert into t1 select i, md5((i/$d)::text) from generate_series(1, $rows * 1000000) s(i)"
					psql test -c "insert into t2 select i, md5((i/$d)::text) from generate_series(1, $rows * 1000000) s(i)"

					psql test -c "vacuum analyze"
					psql test -c "checkpoint"

					relpages=$(psql -t -A test -c "select relpages from pg_class where relname = 't1'")

					pg_ctl -D $DATADIR -l $TS/pg.log stop

					for c in no pglz lz4; do

						sudo ./drop-caches.sh

						cp postgresql.conf $DATADIR

						echo "io_method = io_uring" >> $DATADIR/postgresql.conf

						echo "enable_nestloop = off" >> $DATADIR/postgresql.conf
						echo "enable_mergejoin = off" >> $DATADIR/postgresql.conf
						echo "max_parallel_workers_per_gather = 0" >> $DATADIR/postgresql.conf
						echo "temp_file_compression = '$c'" >> $DATADIR/postgresql.conf

						for r in $(seq 1 $RUNS); do

							echo "===== $branch $c $r =====" >> $TS/explains.log

							sudo ./drop-caches.sh

							pg_ctl -D $DATADIR -l $TS/pg.log start

							psql test > $TS/explain.log 2>&1 <<EOF
EXPLAIN (SETTINGS) SELECT * FROM (SELECT * FROM t1 JOIN t2 ON (t1.a = t2.a) OFFSET 1000000000);
EOF

							cat $TS/explain.log >> $TS/explains.log

							bytes_start=$(psql -t -A test -c "select temp_bytes from pg_stat_database where datname = 'test'")

							s=$(psql -t -A test -c "select extract(epoch from now()) + 1")

							echo "select pg_sleep($s - extract(epoch from now()));" > tmp.sql
							echo "\timing on" >> tmp.sql
							echo "SELECT * FROM (SELECT * FROM t1 JOIN t2 ON (t1.a = t2.a) OFFSET 1000000000);" >> tmp.sql

							for x in $(seq 1 $w); do
								psql test < tmp.sql > $TS/tmp-$x.log 2>&1 &
							done

							wait

							times="0.0"
                                                        for x in $(seq 1 $w); do
                                                                t=$(grep 'Time:' $TS/tmp-$x.log | awk '{print $2}')
								times="$times + $t"
                                                        done

							time_uncached=$(echo "($times)/$w" | bc | awk '{printf "%f", $0}')
							bytes_uncached=$(psql -t -A test -c "select (temp_bytes - $bytes_start)/$w from pg_stat_database where datname = 'test'")

							pg_ctl -D $DATADIR -l $TS/pg.log stop

							echo $rows $d $w $dev $branch $relpages $c $r $time_uncached $bytes_uncached >> $TS/results.csv

						done

					done

				done

			done

		done

	done

done
