操作系统实验报告线程并发拷贝程序定稿版

操作系统实验报告线程并发拷贝程序HUA system office room 【HUA16H-TTMS2A-HUAS8Q8-HUAH1688】操作系统:线程(进程)并发拷贝程序附录一:程序代码#include<stdio.h>#include<sys/types.h>#include<sys/stat.h>#include<fcntl.h>#include<unistd.h>#include<pthread.h>#include<malloc.h>#define PSIZE 4096 /*管道文件的大小*/#define BSIZE 128 /*默认缓冲区的大小*/#define NOFILE 20 /*u_ofile3575表可分配的个数*/#define NFILE 20 /*file表可分配的个数*/#define NPIPE 20 /*pipecb3575可分配的个数*//*进程的u_file表*/int u_ofile3575[NOFILE];struct{char f_flag;/*读写标志,'w'表示写,'r'表示读*/int f_count;/*表示此表项的状态,=0表示此表项没被使用,可分配;=1表示此表项在被使用,不可再分配*/int f_inode;/*对应的pipecb3575表下标*/long f_offset;/*读写指针,当前已读或已写个数*/}file[NFILE];/*管道控制块*/struct{char *p_addr;/*管道文件基地址*/int p_size;/*管道文件大小,PSIZE*/int p_count;/*=2表示读写都在被进行,=1表示在被读或被写,=0表示管道没被使用,可分配*/}pipecb3575[NPIPE];char *pfile;/*管道的写入写出端*/int fd[2];/*锁机制,实现互斥*/pthread_mutex_t lock = PTHREAD_MUTEX_INITIALIZER;/*进程间通信,实现同步*/pthread_cond_t rflag = PTHREAD_COND_INITIALIZER;/*读信号量*/ pthread_cond_t wflag = PTHREAD_COND_INITIALIZER;/*写信号量*/ /*线程创建函数只能传一个参数,用结构体来封装所有参数*/struct arg_set{char *fname; /*文件名*/int f; /*传递fdp[]*/};/*u_ofile3575表初始化*/int u_ofile_init3575(){printf("init the u_ofile3575\n"); int i;for(i=0;i<NOFILE;i++)u_ofile3575[i] = -1;u_ofile3575[0]=0;u_ofile3575[1]=0;u_ofile3575[2]=0;return 0;}/*创建管道*/int pipe_simulate3575(int a[]){printf("start to create a pipe\n"); int i;for(i=0;i<NOFILE;i++){if(u_ofile3575[i]==-1){a[0] = i;/*读*/u_ofile3575[i] = 0;/*读端*/ break;}}for(i;i<NOFILE;i++){if(u_ofile3575[i]==-1){a[1] = i;/*写*/u_ofile3575[i] = 1;/*写端*/ break;}if(i>=NOFILE){printf("u_ofile3575分配失败,failure to create a pipe\n");return -2;}pfile = (char *)malloc(PSIZE*sizeof(char));/*申请模拟管道用的内存空间*/ if(pfile==NULL)/*申请可能不成功*/{printf("failure to create a pipe\n");return -1;}for(i=0;i<NFILE;i++){if(file[i].f_count!=1)file[i].f_flag = 'r';/*读标志*///file[i].f_inode = 0;/*读对应pipecb3575表下标*/file[i].f_count = 1;/*file[0]这个表项在被使用,不可再分配*/ file[i].f_offset = 0;/*读指针*/u_ofile3575[a[0]] = i;/*读端*/break;}}for(i=0;i<NFILE;i++){if(file[i].f_count!=1){file[i].f_flag = 'w';/*写标志*///file[i].f_inode = 0;/*写对应pipecb3575控制块下标*/file[i].f_count = 1;/*file[1]这个表项在被使用,不可再分配*/file[i].f_offset = 0;/*写指针*/u_ofile3575[a[1]] = i;/*写端*/break;}}if(i>=NFILE){printf("failure to create a pipe\n");return -1;}for(i=0;i<NPIPE;i++){if(pipecb3575[i].p_count==0){pipecb3575[i].p_addr = pfile;/*给管道文件基地址赋值*/ pipecb3575[i].p_size = PSIZE;/*管道文件大小*/pipecb3575[i].p_count = 2;/*读写都在进行,此pipecb3575表项不可再分*/file[u_ofile3575[a[0]]].f_inode = i;file[u_ofile3575[a[1]]].f_inode = i;break;}}if(i>=NPIPE){printf("failure to create a pipe\n");return -1;}printf("Secceed create the pipe\n");return 0;/*分配成功*/}/*关闭管道*/int close_simulate3575(int a[]){printf("start to close the pipe you have created\n");char *p;int i;for(i=0;i<2;i++){p=pipecb3575[file[u_ofile3575[a[i]]].f_inode].p_addr;/*if(p!=NULL)free(p); //释放管道内存*/pipecb3575[file[u_ofile3575[a[i]]].f_inode].p_count = 0; /*管道控制块计数清零*/file[u_ofile3575[a[i]]].f_count = 0; /*file表项计数清零*/u_ofile3575[a[i]] = -1; /*u_ofile3575表项清空*/a[i] = -1; /*fdp[]清空?*/}printf("secceed close the pipe\n");return 0;}/*写管道*/int numwrite_simulate3575;int write_simulate3575(int fd,char *ca,int n)//将内存ca内容写入n个字符到管道fd里{printf("(memory---->pipe)input data in memory *ca into pipe\n");numwrite_simulate3575++;long offr,offw;/*读写指针,实际是读写字符个数*/int r;/*管道文件读端*/int m;/*若ca中的字符不能一次写完,m用来表示一次可写入的字符的最大数*/int w = u_ofile3575[fd];/*管道文件写端*/int pf = file[w].f_inode;/*读管道对应的pipecb3575表的下标*/ int n1 = n;/*一次应该写入的字符个数*/int wstart = 0;/*计数器,写入字符个数*/int i = 0;for(i;i<NFILE;i++)/*寻找写管道对应的读管道的读端*/{if((file[i].f_flag=='r')&&(file[i].f_inode==pf)){r = i;break;}else{continue;}}printf("----add the lock\n");pthread_mutex_lock(&lock);/*互斥锁,相当于进入临界区*/offr = file[r].f_offset;/*赋值读指针*/offw = file[w].f_offset;/*赋值写指针*/if((offw+n1-PSIZE)>offr)/*不能一次写完*/{if(pipecb3575[pf].p_count==0)/*对文件的复制操作已进行结束,管道文件被释放*/{printf("对文件的复制操作已进行结束,管道文件被释放\n");return 0;}else{m = PSIZE+offr-offw;/*最多可写入数*/for(wstart=0;wstart<m;wstart++){*(pipecb3575[pf].p_addr+offw%PSIZE) = *ca;ca++;offw++;}file[w].f_offset = offw;/*重定位写指针位置*/n1 = n1-m;/*剩余需要读的字符个数*/printf("weak up the read thread , pipe is readable\n");pthread_cond_signal(&rflag);/*唤醒读线程,管道可读*/printf("write thread is blocked and under the statement of waiting\n");pthread_cond_wait(&wflag,&lock);/*写线程封锁等待*/}}/*一次性可将ca中内容全部写入管道*/offr = file[r].f_offset;offw = file[w].f_offset;for(wstart=0;wstart<n1;wstart++){/*printf("%d\n",pipecb3575[pf].p_addr);*/*(pipecb3575[pf].p_addr+offw%PSIZE) = *ca;/*printf("%d\n",wstart);*/ca++;offw++;}file[w].f_offset = offw;pthread_cond_signal(&rflag);printf("----release the lock\n");pthread_mutex_unlock(&lock);printf("Secceed (memory---->pipe)input data in memory *ca into pipe\n"); return n;/*返回写入字符个数*/}/*读管道*/int numread_simulate3575;//read_simulate3575 diaoyongshuint read_simulate3575(int fd,char *ca,int n)//将管道fd内容读取n个字符到内存ca里{printf("(pipe---->memory)output data from pipe into memory *ca\n");numread_simulate3575++;long offr,offw;/*读写指针,实际是读写字符个数*/int w;/*管道文件写端*/int m;/*若ca中的字符不能一次读完,m用来表示一次可读出的字符的最大数*/int r = u_ofile3575[fd];/*管道文件读端*/int pf = file[r].f_inode;/*读管道对应的pipecb3575表的下标*/int rstart = 0;/*计数器,读出字符个数*/int i = 0;for(i;i<NFILE;i++)/*寻找读管道对应的读管道的端*/{if((file[i].f_flag=='w')&&(file[i].f_inode==pf)) {w = i;break;}else{continue;}}printf("----add the lock\n");pthread_mutex_lock(&lock);/*互斥锁,相当于进入临界区*/ offr = file[r].f_offset;/*赋值读指针*/offw = file[w].f_offset;/*赋值写指针*/if(offr==offw)/*管道空,无内容可读*/{printf("pipe is empty , nothing to output\n");if(pipecb3575[pf].p_count==1)/*写端关闭*/{pipecb3575[pf].p_count--;/*文件的复制以完成,释放管道文件的空间*/ printf("the write point is closed,the copy of the file is finished\n");return 0;}else{printf("weak up the write thread , make the pipe writable\n");pthread_cond_signal(&wflag);/*唤醒写线程,管道可写*/printf("read thread is blocked and under the statement of waiting\n");pthread_cond_wait(&rflag,&lock);/*读线程封锁等待*/}}offr = file[r].f_offset;offw = file[w].f_offset;m = n<=(offw-offr)?n:(offw-offr);/*得到可读字符个数*/for(rstart=0;rstart<m;rstart++){*ca = *(pipecb3575[pf].p_addr+offr%PSIZE);ca++;offr++;}file[r].f_offset = offr;/*重定位读指针位置*/printf("weak the write thread , make the pipe writable\n");pthread_cond_signal(&wflag);printf("----release the lock\n");pthread_mutex_unlock(&lock);printf("Secceed (pipe---->memory)output data from the pipe into memory *ca\n");return m;}/*线程调用,读源文件,写管道*/void *pwrite3575(void *a)//将源文件a内容写入管道中{printf("(file---->pipe)input data from the original file into pipe\n"); char abuf1[BSIZE];struct arg_set *args=(struct arg_set *)a;/*需要传入多个参数时,用结构体传*/int fdr;int n_r;/*管道文件写入字符数*/if((fdr=open(args->fname,O_RDONLY))!=-1){while((n_r=read(fdr,abuf1,BSIZE))>0)/*读文件,写管道*/{printf("(file---->memory)input data in original file into memory *ca\n");printf("Secceed (file---->memory)input data in original file into memory *ca\n");//printf("(memory---->pipe)input data in memory *ca into pipe\n"); write_simulate3575(args->f,abuf1,n_r);//printf("Secceed (memory---->pipe)input\n");}pipecb3575[file[u_ofile3575[args->f]].f_inode].p_count--;/*文件已读完,关闭管道写端*/}else{perror(args->fname);/*打开源文件可能不成功*/return NULL;}printf("Secceed (file---->pipe)input data from the original file into pipe\n");return NULL;}/*线程调用,写目标文件,读管道*/void *pread3575(void *a)//读取管道,将其中内容写入新建文件中{printf("(pipe---->file)output data from the pipe into new file\n");char abuf2[BSIZE];/*缓冲区*/struct arg_set *args=(struct arg_set *)a;/*需要传入多个参数时,用结构体传*/int fdw;int n_w;/*管道文件读出字符数*/if((fdw=open(args->fname,O_CREAT|O_RDWR,0777))!=-1){while((n_w=read_simulate3575(args->f,abuf2,BSIZE))>0)/*读管道,写文件*/{//printf("(pipe---->memory)output data from pipe into memory*ca\n");//printf("Secceed (pipe---->memory)output data from pipe into memory *ca\n");printf("(memory---->file)output data in memory *ca into file\n");write(fdw,abuf2,n_w);printf("Secceed (memory---->file)output data from the pipe into new file\n");}}else{perror(args->fname);/*打开目标文件可能出错*/return NULL;}printf("Secceed (pipe---->file)output data from the pipe into new file\n"); return NULL;}/*主函数*/int main(int argc,char *argv[]){int x;u_ofile_init3575();while((x=pipe_simulate3575(fd))==-1);/*创建管道,即申请空间*/if(x==-2)return -1;pthread_t t;//thread IDstruct arg_set args[2];/*用结构体传写线程需要的参数:文件名,管道文件读写端*/args[0].fname=argv[1];/*源文件名*/args[0].f=fd[1];/*管道文件写端*/args[1].fname=argv[2];/*目标文件名*/args[1].f=fd[0];/*管道文件读端*/pthread_create(&t,NULL,pwrite3575,(void *)&args[0]);/*创建子线程,写管道*/ pread3575((void *)&args[1]);/*主线程调用,读管道*/pthread_join(t,NULL);/*等待写线程结束*/close_simulate3575(fd);printf("\nnum of read_simulate3575 = %d\n",numread_simulate3575); printf("num of write_simulate3575 = %d\n",numwrite_simulate3575); return 0;}附录二(实验结果):ls -l总用量 2379-rw-r--r-- 1 john john 50 2012-12-17 18:06 3575-rw-r--r-- 1 john john 36864 2012-07-15 07:53 3575.doc-rw-r--r-- 1 john john 95441 2012-08-27 22:16 3575.JPG-rw-r--r-- 1 john john 2083969 2010-11-08 13:07 3575.mp3-rw-r--r-- 1 john john 84835 2012-07-11 13:22 3575.pdf-rw-r--r-- 1 john john 73728 2012-12-17 16:48 3575.ppt-rw-r--r-- 1 john john 19924 2012-07-03 18:51 3575.rar-rw-r--r-- 1 john john 0 2012-12-17 22:49 sta1-rw-r--r-- 1 john john 11563 2012-12-17 22:46 tc_copy.cpp ./tc 3575 a3575 > copy1./tc 3575 a3575.doc./tc 3575.doc a3575.doc./tc 3575.ppt a3575.ppt./tc 3575.mp3 a3575.mp3./tc 3575.rar a3575.rar > copy2./tc 3575.pdf a3575.rarls -l总用量 5163-rw-r--r-- 1 john john 50 2012-12-17 18:06 3575-rw-r--r-- 1 john john 36864 2012-07-15 07:53 3575.doc-rw-r--r-- 1 john john 95441 2012-08-27 22:16 3575.JPG-rw-r--r-- 1 john john 2083969 2010-11-08 13:07 3575.mp3-rw-r--r-- 1 john john 84835 2012-07-11 13:22 3575.pdf-rw-r--r-- 1 john john 73728 2012-12-17 16:48 3575.ppt-rw-r--r-- 1 john john 19924 2012-07-03 18:51 3575.rar-rwxr-xr-x 1 john john 50 2012-12-17 22:51 a3575-rwxr-xr-x 1 john john 36864 2012-12-17 22:51 a3575.doc -rwxr-xr-x 1 john john 95441 2012-12-17 22:53 a3575.JPG -rwxr-xr-x 1 john john 2083969 2012-12-17 22:54 a3575.mp3 -rwxr-xr-x 1 john john 84835 2012-12-17 22:56 a3575.pdf -rwxr-xr-x 1 john john 73728 2012-12-17 22:53 a3575.ppt -rwxr-xr-x 1 john john 19924 2012-12-17 22:55 a3575.rar -rw-r--r-- 1 john john 1320 2012-12-17 22:51 copy1-rw-r--r-- 1 john john 419294 2012-12-17 22:56 copy2-rw-r--r-- 1 john john 690 2012-12-17 22:49 sta1-rw-r--r-- 1 john john 0 2012-12-17 22:57 sta2-rwxr-xr-x 1 john john 12256 2012-12-17 22:50 tc-rw-r--r-- 1 john john 11563 2012-12-17 22:46 tc_copy.cpp cat copy1init the u_ofilestart to create a pipeSecceed create the pipe(pipe---->file)output data from the pipe into new file(pipe---->memory)output data from pipe into memory *ca----add the lockpipe is empty , nothing to outputweak up the write thread , make the pipe writableread thread is blocked and under the statement of waiting(file---->pipe)input data from the original file into pipe(file---->memory)input data in original file into memory *ca Secceed (file---->memory)input data in original file into memory *ca (memory---->pipe)input data in memory *ca into pipe----add the lock----release the lockSecceed (memory---->pipe)input data in memory *ca into pipeSecceed (file---->pipe)input data from the original file into pipe weak the write thread , make the pipe writable----release the lockSecceed (pipe---->memory)output data from the pipe into memory *ca (memory---->file)output data in memory *ca into fileSecceed (memory---->file)output data from the pipe into new file (pipe---->memory)output data from pipe into memory *ca----add the lockpipe is empty , nothing to outputthe write point is closed,the copy of the file is finished Secceed (pipe---->file)output data from the pipe into new file start to close the pipe you have createdsecceed close the pipenum of readp = 2num of writep = 1。

