Synchronizacja wg. priorytetów

0

Witam,
potrzebuję czegoś w stylu standardowych sekcji krytycznych (win) czy rekursywnych mutexow (linux), lecz z priorytetami. Potrzebuję zsynchronizować operację w kilku wątkach wg. najważniejszych do najmniej ważnych, które korzystają z tym samych zasobów. W zwykłych sekcjach krytycznych w windowsie, gdy kilka wątków bije się o mutexa, to po jego zwolnieniu zupełnie przypadkowy wątek go zyskuje bez względu na jakiekolwiek czynniki. Ja potrzebuje, aby mutex był przekazywany wg. z góry ustalonych priorytetów.

Na całą aplikację tylko w 1 miejscu coś takiego muszę synchronizować, więc równie dobrze mogłaby to być własna klasa, która by tym zarządzała, lecz tu się pojawia problem z wydajnością. Musiałbym trzymać listę wszystkich 'bijących się' wątków i ją często przeszukiwać, co jest dość nieeleganckim rozwiązaniem. Myślałem o kombinowaniu z WaitForSingleObject i sygnałach, aby powiadomić wątek, że jest jego kolej, lecz tu się pojawia problem z odpowiednikami na Linuxie...

Stąd moje pytanie - czy windowsowe/linuxowe API zawiera jakieś metody, aby uzyskać to o czym mówię? Jeżeli nie, to jakie byłyby linuxowe odpowiedniki poniższych windowsowych funkcji?

  typedef HANDLE API_SIGNALVAR;
  #define API_SIGNALVAR_INIT(a) a =  CreateEvent(NULL,true,false,"NULL")
  #define API_SIGNALVAR_RELEASE(a)   CloseHandle(a)
  #define API_SIGNALVAR_SIGNAL(a)    SetEvent(a)
  #define API_SIGNALVAR_RESET(a)     ResetEvent(a)
  #define API_SIGNALVAR_WAIT(a)      WaitForSingleObject(a, INFINITE)

Z góry dzięki za pomoc

0

To co masz powyżej to zdarzenia czyli właściwie coś podobnego do muteksa/sekcji krytycznej, równie dobrze mógłbyś ich użyć.

Nie widzę nic złego w liście bijących się wątków. Dodawaj je na listę w odpowiednim miejscu zgodnie z priorytetem tak aby brany był zawsze wątek z początku listy. Niech każdy wątek posiada swój muteks początkowo przejęty przez manager wątków. Kiedy nadejdzie jego kolej zwalniasz jego muteks i pozwalasz przejąć go wątkowi. Muteks możesz przekazać z powrotem managerowi od razu po przejęciu przez wątek. Kiedy wątek kończy prace niech zwlaniany będzie muteks kolejnego czekającego wątku pierwszego w kolejce. Sam manager również będzie potrzebować własny muteks aby nie krzyżowały się dodawania do/ściąganie z kolejki.

I teraz jeśli poziomów priorytetu jest niewiele to proponuje zrobić po jednej liście na każdy poziom. Wtedy dodanie wątku do listy to O(1), a zdjęcie O(p) gdzie 'p' to ilość poziomów.

Jeśli poziomy są jednak zróżnicowane to zrób sobie drzewko binarne sortowane wg. priorytetu. Dodawanie wątku do drzewa to O(log(n)) gdzie 'n' to ilość wątków, a zdejmowanie O(1).

Pomocne może być pthreads na Windows'a coby nie robić dwóch wersji kodu na dwa systemy.

1 użytkowników online, w tym zalogowanych: 0, gości: 1