Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit b1cccd53 authored by Linux Build Service Account's avatar Linux Build Service Account Committed by Gerrit - the friendly Code Review server
Browse files

Merge "msm: kgsl: Clear pending transactions from VBIF on hang"

parents e6648086 8069dc48
Loading
Loading
Loading
Loading
+10 −0
Original line number Diff line number Diff line
@@ -545,7 +545,17 @@
#define A3XX_VBIF_PERF_PWR_CNT2_LO 0x307b
#define A3XX_VBIF_PERF_PWR_CNT2_HI 0x307c

#define A3XX_VBIF_XIN_HALT_CTRL0 0x3080
#define A3XX_VBIF_XIN_HALT_CTRL0_MASK 0x3F

#define A3XX_VBIF_XIN_HALT_CTRL1 0x3081

/* VBIF register offsets for A306 */
#define A3XX_VBIF2_XIN_HALT_CTRL0 0x3081
#define A3XX_VBIF2_XIN_HALT_CTRL0_MASK 0x7

#define A3XX_VBIF2_XIN_HALT_CTRL1 0x3082

#define A3XX_VBIF2_PERF_CNT_EN0 0x30c0
#define A3XX_VBIF2_PERF_CNT_EN1 0x30c1
#define A3XX_VBIF2_PERF_CNT_EN2 0x30c2
+6 −0
Original line number Diff line number Diff line
@@ -662,6 +662,12 @@ enum a4xx_vfd_perfctr_vfd_sel {
#define A4XX_VBIF_IN_WR_LIM_CONF0	0x3030
#define A4XX_VBIF_IN_WR_LIM_CONF1	0x3031
#define A4XX_VBIF_ROUND_ROBIN_QOS_ARB	0x3049

#define A4XX_VBIF_XIN_HALT_CTRL0	0x3080
#define A4XX_VBIF_XIN_HALT_CTRL0_MASK	0x1F

#define A4XX_VBIF_XIN_HALT_CTRL1	0x3081

#define A4XX_VBIF_TEST_BUS_OUT_CTRL		0x3084
#define A4XX_VBIF_TEST_BUS_OUT_CTRL_EN_MASK	0x1
#define A4XX_VBIF_TEST_BUS_OUT_CTRL_EN_SHIFT	0x0
+34 −0
Original line number Diff line number Diff line
@@ -516,6 +516,8 @@ adreno_identify_gpu(struct adreno_device *adreno_dev)
		if (reg_offsets->offset_0 != i && !reg_offsets->offsets[i])
			reg_offsets->offsets[i] = ADRENO_REG_UNUSED;
	}
	if (gpudev->gpudev_init)
		gpudev->gpudev_init(adreno_dev);
}

static const struct platform_device_id adreno_id_table[] = {
@@ -1291,6 +1293,35 @@ static int adreno_start(struct kgsl_device *device, int priority)
	return _status;
}

/**
 * adreno_vbif_clear_pending_transactions() - Clear transactions in VBIF pipe
 * @device: Pointer to the device whose VBIF pipe is to be cleared
 */
static void adreno_vbif_clear_pending_transactions(struct kgsl_device *device)
{
	struct adreno_device *adreno_dev = ADRENO_DEVICE(device);
	struct adreno_gpudev *gpudev = ADRENO_GPU_DEVICE(adreno_dev);
	unsigned int mask = gpudev->vbif_xin_halt_ctrl0_mask;
	unsigned int val;
	unsigned long wait_for_vbif;

	adreno_writereg(adreno_dev, ADRENO_REG_VBIF_XIN_HALT_CTRL0, mask);
	/* wait for the transactions to clear */
	wait_for_vbif = jiffies + msecs_to_jiffies(100);
	while (1) {
		adreno_readreg(adreno_dev,
			ADRENO_REG_VBIF_XIN_HALT_CTRL1, &val);
		if ((val & mask) == mask)
			break;
		if (time_after(jiffies, wait_for_vbif)) {
			KGSL_DRV_ERR(device,
				"Wait limit reached for VBIF XIN Halt\n");
			break;
		}
	}
	adreno_writereg(adreno_dev, ADRENO_REG_VBIF_XIN_HALT_CTRL0, 0);
}