合集下载

操作系统实验:Linux并发程序设计

操作系统实验:Linux并发程序设计

实验4 操作系统综合实验----Linux并发程序设计(实验时间:90分钟)一、背景知识:管道是Linux中最常用的进程间通信IPC(inter process communication)机制。

利用管道时,一个进程的输出可成为另外一个进程的输入。

当输入输出的数据量特别大时,这种IPC机制非常有用。

可以想象,如果没有管道机制,而必须利用文件传递大量数据时,会造成许多空间和时间上的浪费。

在Linux中,通过将两个file结构指向同一个临时的索引节点,而索引节点又指向同一个物理页而实现管道。

管道被定义为一对分开的文件描述符:一个输入和一个输出。

我们可以从管道的一端写入然后从管道的另一端读取。

如果定义管道的函数pipe使管道成功建立的话,pipe就会返回0,同时生成两个文件描述符。

例如,如果两个文件描述符是数组myPipe[2],则myPipe[2]将会包括两个新的代表管道的输入(myPipe[1])和对管道的输出(myPipe[0])的文件描述符。

函数dup允许我们复制一个文件描述符。

我们向函数传递一个已经存在了的描述符,然后它返回了一个和前面那个一模一样的新的描述符。

这意味着两个描述符共享相同的结构。

程序调用fork创建一个进程,称为子进程。

