> -----Original Message----- > From: Tomi Valkeinen [mailto:tomi.valkeinen@xxxxxxxxx] > Sent: Friday, April 16, 2010 3:08 PM > To: Hiremath, Vaibhav > Cc: linux-omap@xxxxxxxxxxxxxxx > Subject: Re: [PATCH] OMAP: DSS2: GFX FIFO UNDERFLOW issue fixed > > On Mon, 2010-03-22 at 14:09 +0100, ext hvaibhav@xxxxxx wrote: > > From: Vaibhav Hiremath <hvaibhav@xxxxxx> > > > > In case of 720P with 90/270 degree rotation, the system reports > > GFX_FIFO_UNDERFLOW error which usually happens if DSS DMA is not able to > fill > > the FIFO as per requirement. > > > > In TRM (section 11.2.6.1.3), where is has been clearly mentioned that, > > > > "To improve the performance on 90 degree rotation, split the data access > on > > write side and not read side." > > > > That means, read should always happen on 0 degree and write should go to > > respective rotation view. > > > > With this patch my db test app (from > git://gitorious.org/linux-omap-dss2/omapfb-tests.git) shows a lot of > tearing when rotation != 0. I tested this on 3430SDP using the LCD. > [Hiremath, Vaibhav] I had tested it with the sample application which draws color bars to the frame-buffer, let me once again check with your (omapfb-test) application. Tomi, I am going out of station so will be able to do this on Tuesday. Thanks, Vaibhav > Tomi > > > > Signed-off-by: Vaibhav Hiremath <hvaibhav@xxxxxx> > > --- > > drivers/video/omap2/omapfb/omapfb-main.c | 85 +++++++++++++++++++------ > ---- > > 1 files changed, 56 insertions(+), 29 deletions(-) > > > > diff --git a/drivers/video/omap2/omapfb/omapfb-main.c > b/drivers/video/omap2/omapfb/omapfb-main.c > > index 4a76917..fea6b08 100644 > > --- a/drivers/video/omap2/omapfb/omapfb-main.c > > +++ b/drivers/video/omap2/omapfb/omapfb-main.c > > @@ -184,6 +184,11 @@ static unsigned omapfb_get_vrfb_offset(const struct > omapfb_info *ofbi, int rot) > > static u32 omapfb_get_region_rot_paddr(const struct omapfb_info *ofbi, > int rot) > > { > > if (ofbi->rotation_type == OMAP_DSS_ROT_VRFB) { > > + if (rot == FB_ROTATE_CW) > > + rot = FB_ROTATE_CCW; > > + else if (rot == FB_ROTATE_CCW) > > + rot = FB_ROTATE_CW; > > + > > return ofbi->region.vrfb.paddr[rot] > > + omapfb_get_vrfb_offset(ofbi, rot); > > } else { > > @@ -191,20 +196,32 @@ static u32 omapfb_get_region_rot_paddr(const struct > omapfb_info *ofbi, int rot) > > } > > } > > > > -static u32 omapfb_get_region_paddr(const struct omapfb_info *ofbi) > > +static u32 omapfb_get_region_paddr(struct omapfb_info *ofbi, int rot) > > { > > - if (ofbi->rotation_type == OMAP_DSS_ROT_VRFB) > > - return ofbi->region.vrfb.paddr[0]; > > - else > > + if (ofbi->rotation_type == OMAP_DSS_ROT_VRFB) { > > + if (rot == FB_ROTATE_CW) > > + rot = FB_ROTATE_CCW; > > + else if (rot == FB_ROTATE_CCW) > > + rot = FB_ROTATE_CW; > > + > > + return ofbi->region.vrfb.paddr[rot]; > > + } else { > > return ofbi->region.paddr; > > + } > > } > > > > -static void __iomem *omapfb_get_region_vaddr(const struct omapfb_info > *ofbi) > > +static void __iomem *omapfb_get_region_vaddr(struct omapfb_info *ofbi, > int rot) > > { > > - if (ofbi->rotation_type == OMAP_DSS_ROT_VRFB) > > - return ofbi->region.vrfb.vaddr[0]; > > - else > > + if (ofbi->rotation_type == OMAP_DSS_ROT_VRFB) { > > + if (rot == FB_ROTATE_CW) > > + rot = FB_ROTATE_CCW; > > + else if (rot == FB_ROTATE_CCW) > > + rot = FB_ROTATE_CW; > > + > > + return ofbi->region.vrfb.vaddr[rot]; > > + } else { > > return ofbi->region.vaddr; > > + } > > } > > > > static struct omapfb_colormode omapfb_colormodes[] = { > > @@ -503,7 +520,7 @@ static int setup_vrfb_rotation(struct fb_info *fbi) > > unsigned bytespp; > > bool yuv_mode; > > enum omap_color_mode mode; > > - int r; > > + int r, rotation = var->rotate; > > bool reconf; > > > > if (!rg->size || ofbi->rotation_type != OMAP_DSS_ROT_VRFB) > > @@ -511,6 +528,11 @@ static int setup_vrfb_rotation(struct fb_info *fbi) > > > > DBG("setup_vrfb_rotation\n"); > > > > + if (rotation == FB_ROTATE_CW) > > + rotation = FB_ROTATE_CCW; > > + else if (rotation == FB_ROTATE_CCW) > > + rotation = FB_ROTATE_CW; > > + > > r = fb_mode_to_dss_mode(var, &mode); > > if (r) > > return r; > > @@ -534,32 +556,35 @@ static int setup_vrfb_rotation(struct fb_info *fbi) > > vrfb->yres != var->yres_virtual) > > reconf = true; > > > > - if (vrfb->vaddr[0] && reconf) { > > + if (vrfb->vaddr[rotation] && reconf) { > > fbi->screen_base = NULL; > > fix->smem_start = 0; > > fix->smem_len = 0; > > - iounmap(vrfb->vaddr[0]); > > - vrfb->vaddr[0] = NULL; > > + iounmap(vrfb->vaddr[rotation]); > > + vrfb->vaddr[rotation] = NULL; > > DBG("setup_vrfb_rotation: reset fb\n"); > > } > > > > - if (vrfb->vaddr[0]) > > + if (vrfb->vaddr[rotation]) > > return 0; > > > > - omap_vrfb_setup(&rg->vrfb, rg->paddr, > > - var->xres_virtual, > > - var->yres_virtual, > > - bytespp, yuv_mode); > > + if (rotation == FB_ROTATE_CW || rotation == FB_ROTATE_CCW) > > + omap_vrfb_setup(&rg->vrfb, rg->paddr, > > + var->yres_virtual, var->xres_virtual, > > + bytespp, yuv_mode); > > + else > > + omap_vrfb_setup(&rg->vrfb, rg->paddr, > > + var->xres_virtual, var->yres_virtual, > > + bytespp, yuv_mode); > > > > - /* Now one can ioremap the 0 angle view */ > > - r = omap_vrfb_map_angle(vrfb, var->yres_virtual, 0); > > + /* Now one can ioremap the rotation angle view */ > > + r = omap_vrfb_map_angle(vrfb, var->yres_virtual, rotation); > > if (r) > > return r; > > - > > /* used by open/write in fbmem.c */ > > - fbi->screen_base = ofbi->region.vrfb.vaddr[0]; > > + fbi->screen_base = ofbi->region.vrfb.vaddr[rotation]; > > > > - fix->smem_start = ofbi->region.vrfb.paddr[0]; > > + fix->smem_start = ofbi->region.vrfb.paddr[rotation]; > > > > switch (var->nonstd) { > > case OMAPFB_COLOR_YUV422: > > @@ -603,7 +628,8 @@ void set_fb_fix(struct fb_info *fbi) > > DBG("set_fb_fix\n"); > > > > /* used by open/write in fbmem.c */ > > - fbi->screen_base = (char __iomem *)omapfb_get_region_vaddr(ofbi); > > + fbi->screen_base = (char __iomem *)omapfb_get_region_vaddr(ofbi, > > + var->rotate); > > > > /* used by mmap in fbmem.c */ > > if (ofbi->rotation_type == OMAP_DSS_ROT_VRFB) { > > @@ -626,7 +652,7 @@ void set_fb_fix(struct fb_info *fbi) > > fix->smem_len = rg->size; > > } > > > > - fix->smem_start = omapfb_get_region_paddr(ofbi); > > + fix->smem_start = omapfb_get_region_paddr(ofbi, var->rotate); > > > > fix->type = FB_TYPE_PACKED_PIXELS; > > > > @@ -862,15 +888,15 @@ static int omapfb_setup_overlay(struct fb_info *fbi, > struct omap_overlay *ovl, > > > > > > if (ofbi->rotation_type == OMAP_DSS_ROT_VRFB) { > > - data_start_p = omapfb_get_region_rot_paddr(ofbi, rotation); > > + data_start_p = omapfb_get_region_rot_paddr(ofbi, 0); > > data_start_v = NULL; > > } else { > > - data_start_p = omapfb_get_region_paddr(ofbi); > > - data_start_v = omapfb_get_region_vaddr(ofbi); > > + data_start_p = omapfb_get_region_paddr(ofbi, 0); > > + data_start_v = omapfb_get_region_vaddr(ofbi, 0); > > } > > > > if (ofbi->rotation_type == OMAP_DSS_ROT_VRFB) > > - offset = calc_rotation_offset_vrfb(var, fix, rotation); > > + offset = calc_rotation_offset_vrfb(var, fix, 0); > > else > > offset = calc_rotation_offset_dma(var, fix, rotation); > > > > @@ -1078,6 +1104,7 @@ static struct vm_operations_struct mmap_user_ops = { > > static int omapfb_mmap(struct fb_info *fbi, struct vm_area_struct *vma) > > { > > struct omapfb_info *ofbi = FB2OFB(fbi); > > + struct fb_var_screeninfo *var = &fbi->var; > > struct fb_fix_screeninfo *fix = &fbi->fix; > > unsigned long off; > > unsigned long start; > > @@ -1089,7 +1116,7 @@ static int omapfb_mmap(struct fb_info *fbi, struct > vm_area_struct *vma) > > return -EINVAL; > > off = vma->vm_pgoff << PAGE_SHIFT; > > > > - start = omapfb_get_region_paddr(ofbi); > > + start = omapfb_get_region_paddr(ofbi, var->rotate); > > len = fix->smem_len; > > if (off >= len) > > return -EINVAL; > -- To unsubscribe from this list: send the line "unsubscribe linux-omap" in the body of a message to majordomo@xxxxxxxxxxxxxxx More majordomo info at http://vger.kernel.org/majordomo-info.html