Loading drivers/gpu/drm/nouveau/nouveau_pm.c +5 −2 Original line number Diff line number Diff line Loading @@ -167,8 +167,11 @@ nouveau_pm_perflvl_get(struct drm_device *dev, struct nouveau_pm_level *perflvl) } } if (pm->fanspeed_get) perflvl->fanspeed = pm->fanspeed_get(dev); if (pm->fanspeed_get) { ret = pm->fanspeed_get(dev); if (ret > 0) perflvl->fanspeed = ret; } return 0; } Loading drivers/gpu/drm/nouveau/nouveau_pm.h +2 −0 Original line number Diff line number Diff line Loading @@ -66,6 +66,8 @@ int nv50_pm_clock_get(struct drm_device *, u32 id); void *nv50_pm_clock_pre(struct drm_device *, struct nouveau_pm_level *, u32 id, int khz); void nv50_pm_clock_set(struct drm_device *, void *); int nv50_pm_fanspeed_get(struct drm_device *); int nv50_pm_fanspeed_set(struct drm_device *, int percent); /* nva3_pm.c */ int nva3_pm_clocks_get(struct drm_device *, struct nouveau_pm_level *); Loading drivers/gpu/drm/nouveau/nouveau_state.c +4 −0 Original line number Diff line number Diff line Loading @@ -386,6 +386,8 @@ static int nouveau_init_engine_ptrs(struct drm_device *dev) engine->pm.temp_get = nv84_temp_get; else engine->pm.temp_get = nv40_temp_get; engine->pm.fanspeed_get = nv50_pm_fanspeed_get; engine->pm.fanspeed_set = nv50_pm_fanspeed_set; engine->vram.init = nv50_vram_init; engine->vram.takedown = nv50_vram_fini; engine->vram.get = nv50_vram_new; Loading Loading @@ -441,6 +443,8 @@ static int nouveau_init_engine_ptrs(struct drm_device *dev) engine->pm.clocks_get = nvc0_pm_clocks_get; engine->pm.voltage_get = nouveau_voltage_gpio_get; engine->pm.voltage_set = nouveau_voltage_gpio_set; engine->pm.fanspeed_get = nv50_pm_fanspeed_get; engine->pm.fanspeed_set = nv50_pm_fanspeed_set; break; case 0xd0: engine->instmem.init = nvc0_instmem_init; Loading drivers/gpu/drm/nouveau/nv50_pm.c +74 −0 Original line number Diff line number Diff line Loading @@ -144,3 +144,77 @@ nv50_pm_clock_set(struct drm_device *dev, void *pre_state) kfree(state); } struct pwm_info { int id; int invert; u8 tag; u32 ctrl; int line; }; static int nv50_pm_fanspeed_pwm(struct drm_device *dev, struct pwm_info *pwm) { struct dcb_gpio_entry *gpio; gpio = nouveau_bios_gpio_entry(dev, 0x09); if (gpio) { pwm->tag = gpio->tag; pwm->id = (gpio->line == 9) ? 1 : 0; pwm->invert = gpio->state[0] & 1; pwm->ctrl = (gpio->line < 16) ? 0xe100 : 0xe28c; pwm->line = (gpio->line & 0xf); return 0; } return -ENOENT; } int nv50_pm_fanspeed_get(struct drm_device *dev) { struct drm_nouveau_private *dev_priv = dev->dev_private; struct nouveau_gpio_engine *pgpio = &dev_priv->engine.gpio; struct pwm_info pwm; int ret; ret = nv50_pm_fanspeed_pwm(dev, &pwm); if (ret) return ret; if (nv_rd32(dev, pwm.ctrl) & (0x00000001 << pwm.line)) { u32 divs = nv_rd32(dev, 0x00e114 + (pwm.id * 8)); u32 duty = nv_rd32(dev, 0x00e118 + (pwm.id * 8)); if (divs) { divs = max(divs, duty); if (pwm.invert) duty = divs - duty; return (duty * 100) / divs; } return 0; } return pgpio->get(dev, pwm.tag) * 100; } int nv50_pm_fanspeed_set(struct drm_device *dev, int percent) { struct pwm_info pwm; u32 divs, duty; int ret; ret = nv50_pm_fanspeed_pwm(dev, &pwm); if (ret) return ret; divs = nv_rd32(dev, 0x00e114 + (pwm.id * 8)); duty = ((divs * percent) + 99) / 100; if (pwm.invert) duty = divs - duty; nv_mask(dev, pwm.ctrl, 0x00010001 << pwm.line, 0x00000001 << pwm.line); nv_wr32(dev, 0x00e118 + (pwm.id * 8), 0x80000000 | duty); return 0; } Loading
drivers/gpu/drm/nouveau/nouveau_pm.c +5 −2 Original line number Diff line number Diff line Loading @@ -167,8 +167,11 @@ nouveau_pm_perflvl_get(struct drm_device *dev, struct nouveau_pm_level *perflvl) } } if (pm->fanspeed_get) perflvl->fanspeed = pm->fanspeed_get(dev); if (pm->fanspeed_get) { ret = pm->fanspeed_get(dev); if (ret > 0) perflvl->fanspeed = ret; } return 0; } Loading
drivers/gpu/drm/nouveau/nouveau_pm.h +2 −0 Original line number Diff line number Diff line Loading @@ -66,6 +66,8 @@ int nv50_pm_clock_get(struct drm_device *, u32 id); void *nv50_pm_clock_pre(struct drm_device *, struct nouveau_pm_level *, u32 id, int khz); void nv50_pm_clock_set(struct drm_device *, void *); int nv50_pm_fanspeed_get(struct drm_device *); int nv50_pm_fanspeed_set(struct drm_device *, int percent); /* nva3_pm.c */ int nva3_pm_clocks_get(struct drm_device *, struct nouveau_pm_level *); Loading
drivers/gpu/drm/nouveau/nouveau_state.c +4 −0 Original line number Diff line number Diff line Loading @@ -386,6 +386,8 @@ static int nouveau_init_engine_ptrs(struct drm_device *dev) engine->pm.temp_get = nv84_temp_get; else engine->pm.temp_get = nv40_temp_get; engine->pm.fanspeed_get = nv50_pm_fanspeed_get; engine->pm.fanspeed_set = nv50_pm_fanspeed_set; engine->vram.init = nv50_vram_init; engine->vram.takedown = nv50_vram_fini; engine->vram.get = nv50_vram_new; Loading Loading @@ -441,6 +443,8 @@ static int nouveau_init_engine_ptrs(struct drm_device *dev) engine->pm.clocks_get = nvc0_pm_clocks_get; engine->pm.voltage_get = nouveau_voltage_gpio_get; engine->pm.voltage_set = nouveau_voltage_gpio_set; engine->pm.fanspeed_get = nv50_pm_fanspeed_get; engine->pm.fanspeed_set = nv50_pm_fanspeed_set; break; case 0xd0: engine->instmem.init = nvc0_instmem_init; Loading
drivers/gpu/drm/nouveau/nv50_pm.c +74 −0 Original line number Diff line number Diff line Loading @@ -144,3 +144,77 @@ nv50_pm_clock_set(struct drm_device *dev, void *pre_state) kfree(state); } struct pwm_info { int id; int invert; u8 tag; u32 ctrl; int line; }; static int nv50_pm_fanspeed_pwm(struct drm_device *dev, struct pwm_info *pwm) { struct dcb_gpio_entry *gpio; gpio = nouveau_bios_gpio_entry(dev, 0x09); if (gpio) { pwm->tag = gpio->tag; pwm->id = (gpio->line == 9) ? 1 : 0; pwm->invert = gpio->state[0] & 1; pwm->ctrl = (gpio->line < 16) ? 0xe100 : 0xe28c; pwm->line = (gpio->line & 0xf); return 0; } return -ENOENT; } int nv50_pm_fanspeed_get(struct drm_device *dev) { struct drm_nouveau_private *dev_priv = dev->dev_private; struct nouveau_gpio_engine *pgpio = &dev_priv->engine.gpio; struct pwm_info pwm; int ret; ret = nv50_pm_fanspeed_pwm(dev, &pwm); if (ret) return ret; if (nv_rd32(dev, pwm.ctrl) & (0x00000001 << pwm.line)) { u32 divs = nv_rd32(dev, 0x00e114 + (pwm.id * 8)); u32 duty = nv_rd32(dev, 0x00e118 + (pwm.id * 8)); if (divs) { divs = max(divs, duty); if (pwm.invert) duty = divs - duty; return (duty * 100) / divs; } return 0; } return pgpio->get(dev, pwm.tag) * 100; } int nv50_pm_fanspeed_set(struct drm_device *dev, int percent) { struct pwm_info pwm; u32 divs, duty; int ret; ret = nv50_pm_fanspeed_pwm(dev, &pwm); if (ret) return ret; divs = nv_rd32(dev, 0x00e114 + (pwm.id * 8)); duty = ((divs * percent) + 99) / 100; if (pwm.invert) duty = divs - duty; nv_mask(dev, pwm.ctrl, 0x00010001 << pwm.line, 0x00000001 << pwm.line); nv_wr32(dev, 0x00e118 + (pwm.id * 8), 0x80000000 | duty); return 0; }