调用的进程称为父进程。

子进程继承了父进程的几乎所有的属性,当然也具有跟父进程不同的属性。

调用fork会返回两次。

返回值= = 0,代表子进程;返回值> 0 ,代表父进程。

返回值< 0 ,代表error。

fork正确返回后,在父、子进程中可以直接写代码或者用execl系列函数执行应用程序。

如果是用execl函数执行应用程序,且调用execl成功,那么进程会一直阻塞在execl处,执行完后直接退出进程,而不会再执行execl以后的代码。

二、实验目的1) 通过在Linux进程之间进行的通信实例来学习并发程序设计的方法。

2) 通过Linux进程通信的程序设计与实现,进一步熟悉操作系统的进程概念,理解Linux 进程管理概念。

操作系统实验报告进程、线程观察参考模板

操作系统实验报告进程、线程观察参考模板

实验要求:
对观察到的内容做详细记录分析,并写出实验报告。

四、实验过程与分析
1、Windows XP的操作:
在Windows XP下任务管理器中观察所有进程的情况
Cpu使用情况
(1)在Windows XP下打开Word,QQ,IE浏览器,,三个程序,在任务管理器中观察三个进程的大小,并做好记录。

设置进程中的显示列
a﹑对IE浏览器进行观察
当打开多个IE网页时
b﹑对Word进行观察打开1个word文档时
当打开3个word文档时c﹑对QQ进行观察
打开多个会话页面时
2、虚拟机 Linux下的操作:
(1)在虚拟机 Linux下的系统监视器中观察所有进程的情况
在虚拟机 Linux下的终端,用ps aux 观察所有进程的情况
总结:
(1)同一程序的进程大于其可执行程序的大小.。

