опубликован 06-12-2001 04:16 MSK
Привет шумной компании и персонально zlelikГоспода, я работал с железом еще с 198х года.
Так вот что я вам могу сказать. Давайте вспомним,
кто первый сказал: "55 мс". И откуда взялась эта
странная цифра.
Давнам давно, Когда Гейтс был молодой и
(относительно) бедный, знаменитый Голубой Гигант
создал уникальную (в смысле -- бездарную) IBM PC,
которую вскоре переделали в IBM PC/XT. PC-ишка
создавалась в жуткой спешке и не очень продвинутыми
специалистами (иначе бы мы сейчас не маялись с
нехваткой прерываний и др. прелестями, доставшимися
нам в наследство).
Итак, В PC-шке была одна мелкосхема -- таймер i8253.
Он имел три канала:
нулевой -- вырабатывал тики для часов,
первый -- отвечал за регенерацию памяти,
второй -- противно пищал в динамик.
Все три канала таймера были запитаны от единственного
генератора. Кварцевый генератор работал на частоте
14,31818 Мгц.
Затем эту частоту делили на три (= 4.77 МГц) и
подавали на тактовый вход микропроцессора (i8088).
Потом ее еще раз делили на 4 (= 1.19318 МГц) и
подавали на входы всех трех таймеров.
Таймер устроен очень просто. Можно считать, что это
три независимых 16-разрядных регистра (порта). В них
записывается коэффициент деления. Таким образом,
в нулевой канал записывали число 0х0000, в первый --
0х0012, во второй -- 0х0528.
После инициализации канала он начинал декрементироваться
и по достижению нуля на выходе канала появлялся
коротенький импульс. После чего канал (уже самостоятельно,
без вмешательства программ) вновь инициализировался и
т.о. весь процесс шел по кругу.
Не трудно догадаться, что нулевой канал вырабатывал
импульсы с частотой равной
1.19318 МГц / 65536 = 19.5 Гц или каждые 55 мс.
А вот у первого канала на выходе стоял еще один счетный
триггер, который делил частоту на два. Таким образом,
получались почти 15 микросекундные импульсы.
(Я не привожу расчеты.)
Так вот, изюминка состоит в том, что программы могут не
только инициализировать эти каналы, но и считывать их
текущее состояние. Другими словами, если мы читаем из
нулевого канала его состояние, потом произведем
некоторые "действия", а затем еще раз считаем состояние
канала, то вычислив разницу можно легко посчитать
длительность этих "действий" -- частоту декремента канала
мы ведь знаем -- 1.19 МГц. Здесь надо оговориться, что
длительность измеряемых "действий" не должна превышать
55 мс.
Все было бы хорошо, если б не прогресс. На современных
компьютерах ставятся совершенно другие таймеры, которые
работают с совершенно другими частотами. Но к счастью,
в С++ нет необходимости лазить по портам, каналам таймера
и прочим бестиям. За нас это делают библиотеки.
Я советую Вам, милейший, посмотреть функции
QueryPerformanceFrequency
QueryPerformanceCounter
, которые как раз и работают с нулевым каналом таймера.
И последнее. Мой предыдущий опыт говорит о том, что если
Вы хотите использовать компьютер в качестве машины для
управления оборудованием и обработки данных, то это
можно делать и на Виндах. Но как только Вы попытаетесь
применять его в качестве прецезионного инструмента, то
лучше работать из-под ДОС, а еще лучше из-под UNIX.
Можно рассмотреть и другой вариант -- в Вашем случае
LPT не _генерирует_ частоту, а _управляет_ частотой
внешнего генератора. Это самый лучший вариант, не смотря
на то, что требует внешнего оборудования. Винды -- это не
коттедж с тремя туалетами для двоих. Винды -- это
коммуналка, где "на 38 комнаток всего одна уборная".
Проблематично какому-то конкретному человечку
периодически справлять свои нужды строго по времени.
Не для таких задач Билл Гейтс создавал "Окна", Вы
онемного шиблись в выборе инструмента для решения своих
задач.
С уважением, Александр Жевак