static int adreno_stop(struct kgsl_device *device)
{
	struct adreno_device *adreno_dev = ADRENO_DEVICE(device);
@@ -1344,6 +1375,9 @@ int adreno_reset(struct kgsl_device *device)
	struct kgsl_mmu *mmu = &device->mmu;
	int i = 0;

	/* clear pending vbif transactions before reset */
	adreno_vbif_clear_pending_transactions(device);

	/* Try soft reset first, for non mmu fault case only */
	if (!atomic_read(&mmu->fault)) {
		ret = adreno_soft_reset(device);
+4 −0
Original line number Diff line number Diff line
@@ -432,6 +432,8 @@ enum adreno_regs {
	ADRENO_REG_RBBM_PERFCTR_LOAD_VALUE_HI,
	ADRENO_REG_RBBM_SECVID_TRUST_CONTROL,
	ADRENO_REG_RBBM_ALWAYSON_COUNTER_LO,
	ADRENO_REG_VBIF_XIN_HALT_CTRL0,
	ADRENO_REG_VBIF_XIN_HALT_CTRL1,
	ADRENO_REG_REGISTER_MAX,
};

@@ -595,9 +597,11 @@ struct adreno_gpudev {

	struct adreno_irq *irq;
	int num_prio_levels;
	unsigned int vbif_xin_halt_ctrl0_mask;
	/* GPU specific function hooks */
	void (*irq_trace)(struct adreno_device *, unsigned int status);
	void (*snapshot)(struct adreno_device *, struct kgsl_snapshot *);
	void (*gpudev_init)(struct adreno_device *);
	int (*rb_init)(struct adreno_device *, struct adreno_ringbuffer *);
	int (*perfcounter_init)(struct adreno_device *);
	void (*start)(struct adreno_device *);
+27 −0
Original line number Diff line number Diff line
@@ -708,6 +708,27 @@ int adreno_a3xx_pwron_fixup_init(struct adreno_device *adreno_dev)
	return 0;
}

/*
 * a3xx_gpudev_init() - Initialize gpudev specific fields
 * @adreno_dev: Pointer to adreno device
 */
void a3xx_gpudev_init(struct adreno_device *adreno_dev)
{
	struct adreno_gpudev *gpudev;
	const struct adreno_reg_offsets *reg_offsets;

	if (adreno_is_a306(adreno_dev)) {
		gpudev = ADRENO_GPU_DEVICE(adreno_dev);
		reg_offsets = gpudev->reg_offsets;
		reg_offsets->offsets[ADRENO_REG_VBIF_XIN_HALT_CTRL0] =
			A3XX_VBIF2_XIN_HALT_CTRL0;
		reg_offsets->offsets[ADRENO_REG_VBIF_XIN_HALT_CTRL1] =
			A3XX_VBIF2_XIN_HALT_CTRL1;
		gpudev->vbif_xin_halt_ctrl0_mask =
				A3XX_VBIF2_XIN_HALT_CTRL0_MASK;
	}
}

/*
 * a3xx_rb_init() - Initialize ringbuffer
 * @adreno_dev: Pointer to adreno device
@@ -2032,6 +2053,10 @@ static unsigned int a3xx_register_offsets[ADRENO_REG_REGISTER_MAX] = {
				A3XX_RBBM_PERFCTR_LOAD_VALUE_LO),
	ADRENO_REG_DEFINE(ADRENO_REG_RBBM_PERFCTR_LOAD_VALUE_HI,
				A3XX_RBBM_PERFCTR_LOAD_VALUE_HI),
	ADRENO_REG_DEFINE(ADRENO_REG_VBIF_XIN_HALT_CTRL0,
				A3XX_VBIF_XIN_HALT_CTRL0),
	ADRENO_REG_DEFINE(ADRENO_REG_VBIF_XIN_HALT_CTRL1,
				A3XX_VBIF_XIN_HALT_CTRL1),
};

const struct adreno_reg_offsets a3xx_reg_offsets = {
@@ -2065,7 +2090,9 @@ struct adreno_gpudev adreno_a3xx_gpudev = {
	.irq_trace = trace_kgsl_a3xx_irq_status,
	.snapshot_data = &a3xx_snapshot_data,
	.num_prio_levels = 1,
	.vbif_xin_halt_ctrl0_mask = A3XX_VBIF_XIN_HALT_CTRL0_MASK,

	.gpudev_init = a3xx_gpudev_init,
	.rb_init = a3xx_rb_init,
	.perfcounter_init = a3xx_perfcounter_init,
	.busy_cycles = a3xx_busy_cycles,
Loading