diff --git a/drivers/gpu/nvgpu/hal/init/hal_tu104.c b/drivers/gpu/nvgpu/hal/init/hal_tu104.c index ed5924362..acfe96a5b 100644 --- a/drivers/gpu/nvgpu/hal/init/hal_tu104.c +++ b/drivers/gpu/nvgpu/hal/init/hal_tu104.c @@ -1146,6 +1146,8 @@ static const struct gops_therm tu104_ops_therm = { #endif .elcg_init_idle_filters = NULL, #ifdef CONFIG_NVGPU_LS_PMU + .get_internal_sensor_curr_temp = + tu104_get_internal_sensor_curr_temp, .get_internal_sensor_limits = tu104_get_internal_sensor_limits, #endif }; diff --git a/drivers/gpu/nvgpu/hal/therm/therm_tu104.c b/drivers/gpu/nvgpu/hal/therm/therm_tu104.c index b2aa3ad59..b3c934aa0 100644 --- a/drivers/gpu/nvgpu/hal/therm/therm_tu104.c +++ b/drivers/gpu/nvgpu/hal/therm/therm_tu104.c @@ -35,3 +35,13 @@ void tu104_get_internal_sensor_limits(s32 *max_24_8, s32 *min_24_8) *max_24_8 = (0x87 << 8); *min_24_8 = (((u32)-216) << 8); } + +void tu104_get_internal_sensor_curr_temp(struct gk20a *g, u32 *temp_f24_8) +{ + u32 read_val; + + read_val = nvgpu_readl(g, therm_i2cs_sensor_00_r()); + + /* Convert from celsius to f24_8 format*/ + *temp_f24_8 = (read_val << 8); +} diff --git a/drivers/gpu/nvgpu/hal/therm/therm_tu104.h b/drivers/gpu/nvgpu/hal/therm/therm_tu104.h index 64e234d8e..1e036e32d 100644 --- a/drivers/gpu/nvgpu/hal/therm/therm_tu104.h +++ b/drivers/gpu/nvgpu/hal/therm/therm_tu104.h @@ -29,6 +29,7 @@ struct gk20a; +void tu104_get_internal_sensor_curr_temp(struct gk20a *g, u32 *temp_f24_8); void tu104_get_internal_sensor_limits(s32 *max_24_8, s32 *min_24_8); #endif diff --git a/drivers/gpu/nvgpu/include/nvgpu/gops/therm.h b/drivers/gpu/nvgpu/include/nvgpu/gops/therm.h index 9484a3101..9cdec4271 100644 --- a/drivers/gpu/nvgpu/include/nvgpu/gops/therm.h +++ b/drivers/gpu/nvgpu/include/nvgpu/gops/therm.h @@ -137,6 +137,7 @@ struct gops_therm { void (*therm_debugfs_init)(struct gk20a *g); #endif u32 (*therm_max_fpdiv_factor)(void); + void (*get_internal_sensor_curr_temp)(struct gk20a *g, u32 *temp_f24_8); /** @endcond DOXYGEN_SHOULD_SKIP_THIS */ }; diff --git a/drivers/gpu/nvgpu/os/linux/debug_therm_tu104.c b/drivers/gpu/nvgpu/os/linux/debug_therm_tu104.c index 276a68b78..eba6e25da 100644 --- a/drivers/gpu/nvgpu/os/linux/debug_therm_tu104.c +++ b/drivers/gpu/nvgpu/os/linux/debug_therm_tu104.c @@ -23,11 +23,27 @@ static int therm_get_internal_sensor_curr_temp(void *data, u64 *val) { struct gk20a *g = (struct gk20a *)data; u32 readval; - int err; + int err = 0; - err = nvgpu_pmu_therm_channel_get_curr_temp(g, &readval); - if (!err) + /* + * If PSTATE is enabled, temp value is taken from THERM_GET_STATUS. + * If PSTATE is disable, temp value is read from NV_THERM_I2CS_SENSOR_00 + * register value. + */ + if (nvgpu_is_enabled(g, NVGPU_PMU_PSTATE)) { + err = nvgpu_pmu_therm_channel_get_curr_temp(g, &readval); + if (!err) { + *val = readval; + } + } else { + if (!g->ops.therm.get_internal_sensor_curr_temp) { + nvgpu_err(g, "reading NV_THERM_I2CS_SENSOR_00 not enabled"); + return -EINVAL; + } + + g->ops.therm.get_internal_sensor_curr_temp(g, &readval); *val = readval; + } return err; } diff --git a/drivers/gpu/nvgpu/os/linux/ioctl_ctrl.c b/drivers/gpu/nvgpu/os/linux/ioctl_ctrl.c index d7eb39107..4d9001b8e 100644 --- a/drivers/gpu/nvgpu/os/linux/ioctl_ctrl.c +++ b/drivers/gpu/nvgpu/os/linux/ioctl_ctrl.c @@ -1744,9 +1744,24 @@ static int nvgpu_gpu_get_temperature(struct gk20a *g, if (err) return err; - err = nvgpu_pmu_therm_channel_get_curr_temp(g, &temp_f24_8); - if (err) { - return err; + /* + * If PSTATE is enabled, temp value is taken from THERM_GET_STATUS. + * If PSTATE is disable, temp value is read from NV_THERM_I2CS_SENSOR_00 + * register value. + */ + if (nvgpu_is_enabled(g, NVGPU_PMU_PSTATE)) { + err = nvgpu_pmu_therm_channel_get_curr_temp(g, &temp_f24_8); + if (err) { + nvgpu_err(g, "pmu therm channel get status failed"); + return err; + } + } else { + if (!g->ops.therm.get_internal_sensor_curr_temp) { + nvgpu_err(g, "reading NV_THERM_I2CS_SENSOR_00 not enabled"); + return -EINVAL; + } + + g->ops.therm.get_internal_sensor_curr_temp(g, &temp_f24_8); } gk20a_idle(g);