/*
 * Copyright © 2014 Broadcom
 *
 * Permission is hereby granted, free of charge, to any person obtaining a
 * copy of this software and associated documentation files (the "Software"),
 * to deal in the Software without restriction, including without limitation
 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
 * and/or sell copies of the Software, and to permit persons to whom the
 * Software is furnished to do so, subject to the following conditions:
 *
 * The above copyright notice and this permission notice (including the next
 * paragraph) shall be included in all copies or substantial portions of the
 * Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
 * IN THE SOFTWARE.
 */

/**
 * DOC: Shader validator for VC4.
 *
 * The VC4 has no IOMMU between it and system memory, so a user with
 * access to execute shaders could escalate privilege by overwriting
 * system memory (using the VPM write address register in the
 * general-purpose DMA mode) or reading system memory it shouldn't
 * (reading it as a texture, or uniform data, or vertex data).
 *
 * This walks over a shader BO, ensuring that its accesses are
 * appropriately bounded, and recording how many texture accesses are
 * made and where so that we can do relocations for them in the
 * uniform stream.
 */

#include "vc4_drv.h"
#include "vc4_qpu_defines.h"

struct vc4_shader_validation_state {
	/* Current IP being validated. */
	uint32_t ip;

	/* IP at the end of the BO, do not read shader[max_ip] */
	uint32_t max_ip;

	uint64_t *shader;

	struct vc4_texture_sample_info tmu_setup[2];
	int tmu_write_count[2];

	/* For registers that were last written to by a MIN instruction with
	 * one argument being a uniform, the address of the uniform.
	 * Otherwise, ~0.
	 *
	 * This is used for the validation of direct address memory reads.
	 */
	uint32_t live_min_clamp_offsets[32 + 32 + 4];
	bool live_max_clamp_regs[32 + 32 + 4];

	/* Bitfield of which IPs are used as branch targets.
	 *
	 * Used for validation that the uniform stream is updated at the right
	 * points and clearing the texturing/clamping state.
	 */
	unsigned long *branch_targets;
};

static uint32_t
waddr_to_live_reg_index(uint32_t waddr, bool is_b)
{
	if (waddr < 32) {
		if (is_b)
			return 32 + waddr;
		else
			return waddr;
	} else if (waddr <= QPU_W_ACC3) {
		return 64 + waddr - QPU_W_ACC0;
	} else {
		return ~0;
	}
}

static uint32_t
raddr_add_a_to_live_reg_index(uint64_t inst)
{
	uint32_t sig = QPU_GET_FIELD(inst, QPU_SIG);
	uint32_t add_a = QPU_GET_FIELD(inst, QPU_ADD_A);
	uint32_t raddr_a = QPU_GET_FIELD(inst, QPU_RADDR_A);
	uint32_t raddr_b = QPU_GET_FIELD(inst, QPU_RADDR_B);

	if (add_a == QPU_MUX_A)
		return raddr_a;
	else if (add_a == QPU_MUX_B && sig != QPU_SIG_SMALL_IMM)
		return 32 + raddr_b;
	else if (add_a <= QPU_MUX_R3)
		return 64 + add_a;
	else
		return ~0;
}

static bool
is_tmu_submit(uint32_t waddr)
{
	return (waddr == QPU_W_TMU0_S ||
		waddr == QPU_W_TMU1_S);
}

static bool
is_tmu_write(uint32_t waddr)
{
	return (waddr >= QPU_W_TMU0_S &&
		waddr <= QPU_W_TMU1_B);
}

static bool
record_texture_sample(struct vc4_validated_shader_info *validated_shader,
		      struct vc4_shader_validation_state *validation_state,
		      int tmu)
{
	uint32_t s = validated_shader->num_texture_samples;
	int i;
	struct vc4_texture_sample_info *temp_samples;

	temp_samples = krealloc(validated_shader->texture_samples,
				(s + 1) * sizeof(*temp_samples),
				GFP_KERNEL);
	if (!temp_samples)
		return false;

	memcpy(&temp_samples[s],
	       &validation_state->tmu_setup[tmu],
	       sizeof(*temp_samples));

	validated_shader->num_texture_samples = s + 1;
	validated_shader->texture_samples = temp_samples;

	for (i = 0; i < 4; i++)
		validation_state->tmu_setup[tmu].p_offset[i] = ~0;

	return true;
}

