Tải bản đầy đủ (.pdf) (19 trang)

BÁO cáo bài tập lớn hệ điều HÀNH đề tài PThread and multicore programming

Bạn đang xem bản rút gọn của tài liệu. Xem và tải ngay bản đầy đủ của tài liệu tại đây (1.66 MB, 19 trang )

ĐẠI HỌC QUỐC GIA THÀNH PHỐ HỒ CHÍ MINH
TRƯỜNG ĐẠI HỌC BÁCH KHOA


BÁO CÁO BÀI TẬP LỚN
HỆ ĐIỀU HÀNH

Đề tài :
PThread and Multicore programming

GVHD: GV: Nguyễn Quang Hùng
Thực hiện: Nguyễn Lê Minh Bảo Hà Việt Đức Đoàn Thảo Nhi - 2014010
Trịnh Tiến Đạt - 2012959
Từ Hoàng Phiếm - 2014112

Lớp L04, ngày 20 tháng 4 năm 2022


Mục lục
1

Phần Lý thuyết . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .

3

2
2.1

Phần code . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
Mutexes . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .


4
4

2.1.1
2.1.2
2.1.3

2.2

Review, compile and run the dotprodserial.c program . . . . .
Review, compile and run the dotprodmutex.c program . . . .
Execute the dotprodmutex.c program with thread are arranged
Condition Variables . . . . . . . . . . . . . . . . . . . . . . . .

.
.
.
.

.
.
.
.

.
.
.
.

.

.
.
.

.
.
.
.

.
.
.
.

.
4
.
4
.
7
. 11

2.2.1
2.2.2

2.3

Review, compile and run the condvar.c program . . . . . . . . . . . . . . . 11
Review, compile, run the bug4.c program and fix the problem . . . . . . . 13
Figure out and fix the global sum . . . . . . . . . . . . . . . . . . . . . . . 14


2.4

Compile and run arrayloops.c . . . . . . . . . . . . . . . . . . . . . . . . . 19


Phần 1 Phần Lý thuyết

Báo cáo Bài tập lớn Hệ Điều Hành

3


Phần 2 Phần code
2.1
2.1.1

Mutexes
Review, compile and run the dotprodserial.c program

The dotprodserial.c program used to calculate the indirection of two vectors with
length =100000. Two vectors is calculated to be shown struct DOTDATA. This program does by running sequentially on a thread.
Output : Result When dotprodserial.c run

Hình 2.1.1: Real time of dotpodserial.c.

2.1.2

Review, compile and run the dotprodmutex.c program


The dotprodmutex.c program used to calculate the direction of two vectors with
length=100000 . But here is the difference:
• In main() function has initialize with the number of thread is 4 to run parallel
processes.
• In dotprod() function use pthreadmutexlock và pthreadmutexunlock is one of
the main means to synchronize flows and to protect shared data when multiple
writing happens.
Output : Result when the dotprodmutex.c run

4

Báo cáo Bài tập lớn Hệ Điều Hành


Phần 2
Phần code

Trường Đại học Bách Khoa Thành phố Hồ Chí Minh

Hình 2.1.2: Real time of dotpodmutex.c

Output : The dotprodmutex.c run with thread = 2, 4, 8, 16, 32 và sum=100000
• Thread=2

Hình 2.1.3: Real time of dotpodmutex.c with thread=2.

• Thread=4

Hình 2.1.4: Real time of dotpodmutex.c with thread=4.


Báo cáo Bài tập lớn Hệ Điều Hành

5


Trường Đại học Bách Khoa Thành phố Hồ Chí Minh

• Thread=8

Hình 2.1.5: Real time of dotpodmutex.c with thread=8.

• Thread=16

Hình 2.1.6: Real time of dotpodmutex.c with thread=16.

6

Báo cáo Bài tập lớn Hệ Điều Hành

Phần 2
Phần code


Phần 2
Phần code

Trường Đại học Bách Khoa Thành phố Hồ Chí Minh

• Thread=32


Hình 2.1.7: Real time of dotpodmutex.c with thread=32.

Comparison chart between dotprodserial.c and dotprodmutex.c

2.1.3

Execute the dotprodmutex.c program with thread are arranged

Explain the code :
• Wanting the thread to be printed in the same self, we need to let pthreadjoin
within for the time of creating pthreadcreate. Because the thread is created it
will run and wait for pthreadjoin to pay the result, then create a new thread new
should order Print it will be true.
• As for pthreadjoin at another for another round, it only works to wait all the
thread returns the result before the main () stops.
• If there is no pthreadjoin, when the main () is finished, no matter whether other
threads are finished or not, the program is terminated.
Code after fixing :

