这门课是一个与麻省理工学院(MIT)的操作系统课程,学习这门课需要配置linux系统,在window有两种方式,一种是配置在wsl上的linux子系统(只有命令行,还需要自行配置图形化界面),另外一种是在VMware模拟器上运行linux(推荐,不需要自己搞图形化界面,且配置相对简单)
- ps:如果使用wsl,时间充裕可以先学一下vim编辑器(在命令行下编辑文件的软件),这个博客是学习记录,也算是给只学了c语言语法的同学一些学习提示(像一开始的我其他基础没有就头铁进来挨打,踩了一个又一个坑)
这门课使用到的Linux命令()
使用重点:看清楚你当前在哪个文件
- 刚登入一般是root用户,@localhost指本地主机(不必深究意义),“~“表示当前所在的路径是当前用户的主目录,在这里省略了“/root”。”#”:表示当前用户是以超级用户身份登录,即具有管理员权限。
上图是一个例子,现在说明一下命令意思
- “cd"用于进入某个目录(”…“表示上一层目录,”."表示当前目录)
- 往下,“su”是登入命令“wuye”是用户名(这个是我自己创建的),在这里我切换了用户,可以看到权限符号变为$
- “ls” 展示当前目录的所有目录(或文件),下面两行是当前目录下我的所有文件。
- "cd home"我切换到了当前目录下的home目录,该目录一般存放用户目录
- 再次使用"ls"可以看到"wuye"用户目录
- 使用"cd wuye"目录后,可以看到"$“前面的路径被”~"省略了,就是在用户目录下
- 使用ls后可以看到xv6-labs-2021这个目录,这个是这门课程的程序目录,在安装完Linux,在自己创建的目录下按照课程网站的教程,使用"git clone git://g.csail.mit.edu/xv6-labs-2022"来下载。下面的环境就可以按照课程网站的来进行了。
- tip:对于输入文件或目录名,如"cd xv6-labs-2022",可以打出"cd xv6"后使用Tab键来补全,只要输入的前缀其他文件没有,都可以使用Tab来补全。按两下后显示所有有该前缀的文件或目录。这个技巧也可以用于补全命令。
- “rm -rf 文件名” //rm为命令名称,-rf是参数,这条命令用于删除文件,所有不要随便使用。
ls()命令的一些参数
“-l”:以长格式显示文件信息,包括文件权限、所有者、大小、创建日期等详细信息。
“-a”:显示所有文件,包括隐藏文件。
“-h”:以人可读的方式显示文件大小,例如 1K、2M、3G 等。
“-t”:按照修改时间排序,最近修改的文件在前面。
“-r”:反向排序,即逆序输出文件列表。
“-S”:按照文件大小排序,文件大小大的在前面。
“-d”:只显示目录本身,不显示目录下的文件列表。
关于这门课
我这里的用到是2022年的课程https://pdos.csail.mit.edu/6.828/2022/schedule.html(这门课程很完善,每年的Lab差不多好像)
一般的路线是:看完LEC1和preparation所显示的教材连接,Homework的连接是向教授提出问题的(没使用过,应该是MIT本校学生用到),然后Assignment的Lab就是主要的作业。我一般是边看视频边看教材,看完后再做Lab。刚学会很累,熬过去有个清晰的认识就舒服了。
Vim使用技巧
- vim是Linux自带的文本编辑器
“vim copy.c"在当前目录创建文件,(copy.c是想要创建的文件,没有后缀默认为创建,这里的.c就是c语言文件),然后会进入该文件当中,输入”:“来输入命令,”:“表示输入命令模式”!q"是退出vim编辑器
esc退出编辑模式, : wq保存;%d清除当前文件内容
"ctrl+c"强制退出程序
无格式粘贴,命令模式下直接“:set paste”(可以用来复制你自己写的代码,就不会有格式问题了)
ps:如果提示没有vim就去搜索如何下载。
Ctrl+z 用于暂停 Vim 编辑器,将其放到后台运行,同时返回到终端命令行界面。
C标准库的一些函数
一. void *memmove(void *dest, const void *src, size_t n);
dest:目标内存块的起始地址,即要将源内存块的内容复制到哪里。
src:源内存块的起始地址,即要从哪里开始复制内容。
n:要复制的字节数,即复制多少个字节的内容。
memmove()函数与memcpy()函数类似,不同之处在于它可以处理源内存块和目标内存块重叠的情况。这意味着,如果要将一段内存块复制到它自身的某个位置,memmove()函数也能正确地处理这种情况,而不会出现错误的结果。
memmove()函数会从源内存块中复制n个字节的内容到目标内存块中,如果目标内存块和源内存块有重叠的部分,memmove()函数会保证复制的结果是正确的。这个函数返回指向目标内存块起始地址的指针。
二.void *memset(void *ptr, int value, size_t num);
_Dst:为数组名,也可以是指向某一内存空间的指针
_v:为要填充的值
_Size:为要填充的字节数
做Lab1前的一些准备以及本人的代码实现
这门课程的Lab需要你编写一些系统命令的文件,第一个Lab可以酌情参考一下别人的做法,先搞清楚要干什么.第一个Lab编写的.c文件要放在"xv6-labs-2022/user"里面
prime:
我这里运行会有个奇怪的问题,$符号会随机插入到输出里,不知道什么原因,但不影响结果
prime
prime 2
prime 3
prime 5
prime 7
prime 11
prime 13
prime 17
prime 19
prime 23
prime 29
prime 31
代码:
#include <kernel/types.h>
#include <user/user.h>
void sieve(int *p1){
int p2[2];
int buffer;
if(pipe(p2)<0){
printf("pipe error");
exit(1);
}
if(fork()==0){
while(read(p2[0],&buffer,sizeof(buffer))){
printf("prime %d\n",buffer);
}
close(p2[0]);
exit(0);
}else{
while(read(p1[0],&buffer,sizeof(buffer))){
int judge=0;
for(int i=2;i<buffer;i++){
if(buffer%i==0&&i!=buffer){
judge=1;
break;
}
}
if(judge==0){
write(p2[1],&buffer,sizeof(buffer));
}
}
close(p1[0]);
close(p2[1]);
exit(0);
}
}
int main(){
int p1[2];
if(pipe(p1)<0){
printf("pipe error");
exit(1);
}
if(fork()==0){
sieve(p1);
}
else for(int i=2;i<=35;i++){
write(p1[1],&i,sizeof(i));
}
close(p1[1]);
exit(0);
}
find:
前置的一些知识:stat.h //文件大小,类型,修改时间等信息;open()系统调用函数;在你写的find函数里面的主函数int main(int argv,char* argv[]):如命令$ find . b,其中“ . ”是第一个参数,”b”为第二个参数
#include <user/user.h>
#include <kernel/fs.h>
#include <kernel/stat.h>
#include <kernel/fcntl.h>
char* fmt_name(char* path){
static char buff[DIRSIZ+1];
char *p;
for(p=path+strlen(path);p>=path&&*p!='/';p--);
p++;
memmove(buff,p,strlen(p)+1);
return buff;
}
void fcom(char* path,char* name){
if(strcmp(fmt_name(path),name)==0){
printf("%s\n",path);
}
}
void find(char* path,char* name){
int fd;
struct stat st;
struct dirent de;
char buff[512];
char* p;
if((fd=open(path,O_RDONLY))<0){
fprintf(2,"find:cannot open %s error\n",path);
return;
}
if(fstat(fd,&st)<0){
fprintf(2,"find:cannot fstat %s error\n",path);
close(fd);
return;
}
switch(st.type){
case T_DIR:
if(strlen(path)+1+DIRSIZ+1>sizeof buff){
printf("find:the path is too long\n");
break;
}
strcpy(buff,path);
p=buff+strlen(buff);
*p++='/';
while(read(fd,&de,sizeof(de))==sizeof(de)){
if(de.inum==0||de.inum==1||strcmp(de.name,".")==0||strcmp(de.name,"..")==0) continue;
memmove(p,de.name,strlen(de.name));
p[strlen(de.name)]=0;
find(buff,name);
}
break;
case T_FILE:
fcom(path,name);
break;
case T_DEVICE:
break;
}
close(fd);
}
int main(int argc,char *argv[]){
if(argc<3){
printf("find:find <path> <fileName>\n");
exit(0);
}
find(argv[1],argv[2]);
exit(0);
}
main(int argc,char *argv[]){
if(argc<3){
printf("find:find <path> <fileName>\n");
exit(0);
}
find(argv[1],argv[2]);
exit(0);
}
先写这么多了,刚开始由于其他课程占用时间,抽空搞了一周多才学到这里,剩下的看时间安排吧,毕竟才大一,学这门课有点早,没有一些知识啃不动。第一次写(水)博客,将就看一下吧。