From mboxrd@z Thu Jan 1 00:00:00 1970 From: Hans de Goede Date: Wed, 12 Aug 2015 14:44:58 +0200 Subject: [U-Boot] [PATCH 3/3] sunxi: display: Add overscan correction In-Reply-To: <1439376340.8356.13.camel@hellion.org.uk> References: <1438787851-31814-1-git-send-email-hdegoede@redhat.com> <1438787851-31814-4-git-send-email-hdegoede@redhat.com> <1439376340.8356.13.camel@hellion.org.uk> Message-ID: <55CB3FCA.2030907@redhat.com> List-Id: MIME-Version: 1.0 Content-Type: text/plain; charset="us-ascii" Content-Transfer-Encoding: 7bit To: u-boot@lists.denx.de Hi, On 12-08-15 12:45, Ian Campbell wrote: > On Wed, 2015-08-05 at 17:17 +0200, Hans de Goede wrote: >> > > sunxi_display.fb_size = >> > > > (mode->xres * mode->yres * 4 + 0xfff) & ~0xfff; >> +> > overscan_offset = (overscan_y * mode->xres + overscan_x) * 4; >> +> > /* We want to keep the fb_base for simplefb page aligned, where as >> +> > * the sunxi dma engines will happily accept an unaligned address. */ >> +> > if (overscan_offset) >> +> > > sunxi_display.fb_size += 0x1000; > > Why plus 4K regardless of the magnitude of overscan_offset? What if it was > 0x1004? If overscan offset is 0x1004 then we make the simplefb start point to fb_base + 0x2000: sunxi_display.fb_addr = gd->fb_base sunxi_display.fb_addr += (overscan_offset + 0xfff) & ~0xfff And make the dma engine start at fb_base + 0xffc: fb_dma_addr = gd->fb_base fb_dma_addr += 0x1000 - (overscan_offset & 0xfff) Notice how we make the dma_engine start at less then 0x1000 offset of fb_base, so making fb_size 0x1000 larger is enough. Basically to page-align the start of the simplefb / sunxi_display.fb_addr we only need a single page, the rest we can get by offsetting sunxi_display.fb_addr from fb_base by a multiple of the page size. > Also, what's the link between fb_base's alignment and fb_size which is > implied by the comment? To align we need a page extra size as the dma-engine may start at an offset of up-to a page-size from gd->fb_base and the dma-engine will dma a full framebuffer size, including the black borders. > >> > > gd->fb_base = gd->bd->bi_dram[0].start + >> > > > gd->bd->bi_dram[0].size - sunxi_display.fb_size; >> > > sunxi_engines_init(); >> -> > sunxi_mode_set(mode, gd->fb_base - CONFIG_SYS_SDRAM_BASE); >> + >> +> > fb_dma_addr = gd->fb_base - CONFIG_SYS_SDRAM_BASE; >> +> > sunxi_display.fb_addr = gd->fb_base; >> +> > if (overscan_offset) { >> +> > > fb_dma_addr += 0x1000 - (overscan_offset & 0xfff); >> +> > > sunxi_display.fb_addr += (overscan_offset + 0xfff) & ~0xfff; >> +> > > memset((void *)gd->fb_base, 0, sunxi_display.fb_size); >> +> > > flush_cache(gd->fb_base, sunxi_display.fb_size); >> +> > } > > Hrm, I think this starts to answer, but I'm still not sure I follow, sorry. Correct this is the answer, sorry for the tricky maths, this is the best solution without wasting a ton of memory with large overscans. I hope the above explanation helps, if not keep asking. >> + sunxi_mode_set(mode, fb_dma_addr); >> >> /* >> > > * These are the only members of this structure that are used. All the >> > > * others are driver specific. There is nothing to decribe pitch or > > > Pre-existing typo "describe". Will fix, Regards, Hans