> -----Original Message----- > From: Ville Syrjala <ville.syrjala@xxxxxxxxxxxxxxx> > Sent: Thursday, April 30, 2020 12:25 AM > To: intel-gfx@xxxxxxxxxxxxxxxxxxxxx > Cc: Gupta, Anshuman <anshuman.gupta@xxxxxxxxx>; Shankar, Uma > <uma.shankar@xxxxxxxxx> > Subject: [PATCH 3/3] drm/i915: Streamline the artihmetic > > From: Ville Syrjälä <ville.syrjala@xxxxxxxxxxxxxxx> > > All these ROUNDIND_FACTORs and whatnot are making this thing hard to read. Get Nit pick: Typo in ROUNDING > rid of them. And let's massage some of the fractions to give us less questionable > intermediate results and perhaps less divisions. > > Also looks like a good helping of 64bit math stuff is needed to avoid some of > overflows present in the current code. There might still be a few overflows, namely > when calculating link_clks_available/samples_room (would require a huge hblank > though), and potentially when calculating hblank_rise (not sure how large > link_clks_active can get). > > It looks like we're still not calculating exactly what the spec says since we truncate > tu_data and tu_line early. But I'm too lazy to figure out if we could avoid that. > > Cc: Anshuman Gupta <anshuman.gupta@xxxxxxxxx> > Cc: Uma Shankar <uma.shankar@xxxxxxxxx> > Signed-off-by: Ville Syrjälä <ville.syrjala@xxxxxxxxxxxxxxx> > --- > drivers/gpu/drm/i915/display/intel_audio.c | 54 ++++++++-------------- > 1 file changed, 19 insertions(+), 35 deletions(-) > > diff --git a/drivers/gpu/drm/i915/display/intel_audio.c > b/drivers/gpu/drm/i915/display/intel_audio.c > index 00f7a3cf9a04..05cab508c626 100644 > --- a/drivers/gpu/drm/i915/display/intel_audio.c > +++ b/drivers/gpu/drm/i915/display/intel_audio.c > @@ -517,16 +517,16 @@ static void hsw_audio_codec_disable(struct intel_encoder > *encoder, > /* Add a factor to take care of rounding and truncations */ #define > ROUNDING_FACTOR 10000 We should drop this declaration as well, as its of no use now. Overall this looks much better for sure, thanks Ville. Reviewed-by: Uma Shankar <uma.shankar@xxxxxxxxx> > -static unsigned int get_hblank_early_enable_config(struct intel_encoder *encoder, > - const struct intel_crtc_state > *crtc_state) > +static unsigned int calc_hblank_early_prog(struct intel_encoder *encoder, > + const struct intel_crtc_state *crtc_state) > { > struct drm_i915_private *i915 = to_i915(encoder->base.dev); > unsigned int link_clks_available, link_clks_required; > unsigned int tu_data, tu_line, link_clks_active; > - unsigned int hblank_rise, hblank_early_prog; > unsigned int h_active, h_total, hblank_delta, pixel_clk; > unsigned int fec_coeff, cdclk, vdsc_bpp; > unsigned int link_clk, lanes; > + unsigned int hblank_rise; > > h_active = crtc_state->hw.adjusted_mode.crtc_hdisplay; > h_total = crtc_state->hw.adjusted_mode.crtc_htotal; > @@ -542,44 +542,33 @@ static unsigned int get_hblank_early_enable_config(struct > intel_encoder *encoder > "lanes = %u vdsc_bpp = %u cdclk = %u\n", > h_active, link_clk, lanes, vdsc_bpp, cdclk); > > - if (WARN_ON(!link_clk || !lanes || !vdsc_bpp || !cdclk)) > + if (WARN_ON(!link_clk || !pixel_clk || !lanes || !vdsc_bpp || !cdclk)) > return 0; > > - link_clks_available = ((((h_total - h_active) * > - ((link_clk * ROUNDING_FACTOR) / > - pixel_clk)) / ROUNDING_FACTOR) - 28); > - link_clks_required = DIV_ROUND_UP(192000, (1000 * pixel_clk / h_total)) * > ((48 / > - lanes) + 2); > + link_clks_available = (h_total - h_active) * link_clk / pixel_clk - 28; > + link_clks_required = DIV_ROUND_UP(192000 * h_total, 1000 * pixel_clk) > +* (48 / lanes + 2); > > if (link_clks_available > link_clks_required) > hblank_delta = 32; > else > - hblank_delta = DIV_ROUND_UP(((((5 * ROUNDING_FACTOR) / > - link_clk) + ((5 * > - ROUNDING_FACTOR) / > - cdclk)) * pixel_clk), > - ROUNDING_FACTOR); > + hblank_delta = DIV64_U64_ROUND_UP(mul_u32_u32(5 * link_clk + > 5 * cdclk, pixel_clk), > + mul_u32_u32(link_clk, cdclk)); > > - tu_data = (pixel_clk * vdsc_bpp * 8) / ((link_clk * > - lanes * fec_coeff) / 1000000); > - tu_line = (((h_active * link_clk * fec_coeff) / > - 1000000) / (64 * pixel_clk)); > + tu_data = div64_u64(mul_u32_u32(pixel_clk * vdsc_bpp * 8, 1000000), > + mul_u32_u32(link_clk * lanes, fec_coeff)); > + tu_line = div64_u64(h_active * mul_u32_u32(link_clk, fec_coeff), > + mul_u32_u32(64 * pixel_clk, 1000000)); > link_clks_active = (tu_line - 1) * 64 + tu_data; > > - hblank_rise = ((link_clks_active + 6 * DIV_ROUND_UP(link_clks_active, > - 250) + 4) * ((pixel_clk * ROUNDING_FACTOR) / > - link_clk)) / ROUNDING_FACTOR; > + hblank_rise = (link_clks_active + 6 * DIV_ROUND_UP(link_clks_active, > +250) + 4) * pixel_clk / link_clk; > > - hblank_early_prog = h_active - hblank_rise + hblank_delta; > - > - return hblank_early_prog; > + return h_active - hblank_rise + hblank_delta; > } > > -static unsigned int get_sample_room_req_config(const struct intel_crtc_state > *crtc_state) > +static unsigned int calc_samples_room(const struct intel_crtc_state > +*crtc_state) > { > unsigned int h_active, h_total, pixel_clk; > unsigned int link_clk, lanes; > - unsigned int samples_room; > > h_active = crtc_state->hw.adjusted_mode.hdisplay; > h_total = crtc_state->hw.adjusted_mode.htotal; > @@ -587,12 +576,8 @@ static unsigned int get_sample_room_req_config(const > struct intel_crtc_state *cr > link_clk = crtc_state->port_clock; > lanes = crtc_state->lane_count; > > - samples_room = ((((h_total - h_active) * ((link_clk * > - ROUNDING_FACTOR) / pixel_clk)) / > - ROUNDING_FACTOR) - 12) / ((48 / > - lanes) + 2); > - > - return samples_room; > + return ((h_total - h_active) * link_clk - 12 * pixel_clk) / > + (pixel_clk * (48 / lanes + 2)); > } > > static void enable_audio_dsc_wa(struct intel_encoder *encoder, @@ -618,8 +603,7 > @@ static void enable_audio_dsc_wa(struct intel_encoder *encoder, > (crtc_state->hw.adjusted_mode.hdisplay >= 3840 && > crtc_state->hw.adjusted_mode.vdisplay >= 2160)) { > /* Get hblank early enable value required */ > - hblank_early_prog = get_hblank_early_enable_config(encoder, > - crtc_state); > + hblank_early_prog = calc_hblank_early_prog(encoder, crtc_state); > if (hblank_early_prog < 32) { > val &= ~HBLANK_START_COUNT_MASK(pipe); > val |= HBLANK_START_COUNT(pipe, > HBLANK_START_COUNT_32); @@ -635,7 +619,7 @@ static void > enable_audio_dsc_wa(struct intel_encoder *encoder, > } > > /* Get samples room value required */ > - samples_room = get_sample_room_req_config(crtc_state); > + samples_room = calc_samples_room(crtc_state); > if (samples_room < 3) { > val &= ~NUMBER_SAMPLES_PER_LINE_MASK(pipe); > val |= NUMBER_SAMPLES_PER_LINE(pipe, samples_room); > -- > 2.24.1 _______________________________________________ Intel-gfx mailing list Intel-gfx@xxxxxxxxxxxxxxxxxxxxx https://lists.freedesktop.org/mailman/listinfo/intel-gfx