}
 }
 
-void viafb_set_start_addr(void)
+void viafb_set_primary_address(u32 addr)
 {
-       unsigned long offset = 0, tmp = 0, size = 0;
-       unsigned long length;
-
-       DEBUG_MSG(KERN_INFO "viafb_set_start_addr!\n");
-       viafb_unlock_crt();
-       /* update starting address of IGA1 */
-       viafb_write_reg(CR0C, VIACR, 0x00);     /*initial starting address */
-       viafb_write_reg(CR0D, VIACR, 0x00);
-       viafb_write_reg(CR34, VIACR, 0x00);
-       viafb_write_reg_mask(CR48, VIACR, 0x00, 0x1F);
-
-       if (viafb_dual_fb) {
-               viaparinfo->iga_path = IGA1;
-               viaparinfo1->iga_path = IGA2;
-       }
-
-       if (viafb_SAMM_ON == 1) {
-               if (!viafb_dual_fb) {
-                       if (viafb_second_size)
-                               size = viafb_second_size * 1024 * 1024;
-                       else
-                               size = 8 * 1024 * 1024;
-               } else {
-
-                       size = viaparinfo1->memsize;
-               }
-               offset = viafb_second_offset;
-               DEBUG_MSG(KERN_INFO
-                         "viafb_second_size=%lx, second start_adddress=%lx\n",
-                         size, offset);
-       }
-       if (viafb_SAMM_ON == 1) {
-               offset = offset >> 3;
-
-               tmp = viafb_read_reg(VIACR, 0x62) & 0x01;
-               tmp |= (offset & 0x7F) << 1;
-               viafb_write_reg(CR62, VIACR, tmp);
-               viafb_write_reg(CR63, VIACR, ((offset & 0x7F80) >> 7));
-               viafb_write_reg(CR64, VIACR, ((offset & 0x7F8000) >> 15));
-               viafb_write_reg(CRA3, VIACR, ((offset & 0x3800000) >> 23));
-       } else {
-               /* update starting address */
-               viafb_write_reg(CR62, VIACR, 0x00);
-               viafb_write_reg(CR63, VIACR, 0x00);
-               viafb_write_reg(CR64, VIACR, 0x00);
-               viafb_write_reg(CRA3, VIACR, 0x00);
-       }
-
-       if (viafb_SAMM_ON == 1) {
-               if (viafb_accel) {
-                       if (!viafb_dual_fb)
-                               length = size - viaparinfo->fbmem_used;
-                       else
-                               length = size - viaparinfo1->fbmem_used;
-               } else
-                       length = size;
-               offset = (unsigned long)(void *)viafb_FB_MM +
-                       viafb_second_offset;
-               memset((void *)offset, 0, length);
-       }
+       DEBUG_MSG(KERN_DEBUG "viafb_set_primary_address(0x%08X)\n", addr);
+       viafb_write_reg(CR0D, VIACR, addr & 0xFF);
+       viafb_write_reg(CR0C, VIACR, (addr >> 8) & 0xFF);
+       viafb_write_reg(CR34, VIACR, (addr >> 16) & 0xFF);
+       viafb_write_reg_mask(CR48, VIACR, (addr >> 24) & 0x1F, 0x1F);
+}
 
-       viafb_lock_crt();
+void viafb_set_secondary_address(u32 addr)
+{
+       DEBUG_MSG(KERN_DEBUG "viafb_set_secondary_address(0x%08X)\n", addr);
+       /* secondary display supports only quadword aligned memory */
+       viafb_write_reg_mask(CR62, VIACR, (addr >> 2) & 0xFE, 0xFE);
+       viafb_write_reg(CR63, VIACR, (addr >> 10) & 0xFF);
+       viafb_write_reg(CR64, VIACR, (addr >> 18) & 0xFF);
+       viafb_write_reg_mask(CRA3, VIACR, (addr >> 26) & 0x07, 0x07);
 }
 
 void viafb_set_output_path(int device, int set_iga, int output_interface)
                outb(VPIT.SR[i - 1], VIASR + 1);
        }
 
-       viafb_set_start_addr();
+       viafb_set_primary_address(0);
+       viafb_set_secondary_address(viafb_SAMM_ON ? viafb_second_offset : 0);
        viafb_set_iga_path();
 
        /* Write CRTC */
 
            var->bits_per_pixel / 16;
 
        DEBUG_MSG(KERN_INFO "\nviafb_pan_display,offset =%d ", offset);
-
-       viafb_write_reg_mask(0x48, 0x3d4, ((offset >> 24) & 0x3), 0x3);
-       viafb_write_reg_mask(0x34, 0x3d4, ((offset >> 16) & 0xff), 0xff);
-       viafb_write_reg_mask(0x0c, 0x3d4, ((offset >> 8) & 0xff), 0xff);
-       viafb_write_reg_mask(0x0d, 0x3d4, (offset & 0xff), 0xff);
-
+       viafb_set_primary_address(offset);
        return 0;
 }
 
                viafb_SAMM_ON = active_dev.samm;
        viafb_primary_dev = active_dev.primary_dev;
 
-       viafb_set_start_addr();
+       viafb_set_primary_address(0);
+       viafb_set_secondary_address(viafb_SAMM_ON ? viafb_second_offset : 0);
        viafb_set_iga_path();
 }
 
                        if (viafb_SAMM_ON)
                                viafb_primary_dev = setting_info.primary_device;
 
-                       viafb_set_start_addr();
+                       viafb_set_primary_address(0);
+                       viafb_set_secondary_address(viafb_SAMM_ON ? viafb_second_offset : 0);
                        viafb_set_iga_path();
                }
                need_set_mode = 1;
                                viafb_second_offset;
                }
 
+               viaparinfo->iga_path = IGA1;
+               viaparinfo1->iga_path = IGA2;
                memcpy(viafbinfo1, viafbinfo, sizeof(struct fb_info));
                viafbinfo1->screen_base = viafbinfo->screen_base +
                        viafb_second_offset;