static bool
check_tmu_write(struct vc4_validated_shader_info *validated_shader,
		struct vc4_shader_validation_state *validation_state,
		bool is_mul)
{
	uint64_t inst = validation_state->shader[validation_state->ip];
	uint32_t waddr = (is_mul ?
			  QPU_GET_FIELD(inst, QPU_WADDR_MUL) :
			  QPU_GET_FIELD(inst, QPU_WADDR_ADD));
	uint32_t raddr_a = QPU_GET_FIELD(inst, QPU_RADDR_A);
	uint32_t raddr_b = QPU_GET_FIELD(inst, QPU_RADDR_B);
	int tmu = waddr > QPU_W_TMU0_B;
	bool submit = is_tmu_submit(waddr);
	bool is_direct = submit && validation_state->tmu_write_count[tmu] == 0;
	uint32_t sig = QPU_GET_FIELD(inst, QPU_SIG);

	if (is_direct) {
		uint32_t add_b = QPU_GET_FIELD(inst, QPU_ADD_B);
		uint32_t clamp_reg, clamp_offset;

		if (sig == QPU_SIG_SMALL_IMM) {
			DRM_ERROR("direct TMU read used small immediate\n");
			return false;
		}

		/* Make sure that this texture load is an add of the base
		 * address of the UBO to a clamped offset within the UBO.
		 */
		if (is_mul ||
		    QPU_GET_FIELD(inst, QPU_OP_ADD) != QPU_A_ADD) {
			DRM_ERROR("direct TMU load wasn't an add\n");
			return false;
		}

		/* We assert that the the clamped address is the first
		 * argument, and the UBO base address is the second argument.
		 * This is arbitrary, but simpler than supporting flipping the
		 * two either way.
		 */
		clamp_reg = raddr_add_a_to_live_reg_index(inst);
		if (clamp_reg == ~0) {
			DRM_ERROR("direct TMU load wasn't clamped\n");
			return false;
		}

		clamp_offset = validation_state->live_min_clamp_offsets[clamp_reg];
		if (clamp_offset == ~0) {
			DRM_ERROR("direct TMU load wasn't clamped\n");
			return false;
		}

		/* Store the clamp value's offset in p1 (see reloc_tex() in
		 * vc4_validate.c).
		 */
		validation_state->tmu_setup[tmu].p_offset[1] =
			clamp_offset;

		if (!(add_b == QPU_MUX_A && raddr_a == QPU_R_UNIF) &&
		    !(add_b == QPU_MUX_B && raddr_b == QPU_R_UNIF)) {
			DRM_ERROR("direct TMU load didn't add to a uniform\n");
			return false;
		}

		validation_state->tmu_setup[tmu].is_direct = true;
	} else {
		if (raddr_a == QPU_R_UNIF || (sig != QPU_SIG_SMALL_IMM &&
					      raddr_b == QPU_R_UNIF)) {
			DRM_ERROR("uniform read in the same instruction as "
				  "texture setup.\n");
			return false;
		}
	}

	if (validation_state->tmu_write_count[tmu] >= 4) {
		DRM_ERROR("TMU%d got too many parameters before dispatch\n",
			  tmu);
		return false;
	}
	validation_state->tmu_setup[tmu].p_offset[validation_state->tmu_write_count[tmu]] =
		validated_shader->uniforms_size;
	validation_state->tmu_write_count[tmu]++;
	/* Since direct uses a RADDR uniform reference, it will get counted in
	 * check_instruction_reads()
	 */
	if (!is_direct)
		validated_shader->uniforms_size += 4;

	if (submit) {
		if (!record_texture_sample(validated_shader,
					   validation_state, tmu)) {
			return false;
		}

		validation_state->tmu_write_count[tmu] = 0;
	}

	return true;
}