分析(1)程序是静态的,而进程是程序的一次执行过程,它是动态的创建和消亡的,具有一定的生命周期,是暂时存在的,而我们运行程序的.exe文件时,系统调用该程序,为其创建相应的的进程。

进程它包括程序、数据和进程控制块(PCB)三部分,所谓的创建进程就是创建PCB。

而在执行过程中它还要获得相应的系统资源,要保证程序能独立运行,操作系统还要为其配置一个专门的数据结构,即PCB,因此,进程大于其可执行程序的大小。

(2)一个进程包还多个线程,同一进程中,多个线程可以并发执行。

线程是轻量级进程,它是一个基本的CPU执行单元,也是程序执行流的最小单元,是被系统独立调度基本单位,线程自己不拥有系统
友情提示:范文可能无法思考和涵盖全面,供参考!最好找专业人士起草或审核后使用,感谢您的下载!。

操作系统实验一进程与线程—Linux进程与线程通讯实验报告

操作系统实验一进程与线程—Linux进程与线程通讯实验报告

实验报告
./clone输出结果:
实验讨论:
由程序1结果可知,使用fork()语句创建的子进程与其父进程具有相对独立的地址空间,在此解决生产者-消费者问题里,可以采用pipe()进行通讯。

子进程复制了父进程的打开文件表,所以pipe()所建立的通信管道可被子进程继承,生产和消费进程可以通过对同一通信管道文件的读书进行通讯。

