Модераторы: feodorv, GremlinProg, xvr, Fixin
  

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> Ожидаемый таймер, вопрос по признаку освобождения 
:(
    Опции темы
IGanja
Дата 8.6.2012, 15:37 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 23
Регистрация: 19.7.2007

Репутация: нет
Всего: нет



Таймер срабатывает каждую секунду. Выполняется итерация цикла и оставшееся время от секунды жду освобождения таймера. Все хорошо пока не случается превышения секунды в работе кода итерации. По моим представлениям после превышения, например при работе 2,8 секунды на строчке WaitForSingleObject(hTimer, INFINITE);  программа должна дожидаться начала следующий секунды, ведь таймер занят. Вреальности же проскакивает коротенькая итерация на 0,2 секунды и далее таймер входит в свою требуемую частоту. Может кто ни будь знает почему так происходит? У Рихтера на этот счет ничего нет.

Код

    while(!stop)
    {
        QueryPerformanceCounter(&Start);

                count++;
        leg += 1;
        leg %= 16;
        printf("InnerLeg %d\n",leg);

        if(count == 7)
        {
            while(Time<2.8f)
            {
                QueryPerformanceCounter(&Stop1);
                Time = (double)(Stop1.QuadPart - Start.QuadPart)/(double)Freq.QuadPart; 
            }
            printf(" %f\n",Time);
        }
        else
        {
            QueryPerformanceCounter(&Stop1);
            Time = (double)(Stop1.QuadPart - Start.QuadPart)/(double)Freq.QuadPart; 
            printf(" %f\n",Time);
        }

        // жду следующего лега
        WaitForSingleObject(hTimer, INFINITE); 

        QueryPerformanceCounter(&Stop2);
        Time = (double)(Stop2.QuadPart - Start.QuadPart)/(double)Freq.QuadPart; 
        printf(" %f\n",Time);
    }


Добавлено через 10 минут и 1 секунду
вот полностью рабочая прога

Код

#define _WIN32_WINNT 0x0501
#include <windows.h>
#include <conio.h>

float FREQUENCY = 1    ; //Гц
int leg = 0; //позиция в 16 ричной решетке

int main(void)
{
    int i=0,j=0;
    int count=0;
    char stop =0;
    char oneIter =0;
    LARGE_INTEGER Start, Stop1, Stop2, Freq;
    LARGE_INTEGER firstStart;
    const int unitPerSecond = 10000000; //10 миллионов интервалов по 100 нано секунд = 1 секунд
    int freq_ms = 1000/FREQUENCY; //msec
    DWORD dwThreadId; 
    HANDLE hTimer = NULL;
    double Time=0;

    SetPriorityClass(GetCurrentProcess(),HIGH_PRIORITY_CLASS); // установка приоритета процесса

    // создание и настройка таймера
    firstStart.QuadPart = -(unitPerSecond/FREQUENCY); // первое срабатывание таймера
    hTimer = CreateWaitableTimer(NULL, FALSE, NULL); // таймер с автосбросом
    SetWaitableTimer(hTimer, &firstStart, freq_ms, NULL, NULL, FALSE); // настройка

    QueryPerformanceFrequency(&Freq); // tick/sec

    while(!stop)
    {
        QueryPerformanceCounter(&Start);

        count++;

        leg += 1;
        leg %= 16;
        printf("InnerLeg %d\n",leg);

        if(count == 7)
        {
            while(Time<2.8f)
            {
                QueryPerformanceCounter(&Stop1);
                Time = (double)(Stop1.QuadPart - Start.QuadPart)/(double)Freq.QuadPart; //ms;
            }
            printf(" %f\n",Time);
        }
        else
        {
            QueryPerformanceCounter(&Stop1);
            Time = (double)(Stop1.QuadPart - Start.QuadPart)/(double)Freq.QuadPart; //ms;
            printf(" %f\n",Time);
        }

        // жду следующего лега
        WaitForSingleObject(hTimer, INFINITE); 

        QueryPerformanceCounter(&Stop2);
        Time = (double)(Stop2.QuadPart - Start.QuadPart)/(double)Freq.QuadPart; //ms;
        printf(" %f\n",Time);
    }


    printf( "game over\n" );
    getch();

    return 0;
}

PM MAIL   Вверх
feodorv
Дата 8.6.2012, 21:07 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Комодератор
Сообщений: 2214
Регистрация: 30.7.2011

Репутация: 9
Всего: 45



Цитата(IGanja @  8.6.2012,  16:37 Найти цитируемый пост)
программа должна дожидаться начала следующий секунды, ведь таймер занят.

Почему он занят? Потому что с автосбросом? Но ведь автосброс сработает только в момент вызова WaitForSingleObject. Так сделано специально, чтобы не потерялось пропущенное срабатывание таймера. Оно и не теряется.

Поскольку Вы ожидаете только срабатывание таймера, то можно его просто сэмулировать через GetTickCount и Sleep.
А можно в существующей схеме просто проверять, что пропущен тик таймера, и уже дожидаться следующего тика.


--------------------
Напильник, велосипед, грабли и костыли - основные инструменты программиста...
PM MAIL   Вверх
IGanja
Дата 9.6.2012, 13:53 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 23
Регистрация: 19.7.2007

Репутация: нет
Всего: нет



feodorv, то есть, таймер через секунду освобождается и снова перейдет в занятое состояние только после вызова WaitForSingleObject? Тогда все понятно. Спасибо.

Я думал что он каждую секунду освобождается на такт и снова переходит в занятое состояние и если я не находился в ожидании, то пропускал этот сигнал.

Это сообщение отредактировал(а) IGanja - 9.6.2012, 13:55
PM MAIL   Вверх
feodorv
Дата 9.6.2012, 19:34 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Комодератор
Сообщений: 2214
Регистрация: 30.7.2011

Репутация: 9
Всего: 45



Цитата(IGanja @  9.6.2012,  14:53 Найти цитируемый пост)
feodorv, то есть, таймер через секунду освобождается и снова перейдет в занятое состояние только после вызова WaitForSingleObject? 

 smile 


--------------------
Напильник, велосипед, грабли и костыли - основные инструменты программиста...
PM MAIL   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
Правила форума "C/C++: Системное программирование и WinAPI"
Fixin
GremlinProg
xvr
feodorv
  • Большое количество информации и примеров с использованием функций WinAPI можно найти в MSDN
  • Описание сообщений, уведомлений и примеров с использованием компонент WinAPI (BUTTON, EDIT, STATIC, и т.п.), можно найти в MSDN Control Library
  • Непосредственно, перед созданием новой темы, проверьте заголовок и удостоверьтесь, что он отражает суть обсуждения.
  • После заполнения поля "Название темы", обратите внимание на наличие и содержание панели "А здесь смотрели?", возможно Ваш вопрос уже был решен.
  • Приводите часть кода, в которой предположительно находится проблема или ошибка.
  • Если указываете код, пользуйтесь тегами [code][/code], или их кнопочными аналогами.
  • Если вопрос решен, воспользуйтесь соответствующей ссылкой, расположенной напротив названия темы.
  • Один топик - один вопрос!
  • Перед тем как создать тему - прочтите это .

На данный раздел распространяются Правила форума и Правила раздела С++:Общие вопросы .


Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Chipset, Step, Fixin, GremlinProg, xvr. feodorv.

 
1 Пользователей читают эту тему (1 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | C/C++: Системное программирование и WinAPI | Следующая тема »


 




[ Время генерации скрипта: 0.0708 ]   [ Использовано запросов: 21 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.