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

Commit da003b7c authored by Carter Cooper's avatar Carter Cooper
Browse files

msm: kgsl: Use one entry point for external HFI requests



For HFI requests that do not originate from HFI itself,
use a generic HFI function as the entry point. This keeps
the usage of different HFI requests simple and easy to
maintain when other functions start relying on HFI requests
more regularly.

Change-Id: I15213ebd6fa3e04a71c0727cf46920f6a2414af3
Signed-off-by: default avatarCarter Cooper <ccooper@codeaurora.org>
parent 8ecd48cc
Loading
Loading
Loading
Loading
+8 −2
Original line number Diff line number Diff line
@@ -28,6 +28,7 @@
#include "kgsl_log.h"
#include "kgsl.h"
#include "kgsl_gmu.h"
#include "kgsl_hfi.h"
#include "kgsl_trace.h"

#define MIN_HBB		13
@@ -955,7 +956,7 @@ static void a6xx_start(struct adreno_device *adreno_dev)
		gmu->bcl_config = 0;
		gmu->lm_dcvs_level = 0;

		result = hfi_send_lmconfig(gmu);
		result = hfi_send_req(gmu, H2F_MSG_LM_CFG, NULL);
		if (result)
			dev_err(dev, "Failure enabling limits management (%d)\n",
			result);
@@ -1797,7 +1798,12 @@ static int a6xx_notify_slumber(struct kgsl_device *device)
		a6xx_sptprac_disable(adreno_dev);

	if (!ADRENO_QUIRK(adreno_dev, ADRENO_QUIRK_HFI_USE_REG)) {
		ret = hfi_notify_slumber(gmu, perf_idx, bus_level);
		struct hfi_dcvs_vote req = {
			.perf_idx = perf_idx,
			.bw_idx = bus_level,
		};

		ret = hfi_send_req(gmu, H2F_MSG_PREPARE_SLUMBER, &req);
		goto out;
	}

+13 −10
Original line number Diff line number Diff line
@@ -446,27 +446,30 @@ int gmu_dcvs_set(struct gmu_device *gmu,
	struct kgsl_device *device = container_of(gmu, struct kgsl_device, gmu);
	struct adreno_device *adreno_dev = ADRENO_DEVICE(device);
	struct adreno_gpudev *gpudev = ADRENO_GPU_DEVICE(adreno_dev);
	int perf_idx = INVALID_DCVS_IDX, bw_idx = INVALID_DCVS_IDX;
	int ret;
	struct hfi_dcvs_vote req = {
		.ack_type = ACK_NONBLOCK,
		.perf_idx = INVALID_DCVS_IDX,
		.bw_idx = INVALID_DCVS_IDX,
	};

	if (gpu_pwrlevel < gmu->num_gpupwrlevels - 1)
		perf_idx = gmu->num_gpupwrlevels - gpu_pwrlevel - 1;
		req.perf_idx = gmu->num_gpupwrlevels - gpu_pwrlevel - 1;

	if (bus_level < gmu->num_bwlevels && bus_level > 0)
		bw_idx = bus_level;
		req.bw_idx = bus_level;

	if ((perf_idx == INVALID_DCVS_IDX) &&
		(bw_idx == INVALID_DCVS_IDX))
	if ((req.perf_idx == INVALID_DCVS_IDX) &&
		(req.bw_idx == INVALID_DCVS_IDX))
		return -EINVAL;

	if (ADRENO_QUIRK(adreno_dev, ADRENO_QUIRK_HFI_USE_REG)) {
		ret = gpudev->rpmh_gpu_pwrctrl(adreno_dev,
			GMU_DCVS_NOHFI, perf_idx, bw_idx);
		int ret = gpudev->rpmh_gpu_pwrctrl(adreno_dev,
			GMU_DCVS_NOHFI, req.perf_idx, req.bw_idx);

		if (ret) {
			dev_err_ratelimited(&gmu->pdev->dev,
				"Failed to set GPU perf idx %d, bw idx %d\n",
				perf_idx, bw_idx);
				req.perf_idx, req.bw_idx);

			adreno_set_gpu_fault(adreno_dev, ADRENO_GMU_FAULT);
			adreno_dispatcher_schedule(device);
@@ -475,7 +478,7 @@ int gmu_dcvs_set(struct gmu_device *gmu,
		return ret;
	}

	return hfi_send_dcvs_vote(gmu, perf_idx, bw_idx, ACK_NONBLOCK);
	return hfi_send_req(gmu, H2F_MSG_DCVS_VOTE, &req);
}

struct rpmh_arc_vals {
+27 −2
Original line number Diff line number Diff line
@@ -459,7 +459,7 @@ static int hfi_send_test(struct gmu_device *gmu)
			msg_size_dwords, &msg);
}