static bool
check_reg_write(struct vc4_validated_shader_info *validated_shader,
		struct vc4_shader_validation_state *validation_state,
		bool is_mul)
{
	uint64_t inst = validation_state->shader[validation_state->ip];
	uint32_t waddr = (is_mul ?
			  QPU_GET_FIELD(inst, QPU_WADDR_MUL) :
			  QPU_GET_FIELD(inst, QPU_WADDR_ADD));

	switch (waddr) {
	case QPU_W_UNIFORMS_ADDRESS:
		/* XXX: We'll probably need to support this for reladdr, but
		 * it's definitely a security-related one.
		 */
		DRM_ERROR("uniforms address load unsupported\n");
		return false;

	case QPU_W_TLB_COLOR_MS:
	case QPU_W_TLB_COLOR_ALL:
	case QPU_W_TLB_Z:
		/* These only interact with the tile buffer, not main memory,
		 * so they're safe.
		 */
		return true;

	case QPU_W_TMU0_S:
	case QPU_W_TMU0_T:
	case QPU_W_TMU0_R:
	case QPU_W_TMU0_B:
	case QPU_W_TMU1_S:
	case QPU_W_TMU1_T:
	case QPU_W_TMU1_R:
	case QPU_W_TMU1_B:
		return check_tmu_write(validated_shader, validation_state,
				       is_mul);

	case QPU_W_HOST_INT:
	case QPU_W_TMU_NOSWAP:
	case QPU_W_TLB_ALPHA_MASK:
	case QPU_W_MUTEX_RELEASE:
		/* XXX: I haven't thought about these, so don't support them
		 * for now.
		 */
		DRM_ERROR("Unsupported waddr %d\n", waddr);
		return false;

	case QPU_W_VPM_ADDR:
		DRM_ERROR("General VPM DMA unsupported\n");
		return false;

	case QPU_W_VPM:
	case QPU_W_VPMVCD_SETUP:
		/* We allow VPM setup in general, even including VPM DMA
		 * configuration setup, because the (unsafe) DMA can only be
		 * triggered by QPU_W_VPM_ADDR writes.
		 */
		return true;

	case QPU_W_TLB_STENCIL_SETUP:
		return true;
	}

	return true;
}

static void
track_live_clamps(struct vc4_validated_shader_info *validated_shader,
		  struct vc4_shader_validation_state *validation_state)
{
	uint64_t inst = validation_state->shader[validation_state->ip];
	uint32_t op_add = QPU_GET_FIELD(inst, QPU_OP_ADD);
	uint32_t waddr_add = QPU_GET_FIELD(inst, QPU_WADDR_ADD);
	uint32_t waddr_mul = QPU_GET_FIELD(inst, QPU_WADDR_MUL);
	uint32_t cond_add = QPU_GET_FIELD(inst, QPU_COND_ADD);
	uint32_t add_a = QPU_GET_FIELD(inst, QPU_ADD_A);
	uint32_t add_b = QPU_GET_FIELD(inst, QPU_ADD_B);
	uint32_t raddr_a = QPU_GET_FIELD(inst, QPU_RADDR_A);
	uint32_t raddr_b = QPU_GET_FIELD(inst, QPU_RADDR_B);
	uint32_t sig = QPU_GET_FIELD(inst, QPU_SIG);
	bool ws = inst & QPU_WS;
	uint32_t lri_add_a, lri_add, lri_mul;
	bool add_a_is_min_0;

	/* Check whether OP_ADD's A argumennt comes from a live MAX(x, 0),
	 * before we clear previous live state.
	 */
	lri_add_a = raddr_add_a_to_live_reg_index(inst);
	add_a_is_min_0 = (lri_add_a != ~0 &&
			  validation_state->live_max_clamp_regs[lri_add_a]);

	/* Clear live state for registers written by our instruction. */
	lri_add = waddr_to_live_reg_index(waddr_add, ws);
	lri_mul = waddr_to_live_reg_index(waddr_mul, !ws);
	if (lri_mul != ~0) {
		validation_state->live_max_clamp_regs[lri_mul] = false;
		validation_state->live_min_clamp_offsets[lri_mul] = ~0;
	}
	if (lri_add != ~0) {
		validation_state->live_max_clamp_regs[lri_add] = false;
		validation_state->live_min_clamp_offsets[lri_add] = ~0;
	} else {
		/* Nothing further to do for live tracking, since only ADDs
		 * generate new live clamp registers.
		 */
		return;
	}

	/* Now, handle remaining live clamp tracking for the ADD operation. */

	if (cond_add != QPU_COND_ALWAYS)
		return;