由程序2结果可知:clone()语句在创建进程时,可通过参数设定子进程与父进程是否共享存储空间,从而可以创建真正意义上的程序。

生产者和消费者进程共享内在,从而可以通过共享交换数据。

但多个进程共享共存需要互斥机制。

三.实验流程图
程序二流程图:
基于clone()系统调用
父进程:
生产者子进程(Producer):。

查看程序的进程和线程实验报告

查看程序的进程和线程实验报告

查看程序的进程和线程实验报告篇一:程序实验2:11-多线程编程---实验报告程序实验二:11-多线程编程实验专业班级实验日期 5.21 姓名学号实验一(p284:11-thread.c)1、软件功能描述创建3个线程,让3个线程重用同一个执行函数,每个线程都有5次循环,可以看成5个小任务,每次循环之间会有随即等待时间(1-10s)意义在于模拟每个任务到达的时间是随机的没有任何的特定规律。

2、程序流程设计3.部分程序代码注释(关键函数或代码)#include#include#include#define T_NUMBER 3#define P_NUMBER 5#define TIME 10.0void *thrd_func(void *arg ){(本文来自: 小草范文网:查看程序的进程和线程实验报告) int thrd_num=(int)arg;int delay_time =0;int count =0;printf("Thread %d is staraing\n",thrd_num);for(count=0;count {delay_time =(int)(rand()*TIME/(RAND_MAX))+1;sleep(delay_time);printf("\tTH%d:job%d delay =%d\n",thrd_num,count,delay_time);}printf("%d finished\n",thrd_num);pthread_exit(NULL);}int main(){pthread_t thread[T_NUMBER];int no=0,res;void * thrd_ret;srand(time(NULL));for(no=0;no {res=pthread_create(&thread[no],NULL, thrd_func,(void*)no);if(res!=0){printf("Creay th %d faild\n",no);exit(res);}}printf("success\nwaiting\n");for(no=0;no {res=pthread_join(thread[no],&thrd_ret);if(!res){printf("t %d joined\n",no);}else{printf("T %djoined faild\n",no);}}return 0;}4.编译、运行方法及结果(抓屏)5.结果分析由运行结果可以看出,创建线程、释放资源按照顺序,而每个线程的运行和结束是独立与并行的。