Báo cáo Bài tập lớn Hệ Điều Hành

7


Trường Đại học Bách Khoa Thành phố Hồ Chí Minh

#include
#include <stdio.h>
#include <stdlib.h>
typedef struct

{
double
*a;
double
*b;
double
sum;
int
veclen;
} DOTDATA;
/* Define globally accessible variables and a mutex */
#define NUMTHRDS 4
#define VECLEN 100000
DOTDATA dotstr;
pthread_t callThd[NUMTHRDS];
pthread_mutex_t mutexsum;
void *dotprod(void *arg)
{
/* Define and use local variables for convenience */
int i, start, end, len ;
long offset;
double mysum, *x, *y;
offset = (long)arg;
len = dotstr.veclen;
start = offset*len;
end
= start + len;
x = dotstr.a;
y = dotstr.b;
/*


8

Báo cáo Bài tập lớn Hệ Điều Hành

Phần 2
Phần code


Phần 2
Phần code

Trường Đại học Bách Khoa Thành phố Hồ Chí Minh

Perform the dot product and assign result
to the appropriate variable in the structure.
*/
mysum = 0;
for (i=start; i{
mysum += (x[i] * y[i]);
}
/*
Lock a mutex prior to updating the value in the shared
structure, and unlock it upon updating.
*/
pthread_mutex_lock (&mutexsum);
dotstr.sum += mysum;
printf("Thread %ld did %d to %d: mysum=%f global
sum=%f\n",offset,start,end,mysum,dotstr.sum);

pthread_mutex_unlock (&mutexsum);
pthread_exit((void*) 0);
}
int main (int argc, char *argv[])
{
long i;
double *a, *b;
void *status;
pthread_attr_t attr;
/* Assign storage and initialize values */
a = (double*) malloc (NUMTHRDS*VECLEN*sizeof(double));
b = (double*) malloc (NUMTHRDS*VECLEN*sizeof(double));
for (i=0; ia[i]=1;
b[i]=a[i];
}

Báo cáo Bài tập lớn Hệ Điều Hành

9


Trường Đại học Bách Khoa Thành phố Hồ Chí Minh

Phần 2
Phần code

dotstr.veclen = VECLEN;
dotstr.a = a;
dotstr.b = b;

dotstr.sum=0;
pthread_mutex_init(&mutexsum, NULL);
/* Create threads to perform the dotproduct */
pthread_attr_init(&attr);
pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_JOINABLE);
for(i=0;i{
/* Each thread works on a different set of data.
* The offset is specified by 'i'. The size of
* the data for each thread is indicated by VECLEN.
*/
pthread_create(&callThd[i], &attr, dotprod, (void *)i);
/* Wait on the other threads- Fix*/
pthread_join(callThd[i], &status);
}
pthread_attr_destroy(&attr);

/* After joining, print out the results and cleanup */
printf ("Sum = %f \n", dotstr.sum);
free (a);
free (b);
pthread_mutex_destroy(&mutexsum);
pthread_exit(NULL);
}
#bo code vao day

10

Báo cáo Bài tập lớn Hệ Điều Hành



Phần 2
Phần code

2.2
2.2.1

Trường Đại học Bách Khoa Thành phố Hồ Chí Minh

Condition Variables
Review, compile and run the condvar.c program

Bài code mẫu condvar.c sử dụng Pthread contidion variables. Ở dưới hàm main(),
chúng ta sẽ tạo ra 3 thread. Hai trong số chúng sẽ tăng biến count, trong khi đó,
thread cịn lại sẽ xem giá trị của count. Khi biến count tăng lên một giới hạn cho
trước, waiting thread được báo hiệu bởi một trong 2 thread tăng biến count. Waiting
thread sẽ "awakens" và sau đó sửa đổi count. Chương trình sẽ tiếp tục cho đến khi
các thread đạt tới giá trị TCOUNT. Cuối cùng, chương trình sẽ in ra giá trị cuối cùng
của biến count.

OUTPUT:

Báo cáo Bài tập lớn Hệ Điều Hành

11


Trường Đại học Bách Khoa Thành phố Hồ Chí Minh

Phần 2

Phần code

inc_count(): thread 3, count = 1, unlocking mutex
inc_count(): thread 2, count = 2, unlocking mutex
Starting watch_count(): thread 1
watch_count(): thread 1 Count= 2. Going into wait...
inc_count(): thread 3, count = 3, unlocking mutex
inc_count(): thread 2, count = 4, unlocking mutex
inc_count(): thread 3, count = 5, unlocking mutex
inc_count(): thread 2, count = 6, unlocking mutex
inc_count(): thread 3, count = 7, unlocking mutex
inc_count(): thread 2, count = 8, unlocking mutex
inc_count(): thread 3, count = 9, unlocking mutex
inc_count(): thread 2, count = 10, unlocking mutex
inc_count(): thread 3, count = 11, unlocking mutex
inc_count(): thread 2, count = 12 Threshold reached. Just
sent signal.
inc_count(): thread 2, count = 12, unlocking mutex
watch_count(): thread 1 Condition signal received. Count=
12
watch_count(): thread 1 Updating the value of count...
watch_count(): thread 1 count now = 137.
watch_count(): thread 1 Unlocking mutex.
inc_count(): thread 3, count = 138, unlocking mutex
inc_count(): thread 2, count = 139, unlocking mutex
inc_count(): thread 3, count = 140, unlocking mutex
inc_count(): thread 2, count = 141, unlocking mutex
inc_count(): thread 3, count = 142, unlocking mutex
inc_count(): thread 2, count = 143, unlocking mutex
inc_count(): thread 3, count = 144, unlocking mutex

inc_count(): thread 2, count = 145, unlocking mutex
Main(): Waited and joined with 3 threads. Final value of
count = 145. Done.

12

Báo cáo Bài tập lớn Hệ Điều Hành


Phần 2
Phần code

2.2.2

Trường Đại học Bách Khoa Thành phố Hồ Chí Minh

Review, compile, run the bug4.c program and fix the problem

1. Run the bug4.c program:

Hình 2.2.1: The result after running the bug4.c program.

2. Run the bug4.c program:

Báo cáo Bài tập lớn Hệ Điều Hành

13


Trường Đại học Bách Khoa Thành phố Hồ Chí Minh


2.3

Figure out and fix the global sum

Result bug6.c
#First
thread: 0 starting. start=0 end=99999
thread: 2 starting. start=200000 end=299999
thread: 2 done. Global sum now is=103536
thread: 3 starting. start=300000 end=399999
thread: 3 done. Global sum now is=209650
thread: 0 done. Global sum now is=144053
thread: 5 starting. start=500000 end=599999
thread: 4 starting. start=400000 end=499999
thread: 5 done. Global sum now is=244978
thread: 6 starting. start=600000 end=699999
thread: 4 done. Global sum now is=354856
thread: 7 starting. start=700000 end=799999
thread: 6 done. Global sum now is=366826
thread: 7 done. Global sum now is=462298
thread: 1 starting. start=100000 end=199999
thread: 1 done. Global sum now is=562298
Final Global Sum=562298
#Second
thread: 0 starting. start=0 end=99999
thread: 1 starting. start=100000 end=199999
thread: 1 done. Global sum now is=123218
thread: 0 done. Global sum now is=133169
thread: 3 starting. start=300000 end=399999

thread: 4 starting. start=400000 end=499999
thread: 3 done. Global sum now is=258391
thread: 5 starting. start=500000 end=599999
thread: 4 done. Global sum now is=281444
thread: 6 starting. start=600000 end=699999
thread: 5 done. Global sum now is=367357
thread: 7 starting. start=700000 end=799999
thread: 6 done. Global sum now is=478160
thread: 2 starting. start=200000 end=299999
thread: 7 done. Global sum now is=519555
thread: 2 done. Global sum now is=584471
Final Global Sum=584471

14

Báo cáo Bài tập lớn Hệ Điều Hành

Phần 2
Phần code


Phần 2
Phần code

Trường Đại học Bách Khoa Thành phố Hồ Chí Minh

Giải thích: Do biến sum là biến global scope và các threads truy cập vào cùng 1
địa chỉ biến sum nên sẽ xảy ra tình trạng race condition. Giải pháp được đưa ra là sử
dụng mutex clock.


Báo cáo Bài tập lớn Hệ Điều Hành

15


Trường Đại học Bách Khoa Thành phố Hồ Chí Minh

Phần 2
Phần code

#include
#include <stdio.h>
#include <stdlib.h>
/* Define global data where everyone can see them */
#define NUMTHRDS 8
#define VECLEN 100000
pthread_mutex_t mutexsum;
int *a, *b;
long sum = 0.0;
void *dotprod(void *arg) {
/* Each thread works on a different set of data.
* The offset is specified by the arg parameter. The
size of
* the data for each thread is indicated by VECLEN.
*/
int i, start, end, offset, len;
long tid;
long local_sum = 0;
tid = (long)arg;
offset = tid;

len = VECLEN;
start = offset*len;
end
= start + len;
/* Perform my section of the dot product */
printf("thread: %ld starting. start=%d
end=%d\n",tid,start,end-1);
for (i=start ; i < end ; i++) local_sum += (a[i] *
b[i]);
printf("thread: %ld done. Global sum now
is=%li\n",tid,sum);
pthread_mutex_lock(&mutexsum);
sum += local_sum;
pthread_mutex_unlock(&mutexsum);
pthread_exit((void*) 0);
}

16

Báo cáo Bài tập lớn Hệ Điều Hành


Phần 2
Phần code

Trường Đại học Bách Khoa Thành phố Hồ Chí Minh

int main (int argc, char *argv[]) {
long i;
void *status;

pthread_t threads[NUMTHRDS];
pthread_attr_t attr;
/* Assign storage and initialize values */
a = (int*) malloc (NUMTHRDS*VECLEN*sizeof(int));
b = (int*) malloc (NUMTHRDS*VECLEN*sizeof(int));
for (i=0 ; i < VECLEN*NUMTHRDS ; i++) a[i] = b[i] = 1;
/* Initialize mutex variable */
pthread_mutex_init(&mutexsum, NULL);
/* Create threads as joinable, each of which will
execute the dot product
* routine. Their offset into the global vectors is
specified by passing
* the "i" argument in pthread_create().
*/
pthread_attr_init(&attr);
pthread_attr_setdetachstate(&attr,
PTHREAD_CREATE_JOINABLE);
for (i=0 ; i < NUMTHRDS ; i++)
pthread_create(&threads[i], &attr, dotprod, (void
*)i);
pthread_attr_destroy(&attr);
/* Wait on the other threads for final result */
for (i=0 ; i < NUMTHRDS ; i++)
pthread_join(threads[i], &status);
/* After joining, print out the results and cleanup */
printf ("Final Global Sum=%li\n",sum);
free (a);
free (b);
pthread_mutex_destroy(&mutexsum);
pthread_exit(NULL);

}

Báo cáo Bài tập lớn Hệ Điều Hành

17


Trường Đại học Bách Khoa Thành phố Hồ Chí Minh

Result bug6fix.c
#First
thread: 0 starting. start=0 end=99999
thread: 1 starting. start=100000 end=199999
thread: 0 done. Global sum now is=0
thread: 2 starting. start=200000 end=299999
thread: 1 done. Global sum now is=100000
thread: 3 starting. start=300000 end=399999
thread: 2 done. Global sum now is=200000
thread: 4 starting. start=400000 end=499999
thread: 4 done. Global sum now is=300000
thread: 5 starting. start=500000 end=599999
thread: 3 done. Global sum now is=400000
thread: 6 starting. start=600000 end=699999
thread: 5 done. Global sum now is=500000
thread: 6 done. Global sum now is=600000
thread: 7 starting. start=700000 end=799999
thread: 7 done. Global sum now is=700000
Final Global Sum=800000
#Second
thread: 0 starting. start=0 end=99999

thread: 0 done. Global sum now is=0
thread: 1 starting. start=100000 end=199999
thread: 2 starting. start=200000 end=299999
thread: 1 done. Global sum now is=100000
thread: 3 starting. start=300000 end=399999
thread: 2 done. Global sum now is=200000
thread: 4 starting. start=400000 end=499999
thread: 3 done. Global sum now is=300000
thread: 5 starting. start=500000 end=599999
thread: 4 done. Global sum now is=400000
thread: 6 starting. start=600000 end=699999
thread: 5 done. Global sum now is=500000
thread: 7 starting. start=700000 end=799999
thread: 6 done. Global sum now is=600000
thread: 7 done. Global sum now is=700000
Final Global Sum=800000

18

Báo cáo Bài tập lớn Hệ Điều Hành

Phần 2
Phần code


Phần 2
Phần code

2.4


Trường Đại học Bách Khoa Thành phố Hồ Chí Minh

Compile and run arrayloops.c

Arrayloops.c là 1 ví dụ khác của việc dùng mutex để cập nhật biến toàn cục sum.
Results:
Thread 0 doing iterations
Thread 2 doing iterations
Thread 3 doing iterations
Thread 1 doing iterations
Done. Sum= 4.999995e+11
Check Sum= 4.999995e+11

0 to 249999
500000 to 749999
750000 to 999999
250000 to 499999

Báo cáo Bài tập lớn Hệ Điều Hành

19



×