Российский производитель и разработчик сертифицированного измерительного оборудования с 1987 года


E14-140M: Потоковый асинхронный сбор данных

Вы не вошли.

 Поиск | Регистрация | Вход 

Дмитрий
29.05.2012 18:49:50
#1

Гость

E14-140M: Потоковый асинхронный сбор данных

В файлах, поставляемых с библиотекой Lusbapi, есть пример - консольная программа ReadData. Привожу из нее кусок кода потока, осуществляющего сбор данных и запись их в файл:

    // делаем предварительный запрос на ввод данных
    RequestNumber = 0x0;
    if(!pModule->ReadData(&IoReq[RequestNumber])) { CloseHandle(ReadEvent[0]); CloseHandle(ReadEvent[1]); ReadThreadErrorNumber = 0x2; IsReadThreadComplete = true; return 0x0; }

    // запустим АЦП
    if(pModule->START_ADC())
    {
        // цикл сбора данных
        for(i = 0x1; i < NDataBlock; i++)
        {
            // сделаем запрос на очередную порции данных
            RequestNumber ^= 0x1;
            if(!pModule->ReadData(&IoReq[RequestNumber])) { ReadThreadErrorNumber = 0x2; break; }

            // ждём завершения операции сбора предыдущей порции данных
            if(WaitForSingleObject(ReadEvent[RequestNumber^0x1], IoReq[RequestNumber^0x1].TimeOut) == WAIT_TIMEOUT) { ReadThreadErrorNumber = 0x3; break; }

            // запишем полученную порцию данных в файл
            if(!WriteFile(    hFile,                                                    // handle to file to write to
                                IoReq[RequestNumber^0x1].Buffer,                    // pointer to data to write to file
                                2*DataStep,                                                 // number of bytes to write
                                &FileBytesWritten,                                    // pointer to number of bytes written
                               NULL                                                          // pointer to structure needed for overlapped I/O
                               )) { ReadThreadErrorNumber = 0x4; break; }

            if(ReadThreadErrorNumber) break;
            else if(kbhit()) { ReadThreadErrorNumber = 0x5; break; }
            else Sleep(20);
            Counter++;
        }

        // последняя порция данных
        if(!ReadThreadErrorNumber)
        {
            RequestNumber ^= 0x1;
            // ждём окончания операции сбора последней порции данных
            if(WaitForSingleObject(ReadEvent[RequestNumber^0x1], IoReq[RequestNumber^0x1].TimeOut) == WAIT_TIMEOUT) ReadThreadErrorNumber = 0x3;
            // запишем последнюю порцию данных в файл
            if(!WriteFile(    hFile,                                                    // handle to file to write to
                                IoReq[RequestNumber^0x1].Buffer,                    // pointer to data to write to file
                                2*DataStep,                                                 // number of bytes to write
                                &FileBytesWritten,                                    // pointer to number of bytes written
                               NULL                                                          // pointer to structure needed for overlapped I/O
                               )) ReadThreadErrorNumber = 0x4;
            Counter++;
        }
    }

Видно, что после приема каждой порции данных в файл записывается порция данных размером 2*DataStep, но
2*DataStep - это полный размер буфера для сбора данных. Таким образом, в одном случае мы записываем в файл весь буфер, а в другом захватываем какую то информацию, находящуюся за пределами буфера, вместо того, чтобы каждый раз записывать то первую, то вторую половину буфера. Действительно ли здесь ошибка, или я что то не понимаю?

Ну и еще вопрос - мне нужно в течении нескольких минут собирать данные с АЦП с постоянной частотой выборки, при этом не должно происходить потери выборок или их дублирования ( результаты в дальнейшем нужно будет проинтегрировать по времени с дискретом, соответствующим частоте выборок АЦП ). Приведенная выше программа позволяет обеспечить эти требования?

30.05.2012 11:50:09
#2

Сотрудник "Л Кард"
Здесь с 24.04.2014
Сообщений: 1,535

Re: E14-140M: Потоковый асинхронный сбор данных

1. Для WinAPI функции WriteFile() размер записываемого блока данных задаётся в байтах, т.е. 2*DataStep байт. Там же даже в комментарии про это указано: "number of bytes to write". Полный же размер буфера данных AdcBuffer равен 2*DataStep*sizeof(SHORT) = 4*DataStep байт. Так что запись идёт строго половинками буфера данных.
2. Да.

Дмитрий
30.05.2012 15:34:40
#3

Гость

Re: E14-140M: Потоковый асинхронный сбор данных

Спасибо большое

31.05.2012 11:05:29
#4

Сотрудник "Л Кард"
Здесь с 18.04.2014
Сообщений: 810

Re: E14-140M: Потоковый асинхронный сбор данных

Можете также почитать примеры из http://www.lcard.ru/download/e140-console-test.zip

Контакты

Адрес: 117105, Москва, Варшавское шоссе, д. 5, корп. 4

Многоканальный телефон:+7 (495) 785-95-25

Письма и запросы: lcard@lcard.ru
Отдел продаж: sale@lcard.ru
Техническая поддержка: support@lcard.ru

Время работы: с 9-00 до 19-00 мск