Panel użytkownika
Nazwa użytkownika:
Hasło:
Nie masz jeszcze konta?

[SFML] Selektor.wait(sf::seconds(?)) nie czeka

Ostatnio zmodyfikowano 2018-02-02 11:51
Autor Wiadomość
thief01
Temat założony przez niniejszego użytkownika
[SFML] Selektor.wait(sf::seconds(?)) nie czeka
» 2018-01-12 11:06:46
Ostatnio używałem selector.wait, jakieś pół roku temu~ selektor czekał dany czas czy będzie możliwość odebrania danych, jeśli nie było to program leciał dalej wykonywać kod, teraz jest tak że gdy użyje sel.wait(sf::seconds(1)) nie czeka ;/
jak kiedyś się bawiłem to była jakaś dolna granica przy sel.wait(sf::miliseconds(5)) ~ że coś się mu złego działo, ale nie pamiętam czy górna też, tak czy siak nie chce czekać ani chwili.

# Edit problem rozwiazany, trzeba ustawić by socket.setBlocking(flase);
# tylko ze kiedyś raczej działało bez tego jeśli ktoś chce dać swoja teorie co można zrobić to poproszę, zwłaszcza że w kursie SFML nie ma o tym
# mowy
P-168655
DejaVu
» 2018-01-14 21:00:16
Jeżeli nie działa tak jak chcesz to znaczy, że zrobili błąd w SFML-u lub Twoje biblioteki mają buga.
P-168732
jankowalski25
» 2018-01-14 22:25:09
Wszystkie gniazda w SFML są domyślnie blokujące. Jeśli mają się zachowywać inaczej, to należy zawsze jawnie napisać:
socket.setBlocking( false )
kiedyś raczej działało bez tego
Zapewne używałeś wtedy starszej wersji SFML, w której były takie błędy. W opisie zmian możesz przeczytać:
  • Fixed sf::TcpSocket::connect()'s switching from blocking to non-blocking mode on immediate connection success (#221)
  • Fixed non-blocking connection with a sf::TcpSocket on Windows
P-168739
DejaVu
» 2018-01-14 23:28:28
No ale po to masz parametr timeout, aby odblokowało go jeżeli upłynie podany czas i nie będzie danych.
P-168740
jankowalski25
» 2018-01-15 00:01:37
Tutaj sytuacja jest nieco inna.

nie chce czekać ani chwili
Czyli chodzi o samo sprawdzenie, czy jakieś gniazdo jest gotowe (bez czekania). Jednak podanie zera (tyle czasu chcemy czekać) nie rozwiąże problemu, ponieważ tutaj zero oznacza czekanie w nieskończoność.

» Kurs WinSock, C++Trochę zaawansowane techniki lekcja
Inne pola zainsteresowania: jeśli ustawisz pola w swojej strukturze struct timeval na 0, select() powróci natychmiast, efektywnie pobierając informacje o wszystkich deskryptorach plików w twoim zestawie. Jeśli ustawisz parametr timeout na NULL, funkcja nigdy nie powróci z powodu przeterminowania, a więc będzie czekała, dopóki nie odkryje, że przynajmniej jeden deskryptor pliku jest gotowy.
Problem w tym, że aktualna implementacja SFML wywołuje funkcję
select()
 wewnątrz metody
wait()
 tylko w ten drugi sposób. Kod z GitHuba:
C/C++
////////////////////////////////////////////////////////////
bool SocketSelector::wait( Time timeout )
{
    // Setup the timeout
    timeval time;
    time.tv_sec = static_cast < long >( timeout.asMicroseconds() / 1000000 );
    time.tv_usec = static_cast < long >( timeout.asMicroseconds() % 1000000 );
   
    // Initialize the set that will contain the sockets that are ready
    m_impl->socketsReady = m_impl->allSockets;
   
    // Wait until one of the sockets is ready for reading, or timeout is reached
    // The first parameter is ignored on Windows
    int count = select( m_impl->maxSocket + 1, & m_impl->socketsReady, NULL, NULL, timeout != Time::Zero ? & time: NULL );
   
    return count > 0;
}
P-168741
thief01
Temat założony przez niniejszego użytkownika
» 2018-01-15 11:20:44
Co do błędu nie wiem, wykluczałbym raczej błąd biblioteki bo używam tej samej wersji nie aktualizowanej ;D

Wiem że wszystkie gniazda są domyślnie blokujące. Napisałem o tym że jeśli przestawię żeby gniazda się nie blokowały to sf::wait czeka, ale to jest trochę bez sens, bo równie dobrze mogę wywoływać funkcje .receive co chwilę i dostanę te dane. W końcu a program będzie się wykonywał itp. Lub też mógłbym napisać swoją pętlę przez jaki czas ma się wykonywać i też by działało bez blokowania gniazda. A tak to jest tylko jeden if potrzebny i selektor, i sprawę załatwia.

Tak jak napisał DejaVu, że po odbytym czasie odblokowuje program, sel.wait() ... nie wchodzi do if'a jeśli gniazdo nie będzie gotowe do odbioru, przez co socket.receive nie blokuje programu, dopiero po ustawieniu setBlocking(false) potrafił przeczekać dany czas.

Hmm. A teraz jest zupełnie jak poprzednio przy utworzeniu nowego projektu, nie trzeba ustawiać setBlocking a działa sf::wait.
Nie zmieniałem nic w kompilatorze itd. jedynie nowy projekt utworzony(wcześniej też to był projekt ale większego znaczenia i tak to nie ma).
P-168753
jankowalski25
» 2018-01-15 17:14:08
używam tej samej wersji nie aktualizowanej
Czyli której? Najprościej chyba to sprawdzić przez
std::cout << SFML_VERSION_MAJOR << '.' << SFML_VERSION_MINOR;
 (jest jeszcze trzecia liczba w stałej
SFML_VERSION_PATCH
, ale nie dotyczy to starszych wersji).
P-168759
thief01
Temat założony przez niniejszego użytkownika
» 2018-01-30 19:16:04
jankowalski25 wersja 2.3
P-169139
« 1 » 2
  Strona 1 z 2 Następna strona