int hfi_send_dcvs_vote(struct gmu_device *gmu, uint32_t perf_idx,
static int hfi_send_dcvs_vote(struct gmu_device *gmu, uint32_t perf_idx,
		uint32_t bw_idx, enum rpm_ack_type ack_type)
{
	struct hfi_dcvs_cmd dcvs_cmd = {
@@ -495,7 +495,7 @@ int hfi_send_dcvs_vote(struct gmu_device *gmu, uint32_t perf_idx,
	return rc;
}

int hfi_notify_slumber(struct gmu_device *gmu,
static int hfi_notify_slumber(struct gmu_device *gmu,
		uint32_t init_perf_idx, uint32_t init_bw_idx)
{
	struct hfi_prep_slumber_cmd slumber_cmd = {
@@ -664,3 +664,28 @@ void hfi_stop(struct gmu_device *gmu)

	clear_bit(GMU_HFI_ON, &gmu->flags);
}

/* Entry point for external HFI requests */
int hfi_send_req(struct gmu_device *gmu, enum hfi_msg_id id, void *data)
{
	switch (id) {
	case H2F_MSG_LM_CFG: {
		return hfi_send_lmconfig(gmu);
	}
	case H2F_MSG_DCVS_VOTE: {
		struct hfi_dcvs_vote *req = (struct hfi_dcvs_vote *)data;

		return hfi_send_dcvs_vote(gmu, req->perf_idx, req->bw_idx,
				req->ack_type);
	}
	case H2F_MSG_PREPARE_SLUMBER: {
		struct hfi_dcvs_vote *req = (struct hfi_dcvs_vote *)data;

		return hfi_notify_slumber(gmu, req->perf_idx, req->bw_idx);
	}
	default:
		break;
	}

	return -EINVAL;
}
+10 −6
Original line number Diff line number Diff line
/* Copyright (c) 2017, The Linux Foundation. All rights reserved.
/* Copyright (c) 2017-2018, The Linux Foundation. All rights reserved.
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License version 2 and
@@ -267,6 +267,12 @@ enum rpm_ack_type {
	ACK_INVALID = 2,
};

struct hfi_dcvs_vote {
	uint32_t perf_idx;
	uint32_t bw_idx;
	enum rpm_ack_type ack_type;
};

struct gpu_dcvs_vote {
	uint32_t perf_idx : 8;
	uint32_t reserved : 20;
@@ -355,9 +361,7 @@ void hfi_stop(struct gmu_device *gmu);
void hfi_receiver(unsigned long data);
void hfi_init(struct kgsl_hfi *hfi, struct gmu_memdesc *mem_addr,
		uint32_t queue_sz_bytes);
int hfi_send_dcvs_vote(struct gmu_device *gmu, uint32_t perf_idx,
		uint32_t bw_idx, enum rpm_ack_type ack_type);
int hfi_notify_slumber(struct gmu_device *gmu, uint32_t init_perf_idx,
		uint32_t init_bw_idx);
int hfi_send_lmconfig(struct gmu_device *gmu);

/* hfi_send_req is only for external (to HFI) requests. */
int hfi_send_req(struct gmu_device *gmu, enum hfi_msg_id id, void *data);
#endif  /* __KGSL_HFI_H */