Ещё один тахометр
Анатолий Сергиенко
Редкий радиолюбитель, владелец автомобиля, не полезет в него с паяльником. Вот и размножаются сотнями любительские схемы разных блоков зажигания, октан-корректоров, тахометров, зарядных устройств, охранной сигнализации. Некоторые идут дальше — и появляются бортовые компьютеры, телевизионные зеркала заднего обзора и даже устройства распознавания знаков дорожного движения.
В данной статье предлагается ещё один тахометр. Тахометр — это измеритель числа оборотов двигателя за единицу времени. Входные данные Fx поступают с датчика числа оборотов, которым чаще всего является прерыватель системы зажигания или емкостной датчик импульсов напряжения в свечных проводах. Результат измерения получают путем интегрирования импульсов одинаковой длительности в аналоговой схеме или простым подсчетом импульсов за единицу времени в частотомере.
Но частота Fx слишком низкая для измерения с точностью до 3-5 десятичных цифр в реальном масштабе времени. Измерение частоты на выходе генератора переменного тока бортовой сети не решает проблему кардинально. Кроме того, ещё необходима коррекция результата измерения путем умножения на масштабный коэффициент, т.е.Y=M*Fx. Выход в том, что необходимо измерять период Тх сигнала, а измеряемую величину находить как результат деления Y=M/Tx.
Для вычисления Y=M/Tx существует очень простой и удобный алгоритм. Если из большеразрядного целого М вычитать малоразрядное Тх до тех пор, пока М не приблизится к нулю, то число вычитаний будет равно искомому Y. При этом счетчик числа этих вычитаний можно выполнить по любому основанию, например, по основанию 2, 10, в кодах 7-сегментных индикаторов, в унитарном коде, т.е. коде бегущей единицы, в коде отображения столбика единиц и т.п.
Недостатком алгоритма является его высокая алгоритмическая сложность, т.е. то, что для получения 3-5 — разрядного десятичного результата необходимо выполнить до 1 -100 тыс. вычитаний и столько же сложений с единицей на одно измерение или 0.1 — 100 млн. операций в секунду, в зависимости от быстродействия измерений. Это довольно сложно для микроконтроллера, зато совсем нетрудно для ПЛИС и даже CPLD.
Здесь приводится простая модель тахометра. Модель представлена в Приложении. Тахометр работает периодически с последовательным повторением четырех фаз. В фазе Waiting ожидается фронт входного сигнала, в фазе Measure измеряется период сигнала Period как число тактов синхросерии между двумя соседними фронтами входного сигнала. При этом период меньше measureMIN не фиксируется, так как в нем могут быть импульсы дребезга контактов. В фазе Calculate вычисляется частота F= Masstab/Period . Эта частота F вычисляется в виде кода столбика единиц, который пригоден для непосредственного вывода на линейный светодиодный индикатор. В фазе Display ничего не происходит, кроме вывода результатов измерения.
Частота синхросерии равна 6,8 кГц. Она может быть подстроена выбором констант Masstab, measure_T, а также повышена при использовании дополнительного делителя частоты.
Такой тахометр помещается в любой корпус ПЛИС или CPLD . Он без особенной оптимизации занимает 125 LUT и 71 триггер. Так что весь прибор занимает один корпус CPLD XC9572 и генератор синхроимпульсов, не считая индикатора. Кстати, выходного тока ПЛИС или CPLD достаточно для прямого подключения светодиодов.
Если датчиком является прерыватель или емкостный датчик на проводе свечи зажигания, то на выходе такого датчика присутствуют высоковольтные импульсы. Хотя входы микросхемы защищены от высоковольтного низкотокового воздействия, следует вход микросхемы защитить от перенапряжения, например, резисторным делителем напряжения с диодным стабилизатором.
Приложение
--^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ -- FILE: TAСHOMETER.VHD -- PROJECT: VHDL_HOBBY -- AUTHOR: Anatoli Sergyienko -- Created: 15/01/02 -- Email: aser@comsys.kpi.ua -- -- FUNCTION: - measuring and displaying the rotating -- frequency of the car engine. -- ALGORITHM: 1. Period of the signal DATAI is -- measured in clocks -- 2. frequency is calculated -- as F= Masstab/Period -- 3. frequency is outputted through DATAO -- to the barcode display -- CONSTRAINTS: the barcode display length is limited -- by Fmax,maximum period of the signal is measure_T; -- display period is equal to Disp_T - Fmax. --^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ library IEEE; use IEEE.std_logic_1164.all; entity Taсhometer is generic( Fmax: integer:=32); -- Максимальная частота, 1 деление=200 об/мин port(CLK: in STD_LOGIC; RST: in STD_LOGIC; DATAI: in STD_LOGIC; DATAO: out STD_LOGIC_VECTOR (Fmax-1 downto 0)); end Taсhometer; architecture Hobby of Taсhometer is constant measure_T: integer := 1024; --Максимальный период сигнала, --тактов, соответствует ~400об/мин constant measureMIN:integer := 68; --Минимальный период сигнала, --тактов=1024/15, -- соответствует ~6000об/мин constant Disp_T: integer := 4093; --Период отображения, тактов constant Masstab:integer := 1000; --Масштабный коэффициент signal DATAId: STD_LOGIC; signal Calculate,Measure,Display, Waiting :boolean; --FSM states signal CT2:integer range 0 to Disp_T+3; signal Period: integer range 0 to measure_T; signal M: integer range 0 to measure_T-1; signal F: STD_LOGIC_VECTOR(Fmax-1 downto 0); --F = Masstab/Period begin --DATAI __/^^\___/^^\___/^^\___ --DATAId __/^^\___/^^\___/^^\___ --Measure__|^^^^^|_____________________ --Calculate_________|^^^^^^|_____________ --Display __________________|^^^^^^^^^^^|____ --Waiting ^^|_______________________________|^^^^ CNTRL:process(CLK,RST) begin if RST='1' then Calculate<=false; Measure<=false; Display<=false; Waiting<=true; CT2<= 0; elsif CLK='1' and CLK'event then DATAId<=DATAI; --input delay -- finite state machine if ( DATAI='1' and DATAId='0' and Waiting ) then Measure<= true ; Waiting<= false; elsif ( DATAI='1' and DATAId='0' and Period>MeasureMIN ) then Measure<=false ; Calculate<=true; elsif(CT2 = Disp_T) then Display<=false; Waiting<=true; elsif (CT2 = Fmax)then Calculate<=false; Display<=true; end if; --clock counter if ( calculate or display) then CT2<= CT2+1; elsif Waiting then CT2<= 0; end if; end if; end process; CT_PERIOD: process(CLK,RST) --Счетчик периода вх.импульсов begin if RST='1' then Period<=0; elsif CLK='1' and CLK'event then if Measure then Period<=Period+1; elsif Waiting then Period<=0; end if; end if; end process; AU_FREQ:process(CLK,RST) --вычисление частоты и ее отображение begin if RST='1' then f<=(others=> '0'); M<=Masstab; elsif CLK='1' and CLK'event then if measure then M<=Masstab; f<=(others=> '0'); elsif calculate then if ( M-Period >0 ) then M<=M-Period ; F<=F(F'left-1 downto 0) & '1'; --сдвиговый регистр- столбик end if; end if; end if; end process; DATAO<=F; end Hobby;