操作系统实践报告_第1页
操作系统实践报告_第2页
操作系统实践报告_第3页
操作系统实践报告_第4页
操作系统实践报告_第5页
已阅读5页,还剩38页未读 继续免费阅读

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

1、精选优质文档-倾情为你奉上精选优质文档-倾情为你奉上专心-专注-专业专心-专注-专业精选优质文档-倾情为你奉上专心-专注-专业操作系统实践报告多进程题目sh1.c: 实现shell程序,要求具备如下功能支持命令参数$ echo arg1 arg2 arg3$ ls /bin /usr/bin /home实现内置命令cd、pwd、exit$ cd /bin$ pwd/bin思路:说明:首先设置一个死循环模仿shell终端,读取用户的输入,并且根据空格将输入拆分成字符串数组,然后调用excute这个子函数进行处理。echo根据数组第一个元素来判断命令是什么,判断出是ehco后,fork一个新的进程

2、,将其后的内容一个个输出出来,并且父进程等待子进程退出后再执行,确保输出在屏幕上时不被打断。ls读取用户输入并且根据拆分的数组判断出是ls命令后,fork一个新的进程,调用execlp函数将/bin/ls下的ls程序装入子进程并将拆分的数组参数部分传递给ls即可,同样的,父进程等待子进程退出,确保输出在屏幕上不被打断。cd同样是根据输入并拆分成数组后判断出是cd命令后,fork一个新的进程,然后调用chdir并将拆分数组的参数部分传递给chdir作为实参即可。pwd同样是根据输入并拆分成数组后判断出是pwd命令后,fork一个新的进程,然后调用system(pwd)即可,此命令也可以用来验证上

3、面的cd命令是否正确执行。exit根据用户输入逼格拆分的数组判断出是exit命令后,excute子函数返回-1,在循环中检测excute的返回值,如果是-1则直接return,退出模仿的shell终端。sh2.c: 实现shell程序,要求在第1版的基础上,添加如下功能实现文件重定向$ echo hello log$ cat logHello思路: 接sh1.c的描述,若判断出是echo命令后,要再次判断拆分的字符串数组中有无“”出现,如果 有,则把“”之前、echo之后的内容作为输出,把“”之后到“”之后的第一个空白字符作为文件名,fopen创建文件并fwrite将输出内容输出到该文件中,并

4、关闭文件。sh1.c和sh2.c的源代码:#include #include #include #include #include #include #include #define LEN 256#define WIDTH 256#define HEIGHT 10void split(char source,char destHEIGHTWIDTH)char *p;p=strsep(&source, );int i=0;for(i=0;pi!=0;i+)dest0i=pi;dest0i=0;int j=1;while(p)p=strsep(&source, );if(p)for(i=0;pi

5、!=0;i+)destji=pi;destji=0;j+;int execute(char commHEIGHTWIDTH)if(strcmp(comm0,echo)=0)int pid=fork();if(pid=0)int i=0;int is=0;for(i=1;commi0!=0;i+)if(commi0=)is=1;break;if(is=1)puts(commi+1);FILE *fp=fopen(commi+1,w+);int j=0;for(j=1;j);gets(command);split(command,splitArray);int i=0;if(-1=execute(

6、splitArray)return 0;sh3.c: 实现shell程序,要求在第2版的基础上,添加如下功能实现管道$ cat /etc/passwd | wc -l实现管道和文件重定向$ cat input.txt321321$ cat output.txt$ cat output.txt123思路:首先读取用户输入,以“|”为分隔符将输入分割成字符串数组,然后在一个while循环中依次执行下面的动作:代码中通过pipe()函数来创建管道,创建之后父进程和子进程一个只能向管道写内容,一个只能向管道读内容。然后利用dup()函数来把进程的输入流或者输出流重定向到管道里,这样就能实现管道的操作。

7、实现的时候注意可以使用多个“|”来迭代进行管道操作,需要使用一个循环来处理。用system执行每一条命令,同时还要注意最后一个操作的输出流是标准输出(即屏幕),不需要重定向到管道里,需要特殊处理一下。源代码:#include #include #include #include #include #include #include #define LEN 256#define WIDTH 256#define HEIGHT 10void split(char source,char destHEIGHTWIDTH)char *p;p=strsep(&source,|);int i=0;for(

8、i=0;pi!=0;i+)dest0i=pi;dest0i=0;int j=1;while(p)p=strsep(&source,|);if(p)for(i=0;pi!=0;i+)destji=pi;destji=0;j+;main()char commandLEN;char splitArrayHEIGHTWIDTH=0;printf(%s,);gets(command); split(command,splitArray); int i=0; for(i=0;splitArrayi0!=0;i+) puts(splitArrayi); int p2; pipe(p); int j=0; f

