Skip to content

Commit

Permalink
Merge pull request #2 from sfaqer/feature/multithreadingSemaphore
Browse files Browse the repository at this point in the history
Многопоточная работа семафора
  • Loading branch information
nixel2007 authored Apr 30, 2021
2 parents 456ee7e + d583882 commit b1eda7f
Show file tree
Hide file tree
Showing 3 changed files with 76 additions and 2 deletions.
4 changes: 2 additions & 2 deletions packagedef
Original file line number Diff line number Diff line change
Expand Up @@ -5,13 +5,13 @@


Описание.Имя("semaphore")
.Версия("1.0.2")
.Версия("1.1.0")
.Автор("Nikita Gryzlov")
.АдресАвтора("nixel2007@gmail.com")
.Описание("Библиотека для организации ""семафора"" - инструмента ограничения одновременного выполнения участков кода.")
.ОпределяетКласс("Семафор", "src/Классы/Семафор.os")
.ОпределяетМодуль("Семафоры", "src/Модули/Семафоры.os")
.ВерсияСреды("1.0.18")
.ВерсияСреды("1.6.0")
.ВключитьФайл("src")
.ВключитьФайл("tests")
;
7 changes: 7 additions & 0 deletions src/Классы/Семафор.os
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
Перем мСчетчик;
Перем СтандартныйРазмерПаузы;
Перем БлокировкаРесурса;

// Конструктор.
//
Expand All @@ -14,7 +15,10 @@
Иначе
мСчетчик = Счетчик;
КонецЕсли;

СтандартныйРазмерПаузы = 10;
БлокировкаРесурса = Новый БлокировкаРесурса(ЭтотОбъект);

КонецПроцедуры

// Осуществить захват семафора.
Expand All @@ -28,9 +32,11 @@
Процедура Захватить(ТаймаутОжидания = 0) Экспорт
ВремяНачала = ТекущаяУниверсальнаяДатаВМиллисекундах();
Пока Истина Цикл
БлокировкаРесурса.Заблокировать();
мСчетчик = мСчетчик - 1;
Если мСчетчик < 0 Тогда
мСчетчик = мСчетчик + 1;
БлокировкаРесурса.Разблокировать();
Если ЗначениеЗаполнено(ТаймаутОжидания) Тогда
ТекущееВремя = ТекущаяУниверсальнаяДатаВМиллисекундах();
Если (ВремяНачала + ТаймаутОжидания) < ТекущееВремя Тогда
Expand All @@ -39,6 +45,7 @@
КонецЕсли;
Приостановить(СтандартныйРазмерПаузы);
Иначе
БлокировкаРесурса.Разблокировать();
Прервать;
КонецЕсли;
КонецЦикла;
Expand Down
67 changes: 67 additions & 0 deletions tests/Семафор.os
Original file line number Diff line number Diff line change
Expand Up @@ -33,4 +33,71 @@

Семафор1.Освободить();
Семафор2.Освободить();

КонецПроцедуры

&Тест
Процедура СемафорыСОдинаковымКлючомБлокируютсяМногопоточно() Экспорт

Параметры = Новый Массив(1);
Параметры[0] = Ложь;

ФоновыеЗадания.Выполнить(ЭтотОбъект, "СемафорыСОдинаковымКлючомБлокируютсяВМногопочтономРежиме", Параметры);

Параметры[0] = Истина;

ФоновыеЗадания.Выполнить(ЭтотОбъект, "СемафорыСОдинаковымКлючомБлокируютсяВМногопочтономРежиме", Параметры);
ФоновыеЗадания.Выполнить(ЭтотОбъект, "СемафорыСОдинаковымКлючомБлокируютсяВМногопочтономРежиме", Параметры);
ФоновыеЗадания.Выполнить(ЭтотОбъект, "СемафорыСОдинаковымКлючомБлокируютсяВМногопочтономРежиме", Параметры);
ФоновыеЗадания.Выполнить(ЭтотОбъект, "СемафорыСОдинаковымКлючомБлокируютсяВМногопочтономРежиме", Параметры);
ФоновыеЗадания.Выполнить(ЭтотОбъект, "СемафорыСОдинаковымКлючомБлокируютсяВМногопочтономРежиме", Параметры);

Попытка
ФоновыеЗадания.ОжидатьЗавершенияЗадач();
Исключение

МассивЗаданий = ИнформацияОбОшибке().Параметры;

Если МассивЗаданий <> Неопределено Тогда

ШаблонТекстаОшибки =
"Ошибки при многопоточной работе семафора:
|%1";

Для Каждого Задание Из МассивЗаданий Цикл

МассивОшибок = Новый Массив();
МассивОшибок.Добавить(Задание.ИнформацияОбОшибке.ПодробноеОписаниеОшибки());

КонецЦикла;

ВызватьИсключение СтрШаблон(
ШаблонТекстаОшибки,
СтрСоединить(МассивОшибок, Символы.ПС)
);

КонецЕсли;
КонецПопытки;

КонецПроцедуры

Процедура СемафорыСОдинаковымКлючомБлокируютсяВМногопочтономРежиме(ДолженВызватьИсключение) Экспорт

Семафор = Семафоры.Получить("тестовый семафор");

Если ДолженВызватьИсключение Тогда

ПараметрыМетода = Новый Массив;
ПараметрыМетода.Добавить(1000);

Ожидаем.Что(Семафор).Метод("Захватить", ПараметрыМетода).ВыбрасываетИсключение("Истекло время ожидания");

Иначе

Семафор.Захватить();
Приостановить(3000);
Семафор.Освободить();

КонецЕсли;

КонецПроцедуры

0 comments on commit b1eda7f

Please sign in to comment.