Інформація про навчальний заклад

ВУЗ:
Національний університет Львівська політехніка
Інститут:
Не вказано
Факультет:
КН
Кафедра:
Кафедра ЕОМ

Інформація про роботу

Рік:
2013
Тип роботи:
Звіт до лабораторної роботи
Предмет:
Системне програмне забезпечення

Частина тексту файла (без зображень, графіків і формул):

Міністерство освіти і науки України Національний університет „Львівська політехніка” Кафедра ЕОМ Звіт до лабораторної роботи № 3-4 з дисципліни " Системне програмне забезпечення" Варіант№9 Тема: «Взаємодія між потоками» Мета: Засвоїти поняття паралельного виконання «потоків» та освоїти засоби їх синхронізації. Здобути навики синхронізації «потоків» при обробці спільних даних та доступу до ресурсів в операційній системі Windows. Згідно варіанту було розроблено програму в середовищі Visual Studio, що демонструє використання об’єктів синхронізації заданого числа потоків. Системний виклик Варіант   9  Critical Section 3  Mutex   Semaphores 2   Лістинг програми: Використання Semaphore : #include "windows.h" #include "iostream" #include "process.h" using namespace std; HANDLE hSemaphore; LONG cMax = 2; void Test1(void *); void Test2(void *); void Test3(void *); void main() { hSemaphore = CreateSemaphore( NULL, cMax, cMax, NULL ); if (!hSemaphore == NULL) { if (_beginthread(Test1,1024,NULL)==-1) cout << "Error begin thread " << endl; if (_beginthread(Test2,1024,NULL)==-1) cout << "Error begin thread " << endl; if (_beginthread(Test3,1024,NULL)==-1) cout << "Error begin thread " << endl; Sleep(1000); CloseHandle(hSemaphore); } else cout << "error create semaphore" << endl; } void Test1(void *) { cout << "Test1 Running" << endl; DWORD dwWaitResult = 1; while(dwWaitResult!=WAIT_OBJECT_0) { dwWaitResult = WaitForSingleObject( hSemaphore, // вказівник на семафор 1 // інтервал очікування ); cout << "Test 1 TIMEOUT" << endl; } Sleep(1000); if (ReleaseSemaphore( hSemaphore, 1, // зміна лічильника на 1 NULL) ) cout << " ReleaseSemaphore Ok Test1" << endl; _endthread(); } void Test2(void *) { cout << "Test2 Running" << endl; DWORD dwWaitResult = 0; while(dwWaitResult!=WAIT_OBJECT_0) { dwWaitResult = WaitForSingleObject(hSemaphore,1); cout << "Test 2 TIMEOUT" << endl; } Sleep(1000); if (ReleaseSemaphore(hSemaphore,1,NULL)) cout << " ReleaseSemaphore Ok Test2" << endl; _endthread(); } void Test3(void *) { cout << "Test2 Running" << endl; DWORD dwWaitResult = 1; while(dwWaitResult!=WAIT_OBJECT_0) { dwWaitResult = WaitForSingleObject(hSemaphore,1); cout << "Test 3 TIMEOUT" << endl; } if (ReleaseSemaphore(hSemaphore,1,NULL)) cout << " ReleaseSemaphore Ok Test3" << endl; _endthread(); } Використання CriticalSection( ) #include<windows.h> #include<windowsx.h> #include<process.h> #include <time.h> #include<iostream> #include<conio.h> using namespace std; #define DATA_SIZE 256 typedef struct msg_block_tag { /* Message block */ volatile DWORD f_ready, f_stop; /* ready state flag, stop flag */ volatile DWORD sequence; /* Message block sequence number */ volatile DWORD nCons, nLost; //time_t timestamp; CRITICAL_SECTION mguard; /* Guard the message block structure */ DWORD checksum; /* Message contents checksum */ DWORD data[DATA_SIZE]; /* Message Contents */ } MSG_BLOCK; /* One of the following conditions holds for the message block */ /* 1) !f_ready || f_stop */ /* nothing is assured about the data OR */ /* 2) f_ready && data is valid */ /* && checksum and timestamp are valid */ /* Also, at all times, 0 <= nLost + nCons <= sequence */ /* Single message block, ready to fill with a new message */ MSG_BLOCK mblock = { 0, 0, 0, 0, 0 }; static unsigned __stdcall produce (void *); static unsigned __stdcall produce1 (void *); static unsigned __stdcall consume (void *); void MessageFill (MSG_BLOCK *); void MessageDisplay (MSG_BLOCK *); int main () { DWORD Status; UINT ThId; HANDLE produce_h, consume_h, produce1_h; /* Initialize the message block CRITICAL SECTION */ InitializeCriticalSection (&mblock.mguard); /* Create the two threads */ produce_h = (HANDLE)_beginthreadex (NULL, 0, produce, NULL, 0, &ThId); if (produce_h == NULL) cout<<"Cannot create producer thread"<<endl; consume_h = (HANDLE)_beginthreadex (NULL, 0, consume, NULL, 0, &ThId); if (consume_h == NULL) cout<<"Cannot create consume thread"<<endl; produce1_h = (HANDLE)_beginthreadex (NULL, 0, produce1, NULL, 0, &ThId); if (produce1_h == NULL) cout<<"Cannot create producer thread#1"<<endl; /* Wait for the producer and consumer to complete */ Status = WaitForSingleObject (consume_h, INFINITE); if (Status != WAIT_OBJECT_0) cout<<"Failed waiting for consumer thread"<<endl; Status = WaitForSingleObject (produce_h, INFINITE); if (Status != WAIT_OBJECT_0) cout<<"Failed waiting for produser threads"<<endl; Status = WaitForSingleObject (produce1_h, INFINITE); if (Status != WAIT_OBJECT_0) cout<<"Failed waiting for produser thread#1"<<endl; DeleteCriticalSection (&mblock.mguard); cout<<"Producer and consumer threads have terminated\n"; cout<<"Messages produced: "<<mblock.sequence<<" Consumed: "<<mblock.nCons<<" Known Lost: "<<mblock.nLost<<" "<<endl; _getch(); return 0; } unsigned __stdcall produce (void *arg) /* Producer thread - Create new messages at random intervals */ { srand ((DWORD)time(NULL)); /* Seed the random # generator */ while (!mblock.f_stop) { /* Random Delay */ Sleep(rand()/100); /* Get the buffer, fill it */ EnterCriticalSection (&mblock.mguard); __try { if (!mblock.f_stop) { mblock.f_ready = 0; MessageFill (&mblock); mblock.f_ready = 1; mblock.sequence++; } } __finally { LeaveCriticalSection (&mblock.mguard); } } return 0; } unsigned __stdcall produce1 (void *arg) /* Producer thread - Create new messages at random intervals */ { srand ((DWORD)time(NULL)); /* Seed the random # generator */ while (!mblock.f_stop) { /* Random Delay */ Sleep(rand()/100); /* Get the buffer, fill it */ EnterCriticalSection (&mblock.mguard); __try { if (!mblock.f_stop) { mblock.f_ready = 0; MessageFill (&mblock); mblock.f_ready = 1; mblock.sequence++; } } __finally { LeaveCriticalSection (&mblock.mguard); } } return 0; } unsigned __stdcall consume (void *arg) { DWORD ShutDown = 0; CHAR command; /* Consume the NEXT message when prompted by the user */ while (!ShutDown) { /* This is the only thread accessing stdin, stdout */ cout<<endl<<"**Enter 'c' for consume; 's' to stop: "<<endl; cin>>command;//>>extra; if (command == 's') { EnterCriticalSection (&mblock.mguard); ShutDown = mblock.f_stop = 1; LeaveCriticalSection (&mblock.mguard); } else if (command == 'c') { /* Get a new buffer to consume */ EnterCriticalSection (&mblock.mguard); __try { if (mblock.f_ready == 0) cout<<"No new messages. Try again later"<<endl; else { MessageDisplay (&mblock); mblock.nCons++; mblock.nLost = mblock.sequence - mblock.nCons; mblock.f_ready = 0; /* No new messages are ready */ } } __finally { LeaveCriticalSection (&mblock.mguard); } } else { cout<<"Illegal command. Try again."<<endl; } } return 0; } void MessageFill (MSG_BLOCK *mblock) { /* Fill the message buffer, and include checksum and timestamp */ /* This function is called from the producer thread while it */ /* owns the message block mutex */ DWORD i; mblock->checksum = 0; for (i = 0; i < DATA_SIZE; i++) { mblock->data[i] = rand(); mblock->checksum ^= mblock->data[i]; } //mblock->timestamp = time(NULL); return; } void MessageDisplay (MSG_BLOCK *mblock) { /* Display message buffer, timestamp, and validate checksum */ /* This function is called from the consumer thread while it */ /* owns the message block mutex */ DWORD i, tcheck = 0; for (i = 0; i < DATA_SIZE; i++) tcheck ^= mblock->data[i]; cout<<endl<<"Message number "<<mblock->sequence<<" generated at: "<< GetTickCount()/*(&(mblock->timestamp))*/<<endl; cout<<"First and last entries: "<<mblock->data[0]<<" "<<mblock->data[DATA_SIZE-1]<<endl; if (tcheck == mblock->checksum) cout<<"GOOD ->Checksum was validated."<<endl; else cout<<"BAD ->Checksum failed. message was corrupted."<<endl; return; } Результат виконання програми: / / Висновок: на даній лабораторній роботі я дослідив синхронізацію «потоків» при обробці спільних даних та доступу до ресурсів в операційній системі Windows.
Антиботан аватар за замовчуванням

17.03.2013 13:20

Коментарі

Ви не можете залишити коментар. Для цього, будь ласка, увійдіть або зареєструйтесь.

Ділись своїми роботами та отримуй миттєві бонуси!

Нічого не вибрано
0%

Оголошення від адміністратора

Антиботан аватар за замовчуванням

Подякувати Студентському архіву довільною сумою

Admin

26.02.2023 12:38

Дякуємо, що користуєтесь нашим архівом!