9、or(j=0;splitArrayj+10!=0;j+) if (fork() = 0) / Child process close(0); close(p0) close(p1); dup(p0); system(splitArrayj); else /Parent process close(1); close(p0) close(p1); dup(p1); system(splitArrayj+1); 多线程题目pi1.c: 使用2个线程根据莱布尼兹级数计算PI莱布尼兹级数公式: 1 - 1/3 + 1/5 - 1/7 + 1/9 - . = PI/4主线程创建1个辅助线程主线程计算级数

10、的前半部分辅助线程计算级数的后半部分主线程等待辅助线程运行結束后,将前半部分和后半部分相加思路:计算公式前1000项,主线程计算前5000项,子线程计算后5000项,主进程等待子进程结束,通过pthread_join(sub,(void *)&result);的result参数获取子进程计算结果再相加即可。源代码:#include#include#include#include#define LEN 10000 struct result float sum;void *subThread() int i; float j; struct result *result; float sum1=

11、0,sum2=0,sum=0; for(i=LEN/2+1;isum=sum; return result;int main() int i; float j; float sum1=0,sum2=0,sum=0; for(i=1;isum; printf(%fn,sum); return 0; pi2.c: 使用N个线程根据莱布尼兹级数计算PI与上一题类似,但本题更加通用化,能适应N个核心,需要使用线程参数来实现主线程创建N个辅助线程每个辅助线程计算一部分任务,并将结果返回主线程等待N个辅助线程运行结束,将所有辅助线程的结果累加思路:设计算公式前1000项,读取用户输入的线程数目N,通过pt

12、hread_create(&workersi-1,NULL,compute,myparam);产生N个线程,并且通过myparam设置每一个线程计算的起始项和终止项,通过pthread_join(workersj,(void *)&myresult);等待每个线程结束并通过result获取结果,将结果相加即可。源代码:#include#include#include#include#define LEN 10000#define MAX_WORKERS 100struct param int start; int end;struct result float sum;void *comput

13、e(void *arg) int i; float j; struct param *myparam; myparam=(struct param *)arg; int start=myparam-start; int end=myparam-end; struct result *myresult; float sum1=0,sum2=0,sum3=0; for(i=start;isum=sum2-sum1; return myresult;int main() int thread_num=1; struct param myparamsMAX_WORKERS+1; pthread_t w

14、orkersMAX_WORKERS; printf(please input thread number:); scanf(%d,&thread_num); int i; myparams0.start=0; myparams0.end=0; for(i=1;istart=myparamsi-1.end+1; myparam-end=myparamsi.start+(LEN/thread_num)-1; pthread_create(&workersi-1,NULL,compute,myparam); myparamsthread_num.start=myparamsthread_num-1.

15、end+1; myparamsthread_num.end=LEN; pthread_create(&workersthread_num-1,NULL,compute,&myparamsthread_num); int j; float sum=0; for(j=0;jsum; free(myresult); printf(%fn,sum); return 0;sort.c: 多线程排序主线程创建一个辅助线程主线程使用选择排序算法对数组的前半部分排序辅助线程使用选择排序算法对数组的后半部分排序主线程等待辅助线程运行結束后,使用归并排序算法归并数组的前半部分和后半部分思路:主线程排序数组的前半部

16、分,辅助线程排序后半部分,pthread_create(&worker_id,NULL,&sort,&pa);中pa传递的是数组的首地址,主线程等辅助线程结束后,再调用merge将数组合并为有序。源代码:#include#include#include#include#define LEN 10int arrayLEN=0,3,8,6,2,9,5,4,1,7;struct param int *arr;void *sort(void *arg) struct param *mypa; mypa=(struct param *)arg; int i=0; int j=0; int min=0;

17、int temp=0; for(i=LEN/2;iLEN-1;i+) min=i; for(j=i;jarrminmypa-arrj)min=j; temp=mypa-arrmin; mypa-arrmin=mypa-arri; mypa-arri=temp; void merge() int i=0; int aLEN/2; int bLEN/2; for(i=0;iLEN/2;i+) ai=arrayi; bi=arrayi+LEN/2; /* for(i=0;iLEN/2;i+) printf(%dn,ai); */ int tm=0; int ti=0,tj=0; while(tiLE

18、N/2&tjLEN/2) if(atibtj) arraytm=ati; ti+; else arraytm=btj; tj+; tm+; int main() struct param pa; pa.arr=array; int ti=0,tj=0,tmin=0; for(ti=0;tiLEN/2-1;ti+) tmin=ti; for(tj=ti;tjarraytj)tmin=tj; int temp=arraytmin; arraytmin=arrayti; arrayti=temp; pthread_t worker_id; pthread_create(&worker_id,NULL

19、,&sort,&pa); pthread_join(worker_id,NULL); merge(); int i=0; for(i=0;iLEN;i+) printf(%dn,arrayi); pc1.c: 使用条件变量解决生产者、计算者、消费者问题系统中有3个线程:生产者、计算者、消费者系统中有2个容量为4的缓冲区:buffer1、buffer2生产者生产a、b、c、d、e、f、g、h八个字符,放入到buffer1计算者从buffer1取出字符,将小写字符转换为大写字符,放入到buffer2消费者从buffer2取出字符,将其打印到屏幕上思路:类似于生产者和消费者,在问题中,生产者、计算者

20、相对应buffer1是生产者、消费者,二者互斥的进入buffer1,并且当buffer1满时,生产者等待,当buffer1空时,且计算值要从中取数据时,计算者等待。同理,计算者、消费者相对应buffer2是生产者和消费者,二者互斥的进入buffer2,当buffer2满时,且计算者要向其中放入数据时,计算者应等待,当buffer2空时,消费者应等待。源代码:#include #include #define CAPACITY 4int buffer1CAPACITY;int buffer2CAPACITY;int in1;int out1;int in2;int out2;int buffer

21、2_is_empty() return in2 = out2;int buffer2_is_full() return (in2 + 1) % CAPACITY = out2;int buffer1_is_empty() return in1 = out1;int buffer1_is_full() return (in1 + 1) % CAPACITY = out1;int get_item() int item; item = buffer2out2; out2 = (out2 + 1) % CAPACITY; return item;void put_item(int item) buf

22、fer1in1 = item; in1 = (in1 + 1) % CAPACITY;int cal_get_item() int item; item = buffer1out1; out1 = (out1 + 1) % CAPACITY; return item;void cal_put_item(int item) buffer2in2 = item; in2 = (in2 + 1) % CAPACITY;pthread_mutex_t mutex1;pthread_cond_t wait_empty_buffer1;pthread_cond_t wait_full_buffer1;pt

23、hread_mutex_t mutex2;pthread_cond_t wait_empty_buffer2;pthread_cond_t wait_full_buffer2;#define ITEM_COUNT (CAPACITY * 2)void *consume(void *arg) int i; int item; for (i = 0; i ITEM_COUNT; i+) pthread_mutex_lock(&mutex2); while (buffer2_is_empty() pthread_cond_wait( &wait_full_buffer2, &mutex2); ite

24、m = get_item(); printf( consume item: %cn, item); sleep(1); pthread_cond_signal(&wait_empty_buffer2); pthread_mutex_unlock(&mutex2); return NULL;void *calculate(void *arg) int i; int item; for (i = 0; i ITEM_COUNT; i+) pthread_mutex_lock(&mutex1); while (buffer1_is_empty() pthread_cond_wait( &wait_f

25、ull_buffer1, &mutex1); item = cal_get_item(); item+=A-a; pthread_cond_signal(&wait_empty_buffer1); pthread_mutex_unlock(&mutex1); pthread_mutex_lock(&mutex2); while (buffer2_is_full() pthread_cond_wait(&wait_empty_buffer2, &mutex2); cal_put_item(item); pthread_cond_signal(&wait_full_buffer2); pthrea

26、d_mutex_unlock(&mutex2); return NULL;void produce() int i; int item; for (i = 0; i ITEM_COUNT; i+) pthread_mutex_lock(&mutex1); while (buffer1_is_full() pthread_cond_wait(&wait_empty_buffer1, &mutex1); item = i + a; printf(produce item: %cn, item); put_item(item); sleep(1); pthread_cond_signal(&wait

27、_full_buffer1); pthread_mutex_unlock(&mutex1); int main() pthread_t consumer_tid; pthread_t calculate_tid; pthread_mutex_init(&mutex1, NULL); pthread_cond_init(&wait_empty_buffer1, NULL); pthread_cond_init(&wait_full_buffer1, NULL); pthread_mutex_init(&mutex2, NULL); pthread_cond_init(&wait_empty_bu

28、ffer2, NULL); pthread_cond_init(&wait_full_buffer2, NULL); pthread_create(&calculate_tid, NULL, calculate, NULL); pthread_create(&consumer_tid, NULL, consume, NULL); produce(); return 0;pc2.c: 使用信号量解决生产者、计算者、消费者问题功能和前面的实验相同,使用信号量解决思路:类似于pc1.c源代码:#include #include #include typedef struct int value; p

29、thread_mutex_t mutex; pthread_cond_t cond; sema_t;void sema_init(sema_t *sema, int value) sema-value = value; pthread_mutex_init(&sema-mutex, NULL); pthread_cond_init(&sema-cond, NULL);void sema_wait(sema_t *sema) pthread_mutex_lock(&sema-mutex); sema-value-; while (sema-value cond, &sema-mutex); pt

30、hread_mutex_unlock(&sema-mutex);void sema_signal(sema_t *sema) pthread_mutex_lock(&sema-mutex); +sema-value; pthread_cond_signal(&sema-cond); pthread_mutex_unlock(&sema-mutex);#define CAPACITY 4int buffer1CAPACITY;int buffer2CAPACITY;int in1;int out1;int in2;int out2;int buffer1_is_empty() return in

31、1 = out1;int buffer1_is_full() return (in1 + 1) % CAPACITY = out1;int buffer2_is_empty() return in2 = out2;int buffer2_is_full() return (in2 + 1) % CAPACITY = out2;int get_item() int item; item = buffer2out2; out2 = (out2 + 1) % CAPACITY; return item;void put_item(int item) buffer1in1 = item; in1 =

32、(in1 + 1) % CAPACITY;int cal_get_item() int item; item = buffer1out1; out1 = (out1 + 1) % CAPACITY; return item;void cal_put_item(int item) buffer2in2 = item; in2 = (in2 + 1) % CAPACITY;sema_t mutex_sema1;sema_t empty_buffer_sema1;sema_t full_buffer_sema1;sema_t mutex_sema2;sema_t empty_buffer_sema2

33、;sema_t full_buffer_sema2;#define ITEM_COUNT (CAPACITY * 2)void *consume(void *arg) int i; int item; for (i = 0; i ITEM_COUNT; i+) sema_wait(&full_buffer_sema2); sema_wait(&mutex_sema2); item = get_item(); sema_signal(&mutex_sema2); sema_signal(&empty_buffer_sema2); printf( consume item: %cn, item);

34、 return NULL;void *calculate() int i; int item; for (i = 0; i ITEM_COUNT; i+) sema_wait(&full_buffer_sema1); sema_wait(&mutex_sema1); item = cal_get_item(); item+=A-a; sema_signal(&mutex_sema1); sema_signal(&empty_buffer_sema1); sema_wait(&empty_buffer_sema2); sema_wait(&mutex_sema2); cal_put_item(i

35、tem); sema_signal(&mutex_sema2); sema_signal(&full_buffer_sema2); void produce() int i; int item; for (i = 0; i ITEM_COUNT; i+) sema_wait(&empty_buffer_sema1); sema_wait(&mutex_sema1); item = i + a; put_item(item); sema_signal(&mutex_sema1); sema_signal(&full_buffer_sema1); printf(produce item: %cn, item); int main() pthread_t consumer_tid; pthread_t calculate_tid; sema_init(&mutex_sema1, 1); sema_init(&empty_buffer_se

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论