多线程程序实验报告(3篇)

多线程程序实验报告(3篇)

第1篇一、实验目的1. 理解多线程的概念和作用。

2. 掌握多线程的创建、同步和通信方法。

3. 熟悉Java中多线程的实现方式。

4. 提高程序设计能力和实际应用能力。

二、实验环境1. 操作系统:Windows 102. 开发工具:IntelliJ IDEA3. 编程语言:Java三、实验内容本次实验主要完成以下任务:1. 创建多线程程序,实现两个线程分别执行不同的任务。

2. 使用同步方法实现线程间的同步。

3. 使用线程通信机制实现线程间的协作。

四、实验步骤1. 创建两个线程类,分别为Thread1和Thread2。

```javapublic class Thread1 extends Thread {@Overridepublic void run() {// 执行Thread1的任务for (int i = 0; i < 10; i++) {System.out.println("Thread1: " + i);}}}public class Thread2 extends Thread {@Overridepublic void run() {// 执行Thread2的任务for (int i = 0; i < 10; i++) {System.out.println("Thread2: " + i);}}}```2. 创建一个主类,在主类中创建两个线程对象,并启动它们。

```javapublic class Main {public static void main(String[] args) {Thread thread1 = new Thread1();Thread thread2 = new Thread2();thread1.start();thread2.start();}```3. 使用同步方法实现线程间的同步。

```javapublic class SynchronizedThread extends Thread {private static int count = 0;@Overridepublic void run() {for (int i = 0; i < 10; i++) {synchronized (SynchronizedThread.class) {count++;System.out.println(Thread.currentThread().getName() + ": " + count);}}}}public class Main {public static void main(String[] args) {Thread thread1 = new SynchronizedThread();Thread thread2 = new SynchronizedThread();thread1.start();thread2.start();}```4. 使用线程通信机制实现线程间的协作。

计算机操作系统实验课实验报告

计算机操作系统实验课实验报告

实验报告实验课程: 计算机操作系统学生姓名:XXX学号:XXXX专业班级:软件2014年12月25日目录实验一熟悉Windows XP中的进程和线程 (3)实验二进程调度 (7)实验三死锁避免—银行家算法的实现 (16)实验四存储管理 (22)实验一熟悉Windows XP中的进程和线程一、实验名称熟悉Windows XP中的进程和线程二、实验目的1、熟悉Windows中任务管理器的使用。

2、通过任务管理器识别操作系统中的进程和线程的相关信息。

3、掌握利用spy++.exe来察看Windows中各个任务的更详细信息。

三、实验结果分析1、启动操作系统自带的任务管理器:方法:直接按组合键Ctrl+Alt+Del,或者是在点击任务条上的“开始”“运行”,并输入“taskmgr.exe”。

2、调整任务管理器的“查看”中的相关设置,显示关于进程的以下各项信息,并完成下表:表一:统计进程的各项主要信息3、启动办公软件“Word”,在任务管理器中找到该软件的登记,并将其结束掉。

再从任务管理器中分别找到下列程序:winlogon.exe、lsass.exe、csrss.exe、smss.exe,试着结束它们,观察到的反应是任务管理器无法结束进程,原因是该系统是系统进程。

4、在任务管理器中找到进程“explorer.exe”,将之结束掉,并将桌面上你打开的所有窗口最小化,看看你的计算机系统起来什么样的变化桌面上图标菜单都消失了、得到的结论 explorer.exe是管理桌面图标的文件(说出explorer.exe进程的作用)。

5、运行“spy++.exe”应用软件,点击按钮“”,切换到进程显示栏上,查看进程“explorer.exe”的各项信息,并填写下表:进程:explorer.exe 中的各个线程6、注意某些线程前有“+”,如图所示:,说明二者之间的差异前有“+”其器线程下有窗口。

