我对
memset
和 Turbo C 中的大 for 循环有疑问。
当代码开始崩溃时,我正在 Virtual Box 上的 MS-DOS 6.22 上使用 Turbo C++ 3.00 编写基于模式 13h 的小型图形库。
我知道 Turbo C 确实已经过时了,但我想在类似 DOS 的系统上尝试旧式编码。
这是我的代码:
#include <stdlib.h>
#include <conio.h>
#include <stdio.h>
#include <string.h>
#include <dos.h>
int main(int argc, char *argv[]) {
int *buf;
unsigned int i;
_AH = 0x0;
_AL = 0x13;
geninterrupt(0x10);
buf = malloc(sizeof(int)*64000);
memset(buf,15,64000); //can't figure out why memset does not work properly...
for (i=0;i< (unsigned int)64000;i++){
buf[i] = 15; //trying to forcely set each byte to 0xf...
pokeb(0xA000,i,buf[i]); //outputting to VGA
}
getch();
free(buf);
return(0);
}
我想做的基本上就是用白色填充屏幕。
开始编码后,我注意到
memset
并未将堆数组的所有字节设置为 0xf。
所以我决定通过编写 for 循环来手动设置它们。
我运行了它,它的效果就像黄油一样。当我把字节戳到屏幕上时,程序就崩溃了,我不明白为什么......
有什么帮助吗?
PS:我对 C 还很陌生。
在 MS-DOS 中,内存按不超过 64K 的
segments
组织。
您的 64,000 个整数的缓冲区比这个还要大。
如果您使用
unsigned char
(单字节)而不是 int
或 unsigned int
(我似乎记得在 DOS/Turbo C++ 中是 16 位),那么它将适合单个“段”并且应该可以正常工作。
...当您存储要插入视频内存的字节时,您不需要整数提供的额外位宽。
#include <stdlib.h>
#include <conio.h>
#include <stdio.h>
#include <string.h>
#include <dos.h>
int main() {
unsigned char *buf;
unsigned int i;
_AH = 0x0;
_AL = 0x13;
geninterrupt(0x10);
buf = malloc(64000);
memset(buf, 15, 64000);
for (i=0; i < (unsigned int)64000; i++) {
pokeb(0xA000, i, buf[i]); //outputting to VGA
}
getch();
free(buf);
return(0);
}
正如 @Jabberwocky 所提到的,如果您不打算做任何其他事情,而是将这些值直接插入视频 RAM,您甚至可以完全忽略缓冲区:
int main() {
unsigned int i;
_AH = 0x0;
_AL = 0x13;
geninterrupt(0x10);
for (i=0; i < (unsigned int)64000; i++) {
pokeb(0xA000, i, 15); //outputting to VGA
}
getch();
return(0);
}