	if (op_add == QPU_A_MAX) {
		/* Track live clamps of a value to a minimum of 0 (in either
		 * arg).
		 */
		if (sig != QPU_SIG_SMALL_IMM || raddr_b != 0 ||
		    (add_a != QPU_MUX_B && add_b != QPU_MUX_B)) {
			return;
		}

		validation_state->live_max_clamp_regs[lri_add] = true;
	} else if (op_add == QPU_A_MIN) {
		/* Track live clamps of a value clamped to a minimum of 0 and
		 * a maximum of some uniform's offset.
		 */
		if (!add_a_is_min_0)
			return;

		if (!(add_b == QPU_MUX_A && raddr_a == QPU_R_UNIF) &&
		    !(add_b == QPU_MUX_B && raddr_b == QPU_R_UNIF &&
		      sig != QPU_SIG_SMALL_IMM)) {
			return;
		}

		validation_state->live_min_clamp_offsets[lri_add] =
			validated_shader->uniforms_size;
	}
}

static bool
check_instruction_writes(struct vc4_validated_shader_info *validated_shader,
			 struct vc4_shader_validation_state *validation_state)
{
	uint64_t inst = validation_state->shader[validation_state->ip];
	uint32_t waddr_add = QPU_GET_FIELD(inst, QPU_WADDR_ADD);
	uint32_t waddr_mul = QPU_GET_FIELD(inst, QPU_WADDR_MUL);
	bool ok;

	if (is_tmu_write(waddr_add) && is_tmu_write(waddr_mul)) {
		DRM_ERROR("ADD and MUL both set up textures\n");
		return false;
	}

	ok = (check_reg_write(validated_shader, validation_state, false) &&
	      check_reg_write(validated_shader, validation_state, true));

	track_live_clamps(validated_shader, validation_state);

	return ok;
}

static bool
check_instruction_reads(uint64_t inst,
			struct vc4_validated_shader_info *validated_shader)
{
	uint32_t raddr_a = QPU_GET_FIELD(inst, QPU_RADDR_A);
	uint32_t raddr_b = QPU_GET_FIELD(inst, QPU_RADDR_B);
	uint32_t sig = QPU_GET_FIELD(inst, QPU_SIG);

	if (raddr_a == QPU_R_UNIF ||
	    (raddr_b == QPU_R_UNIF && sig != QPU_SIG_SMALL_IMM)) {
		/* This can't overflow the uint32_t, because we're reading 8
		 * bytes of instruction to increment by 4 here, so we'd
		 * already be OOM.
		 */
		validated_shader->uniforms_size += 4;
	}

	return true;
}

/* Make sure that all branches are absolute and point within the shader, and
 * note their targets for later.
 */
static bool
vc4_validate_branches(struct vc4_shader_validation_state *validation_state)
{
	uint32_t max_branch_target = 0;
	bool found_shader_end = false;
	int ip;
	int shader_end_ip = 0;
	int last_branch = -2;

	for (ip = 0; ip < validation_state->max_ip; ip++) {
		uint64_t inst = validation_state->shader[ip];
		int32_t branch_imm = QPU_GET_FIELD(inst, QPU_BRANCH_TARGET);
		uint32_t sig = QPU_GET_FIELD(inst, QPU_SIG);
		uint32_t after_delay_ip = ip + 4;
		uint32_t branch_target_ip;

		if (sig == QPU_SIG_PROG_END) {
			shader_end_ip = ip;
			found_shader_end = true;
			continue;
		}

		if (sig != QPU_SIG_BRANCH)
			continue;

		if (ip - last_branch < 4) {
			DRM_ERROR("Branch at %d during delay slots\n", ip);
			return false;
		}
		last_branch = ip;

		if (inst & QPU_BRANCH_REG) {
			DRM_ERROR("branching from register relative "
				  "not supported\n");
			return false;
		}

		if (!(inst & QPU_BRANCH_REL)) {
			DRM_ERROR("relative branching required\n");
			return false;
		}

		/* The actual branch target is the instruction after the delay
		 * slots, plus whatever byte offset is in the low 32 bits of
		 * the instruction.  Make sure we're not branching beyond the
		 * end of the shader object.
		 */
		if (branch_imm % sizeof(inst) != 0) {
			DRM_ERROR("branch target not aligned\n");
			return false;
		}

		branch_target_ip = after_delay_ip + (branch_imm >> 3);
		if (branch_target_ip >= validation_state->max_ip) {
			DRM_ERROR("Branch at %d outside of shader (ip %d/%d)\n",
				  ip, branch_target_ip,
				  validation_state->max_ip);
			return false;
		}
		set_bit(branch_target_ip, validation_state->branch_targets);

		/* Make sure that the non-branching path is also not outside
		 * the shader.
		 */
		if (after_delay_ip >= validation_state->max_ip) {
			DRM_ERROR("Branch at %d continues past shader end "
				  "(%d/%d)\n",
				  ip, after_delay_ip, validation_state->max_ip);
			return false;
		}
		set_bit(after_delay_ip, validation_state->branch_targets);
		max_branch_target = max(max_branch_target, after_delay_ip);

		/* There are two delay slots after program end is signaled
		 * that are still executed, then we're finished.
		 */
		if (found_shader_end && ip == shader_end_ip + 2)
			break;
	}

	if (max_branch_target > shader_end_ip) {
		DRM_ERROR("Branch landed after QPU_SIG_PROG_END");
		return false;
	}

	return true;
}