四、心得体会通过本次实验,我了解到了windows系统中进程的管理与操作,我了解了如何切出任务管理器,任务管理器应用与其他与进程相关的知识,明白了有些系统程序不能够关闭,系统中的进程与线程虽然很多,但是其中有许多关联,只要弄清楚其中的关联那么就能够运用好进程与线程,达到我们的目的。

厦门理工学院操作系统实验4

《操作系统》实验报告a.程序运行结果ret= 是一个不确定的值,试说明原因b.将程序中int a=20语句调换到红颜色位置,结果如何c. 将程序中int a=20 int*p=&a;语句置换成蓝颜色语句,结果又如何?(2)阅读下面接收创建子线程返回一个复杂的数据结构变量程序代码并输入、调试、输出结果;针对下列问题进行说明或修改:将temp定义和赋值变为create()函数内定义的局部变量,应如何修改程序对结果又什么影响并说明原因?四、实验结果与数据处理1.线程的创建(1)实验结果:图1:进程的创建一代码图2:程序运行结果(2)结果分析:运行结果:我们可以看到主线程会先打印出相应的ID,然后再是子线程打印自己的ID原因:当一个程序启动时,就有一个进程被操作系统(OS)创建,与此同时一个线程也立刻运行,该线程通常叫做程序的主线程(Main Thread),因为它是程序开始时就执行的,如果你需要再创建线程,那么创建的线程就是这个主线程的子线程。

每个进程至少都有一个主线程,所以没有干预的情况下,主线程都是优先于子线程运行的。

所以在输出ID的时候,主线程会比子线程早输出自己的ID。

(3)思考:a.通过以上实验线程执行与函数调用的不同,线程与进程的不同答:线程是程序执行部分,是操作系统的划分。

函数是编程中的概念,是功能模块的划分。

b.如何控制主线程与子线程的执行顺序答:我们可以使用sleep函数来对线程进行挂起的操作,从而来控制主线程与子线程的执行顺序。

图3:修改后的代码图4:修改后的代码运行结果总结:①线程被创建后,并不能保证那个线程先执行,新创建的线程和调用线程的执行顺序不确定,由操作系统进行调度,注意:编译时要连接库libpthread;就是编译的时候要加-lpthread②在C程序中, main(int argc, char **argv) 就是一个主线程。

我们可以在主线程中做任何普通线程可以做的事情,但它和一般的线程有有一个很大的区别:主线程返回或者运行结束时会导致进程的结束,而进程的结束会导致进程中所有线程的结束。

计算机操作系统课设操作系统课程设计报告

课程实验报告题目:操作系统原理专业班级:信息安全1302 班学号:姓名:指导教师:报告日期:2016 年2 月29 日计算机科学与技术学院目录1. 初探Linux 编程环境 (1)1.1. 实验目的 (1)1.2. 实验内容 (1)1.2.1. 实验一 (1)1.2.2. 实验二 (1)1.3. 实验设计 (1)1.3.1. 实验一 (1)1.3.2. 实验二 (2)1.4. 实验环境 (3)1.5. 实验步骤 (3)1.5.1. 实验一 (3)1.5.2. 实验二 (3)1.6. 调试记录 (4)1.6.1. 实验一 (4)1.6.2. 实验二 (4)1.7. 实验结果 (5)1.7.1. 实验一 (5)1.7.2. 实验二 (6)2. 通过编译内核的方式为Linux 增加系统调用 (8)2.1. 实验目的 (8)2.2. 实验内容 (8)2.3. 实验设计 (8)2.4. 实验环境 (8)2.5. 实验步骤 (8)2.6. 调试记录 (10)2.7. 实验结果 (11)3. 编写设备驱动程序 (13)3.1. 实验目的 (13)3.2. 实验内容 (13)3.3. 实验设计 (13)3.4. 实验环境 (14)3.5. 实验步骤 (14)3.6. 调试记录 (15)3.7. 实验结果 (15)4. 实现系统监控程序 (17)4.1. 实验目的 (17)4.2. 实验内容 (17)4.3. 实验设计 (18)4.4. 实验环境 (22)4.5. 实验步骤 (22)4.6. 调试记录 (22)4.7. 实验结果 (23)5. 设计模拟文件系统 (28)5.1. 实验目的 (28)5.2. 实验内容 (28)5.3. 实验设计 (28)5.4. 实验环境 (33)5.5. 实验步骤 (34)5.6. 调试记录 (34)5.7. 实验结果 (34)6. 附注:程序清单 (39)6.1. 文件拷贝程序 (39)6.2. 多进程多窗口实验 (40)6.3. 编译内核添加系统调用 (41)6.4. 编写模块 (43)6.5. 任务监视器 (49)6.6. 模拟文件系统 (64)1. 初探Linux 编程环境1.1. 实验目的掌握Linux 操作系统的使用方法,包括键盘命令、系统调用;掌握在Linux 下的编程环境,了解在Linux 如何进行多线程编程以及图形编程。

