分三种情况C语言编程,吴进的256basic.h阅读笔记,请问scanline_copy子程序为什么要分三种情况考虑:(1)d...

吴进的256basic.h阅读笔记,请问scanline_copy子程序为什么要分三种情况考虑:(1)d

注释是我加上去的,不知我的理解是否正确,望给予赐教。

/***********************************************************************************************

// BIOS Video 换页或者 EMS换页函数

***********************************************************************************************/

void MySelectpage1(unsigned int page,char mode)

{

if (mode) // BIOS Video换页

{

if (lastVpage!=page)

selectpage(page); // 调用BIOS Video 换页函数

}

else // EMS换页

{

char n;

for (n = 0 ; n < 4 ; n++)

{

if (page*4+n!=lastEmap[n])

emap(page*4+n,n); // EMS逻辑页page*4+n与物理页n(n=0-4)建立映射

}

}

}

/***********************************************************************************************

// 单扫描线内容拷贝函数,desc与src均使用相对偏移,mode值意义如下:

// 值 意义

// -----------------------------

// 1 EMS屏幕 ---> VRAM屏幕

// -1 VRAM屏幕 ---> EMS屏幕

***********************************************************************************************/

void scanline_copy(unsigned long desc,unsigned long src,unsigned int length,char mode)

{

char pagetype1,pagetype2;

char far* descPoint;

char far* srcPoint;

unsigned int descpage=desc>>16, // 目标转换得到BIOS Video页

descoffset=desc&0xffff,// 目标相对VRAM页的偏移

srcpage=src>>16, // 源转换得到BIOS Video页

srcoffset=src&0xffff; // 源相对VRAM页的偏移

if (mode == 1) // EMS ---> VRAM 拷贝

{

descPoint=VPoint; // 目标基地址 = 0xa000

srcPoint=EmsPoint; // 源基地址 = EMS映射内存基地址

pagetype1=1;

pagetype2=0;

}

else // VRAM ---> EMS 拷贝

{

descPoint=EmsPoint; // 目标基地址 = EMS映射内存基地址

srcPoint=VPoint; // 源基地址 = 0xa000

pagetype1=0;

pagetype2=1;

}

/*----------------------------------------------------------------------------------------------------------------

// 如果 EMS ---> VRAM 拷贝:目标BIOS Video换页, 源EMS逻辑页换页

// 如果 VRAM ---> EMS 拷贝:目标EMS逻辑页换页, 源BIOS Video换页

------------------------------------------------------------------------------------------------------------------*/

MySelectpage1(descpage,pagetype1);

MySelectpage1(srcpage,pagetype2);

/*----------------------------------------------------------------------------------------------------------------

// 如果源复制区域及目标复制区域都未超过BIOS Video当前页(1页=65535Byte)

------------------------------------------------------------------------------------------------------------------*/

if ((long)srcoffset+length<=65536L && (long)descoffset+length<=65536L)

{

memcpy(descPoint+descoffset,srcPoint+srcoffset,length);

return;

}

/*----------------------------------------------------------------------------------------------

// 跨页处理(源复制区域或目标复制区域超过BIOS Video当前页,需作跨页处理)

-----------------------------------------------------------------------------------------------*/

else

{

unsigned int passed_length;

if (descoffset == srcoffset) // 如果目标位置与源位置相同

{

passed_length=65536L-descoffset;//当前页可Copy字节

memcpy(descPoint+descoffset,srcPoint+srcoffset,passed_length);

MySelectpage1(descpage+1,pagetype1); // 目标换至下页

MySelectpage1(srcpage+1,pagetype2); // 源换至下页

memcpy(descPoint,srcPoint,length-passed_length);// 复制跨页剩余内容

}

else // 目标与源位置不同

{

while (length>0)

{

if ((long)srcoffset+length<=65536L && (long)descoffset+length<=65536L)

{

memcpy(descPoint+descoffset,srcPoint+srcoffset,length);

break;

}

if (srcoffset>descoffset)// 如果源偏移位置大于目标偏移位置

{

passed_length=65536L-srcoffset;// 当前页Copy长度

memcpy(descPoint+descoffset,srcPoint+srcoffset,passed_length);

srcpage++; // 源页号+1

MySelectpage1(srcpage,pagetype2);// 源换至下页

descoffset+=passed_length;// 修正目标偏移

srcoffset=0; // 修正源偏移:由于源已经换页,因此偏移从0重新开始。

}

else // 源位置小于目标位置

{

passed_length=65536L-descoffset;// 当前页Copy长度

memcpy(descPoint+descoffset,srcPoint+srcoffset,passed_length);

descpage++; // 目标页号+1

MySelectpage1(descpage,pagetype1);// 目标换至下页

srcoffset+=passed_length;// 修正源偏移

descoffset=0; // 修正目标偏移:由于目标已经换页,因此偏移从0重新开始。

}

length-=passed_length; // 剩余待Copy长度

}

}

}

}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值