struct vc4_validated_shader_info *
vc4_validate_shader(struct drm_gem_cma_object *shader_obj)
{
	bool found_shader_end = false;
	int shader_end_ip = 0;
	uint32_t ip;
	struct vc4_validated_shader_info *validated_shader = NULL;
	struct vc4_shader_validation_state validation_state;
	int i;

	memset(&validation_state, 0, sizeof(validation_state));
	validation_state.shader = shader_obj->vaddr;
	validation_state.max_ip = shader_obj->base.size / sizeof(uint64_t);

	for (i = 0; i < 8; i++)
		validation_state.tmu_setup[i / 4].p_offset[i % 4] = ~0;
	for (i = 0; i < ARRAY_SIZE(validation_state.live_min_clamp_offsets); i++)
		validation_state.live_min_clamp_offsets[i] = ~0;

	validation_state.branch_targets =
		kcalloc(BITS_TO_LONGS(validation_state.max_ip),
			sizeof(unsigned long), GFP_KERNEL);
	if (!validation_state.branch_targets)
		goto fail;

	validated_shader = kcalloc(1, sizeof(*validated_shader), GFP_KERNEL);
	if (!validated_shader)
		goto fail;

	if (!vc4_validate_branches(&validation_state))
		goto fail;

	for (ip = 0; ip < validation_state.max_ip; ip++) {
		uint64_t inst = validation_state.shader[ip];
		uint32_t sig = QPU_GET_FIELD(inst, QPU_SIG);

		validation_state.ip = ip;

		switch (sig) {
		case QPU_SIG_NONE:
		case QPU_SIG_WAIT_FOR_SCOREBOARD:
		case QPU_SIG_SCOREBOARD_UNLOCK:
		case QPU_SIG_COLOR_LOAD:
		case QPU_SIG_LOAD_TMU0:
		case QPU_SIG_LOAD_TMU1:
		case QPU_SIG_PROG_END:
		case QPU_SIG_SMALL_IMM:
			if (!check_instruction_writes(validated_shader,
						      &validation_state)) {
				DRM_ERROR("Bad write at ip %d\n", ip);
				goto fail;
			}

			if (!check_instruction_reads(inst, validated_shader))
				goto fail;

			if (sig == QPU_SIG_PROG_END) {
				found_shader_end = true;
				shader_end_ip = ip;
			}

			break;

		case QPU_SIG_LOAD_IMM:
			if (!check_instruction_writes(validated_shader,
						      &validation_state)) {
				DRM_ERROR("Bad LOAD_IMM write at ip %d\n", ip);
				goto fail;
			}
			break;

		default:
			DRM_ERROR("Unsupported QPU signal %d at "
				  "instruction %d\n", sig, ip);
			goto fail;
		}

		/* There are two delay slots after program end is signaled
		 * that are still executed, then we're finished.
		 */
		if (found_shader_end && ip == shader_end_ip + 2)
			break;
	}

	if (ip == validation_state.max_ip) {
		DRM_ERROR("shader failed to terminate before "
			  "shader BO end at %zd\n",
			  shader_obj->base.size);
		goto fail;
	}

	/* Again, no chance of integer overflow here because the worst case
	 * scenario is 8 bytes of uniforms plus handles per 8-byte
	 * instruction.
	 */
	validated_shader->uniforms_src_size =
		(validated_shader->uniforms_size +
		 4 * validated_shader->num_texture_samples);

	kfree(validation_state.branch_targets);

	return validated_shader;

fail:
	kfree(validation_state.branch_targets);
	if (validated_shader) {
		kfree(validated_shader->texture_samples);
		kfree(validated_shader);
	}
	return NULL;
}