并发执行实验报告

一、实验目的1. 了解并发执行的概念和原理。

2. 学习并发编程技术,提高程序执行效率。

3. 通过实验验证并发执行对程序性能的影响。

二、实验环境1. 操作系统:Windows 102. 编程语言:Java3. 开发工具:IntelliJ IDEA4. 并发框架:Java并发包(java.util.concurrent)三、实验内容1. 实验一:线程同步2. 实验二:线程池3. 实验三:并发容器4. 实验四:Future和Callable四、实验步骤1. 实验一:线程同步(1)创建一个共享资源,用于模拟多个线程对资源的访问。

(2)使用synchronized关键字实现线程同步。

(3)比较同步前后程序执行时间。

2. 实验二:线程池(1)创建一个线程池,并提交多个任务到线程池中执行。

(2)比较线程池和普通线程执行任务的效率。

3. 实验三:并发容器(1)使用并发容器(如ConcurrentHashMap)和普通容器(如HashMap)进行数据操作。

(2)比较两种容器在并发环境下的性能差异。

4. 实验四:Future和Callable(1)使用Callable接口和Future接口实现异步计算。

(2)比较使用Future和Callable前后程序执行时间。

五、实验结果与分析1. 实验一:线程同步实验结果显示,在同步前,程序执行时间为5秒;在同步后,程序执行时间为2秒。

这说明线程同步可以有效地提高程序执行效率。

2. 实验二:线程池实验结果显示,在普通线程环境下,程序执行时间为10秒;在线程池环境下,程序执行时间为6秒。

这说明线程池可以显著提高程序执行效率。

3. 实验三:并发容器实验结果显示,在并发环境下,使用并发容器(如ConcurrentHashMap)的平均执行时间为1秒,而使用普通容器(如HashMap)的平均执行时间为3秒。

这说明并发容器在处理并发操作时具有更好的性能。

4. 实验四:Future和Callable实验结果显示,使用Future和Callable接口实现异步计算后,程序执行时间为4秒;而同步执行程序执行时间为8秒。

操作系统实验报告2doc

操作系统实验报告2doc操作系统实验报告2篇一:操作系统实验二实验报告操作系统实验报告——实验二:线程和管道通信实验一、实验目的通过Linux 系统中线程和管道通信机制的实验,加深对于线程控制和管道通信概念的理解,观察和体验并发进(线)程间的通信和协作的效果 ,练习利用无名管道进行进(线)程间通信的编程和调试技术。

二、实验说明1) 与线程创建、执行有关的系统调用说明线程是在共享内存中并发执行的多道执行路径,它们共享一个进程的资源,如进程程序段、文件描述符和信号等,但有各自的执行路径和堆栈。

线程的创建无需像进程那样重新申请系统资源,线程在上下文切换时也无需像进程那样更换内存映像。

多线程的并发执行即避免了多进程并发的上下文切换的开销又可以提高并发处理的效率。

pthread 库中最基本的调用。

1.pthread_create 系统调用语法:#includeInt pthread_create(pthread_t *thread,pthread_attr_t *attr,void *(*start_routine)(void *) Void *arg);pthread_create 函数创建一个新的线程。

pthread_create 在thread 中保存新线程的标识符。

Attr 决定了线程应用那种线程属性。

使用默认可给定参数 NULL; (*start_routine) 是一个指向新线程中要执行的函数的指针 arg 是新线程函数携带的参数。

Pthread_create 执行成功会返回0并在 thread 中保存线程标识符。

执行失败则返回一个非0的出错代码2.pthread_exit 系统调用语法:#includevoid pthread_exit(void *retval);pthread_exit 函数使用函数pthread_cleanup_push 调用任何用于该线程的清除处理函数,然后中止当前进程的执行,返回retval。

  1. 1、下载文档前请自行甄别文档内容的完整性,平台不提供额外的编辑、内容补充、找答案等附加服务。
  2. 2、"仅部分预览"的文档,不可在线预览部分如存在完整性等问题,可反馈申请退款(可完整预览的文档不适用该条件!)。
  3. 3、如文档侵犯您的权益,请联系客服反馈,我们会尽快为您处理(人工客服工作时间:9:00-18:30)。
相关文档
最新文档