ytgf6785f86rf  
Главная
Продукция
Партнеры
Статьи
О нас

Контакты

Ссылки



Базовая схема вольтметра постоянного тока на микроконтроллере P89LPC901.
 


Базовая схема вольтметра постоянного тока на микроконтроллере P89LPC901.

В статье рассматривается способ измерения напряжения постоянного тока с использованием встроенного в микроконтроллер аналогового компаратора. Предложенная схема вольтметра постоянного тока использует минимальное количество внешних компонентов. Дополняя предложенную схему можно построить многофункциональные измерительные приборы.



Летом 2003 г. Фирма Philips предложила новое семейство микроконтроллеров со старым, хорошо известным российским разработчикам 51 ядром. В микроконтроллеры семейства LPC900 включены очень многие, появившиеся в последние годы, аппаратные решения, повышающие надежность работы и функциональную насыщенность этих приборов.
Вот только короткий перечень дополнительных возможностей микроконтроллеров P89LPC9xx относительно базовой модели стандартного представителя 51 семейства: сторожевой таймер, системный таймер, шестикратно ускоренное ядро, стабильный внутренний RC генератор, режимы пониженного энергопотребления, внутрисхемное программирование, возможность программного сброса и возможность использования Flash памяти программ для записи и чтения данных из программы пользователя, контроль провалов напряжения питания, а также встроенные аналоговые компоненты.
Именно последнее обстоятельство: наличие аналоговых компараторов, раскрывает огромные возможности построения схем приборов с минимальным количеством внешних компонентов.
Основы предлагаемой схемы вольтметра является микроконтроллер P89LPC901 (смотри рис. 1), выпускаемый в восьминожечном корпусе. Особенность этой микросхемы заключается в том, что функции почти всех ножек можно изменять программно, и именно этот факт лежит в основе предлагаемого технического решения.

Рис. 1

Структурная схема вольтметра приведена на рис. 2.



Рис. 2

Принцип измерения базируется на двух известных формулах:
Q = U * C и Q = I * t
Если их приравнять друг другу и произвести некоторое преобразование, то получим:
U * C = I * t
U = (I / C) * t
Теперь посмотрим, что это означает для нашей практической задачи. Измеряемое напряжение оказывается прямо пропорциональным времени заряда конденсатора. Таким образом, узнав время, за которое конденсатор зарядится до величины входного, измеряемого напряжения, можно вычислить его искомое значение.
Задача значительно упрощается благодаря линейной зависимости изменения напряжения на конденсаторе, заряжаемого от источника постоянного тока, и фактически сводится к определению практически приемлемых величин тока, формируемого источником тока, и емкости конденсатора. Эту задачу мы будем решать исходя из следующих данных. Максимальное напряжение на входе измерительного узла, равное максимально возможному напряжению на конденсаторе, ограничено напряжением питания схемы. Это напряжение питания микроконтроллера, и оно составляет 3,3 В.
Максимально возможное время t определяется следующим образом. В качестве измерителя времени предполагается использовать 16-битный встроенный таймер-счетчик, работающий от внутреннего генератора микроконтроллера.
tmax = ((1 / fмк) * D) * 216
tmax = ((1/7,28*106)*2) * 216=0,018 с
где D=2 минимально возможный, программно устанавливаемый делитель микроконтроллера.
Таким образом, зная максимально возможное значение напряжения и времени, мы можем определить значение коэффициента пропорциональности в формуле 3.
(I / C) = Umax / tmax = 3,3 /0,018≈183
Задавшись током I=100 мкА, определим значение ёмкости C≈0,54 мкФ, выбираем конденсатор 0,47 мкФ. Очевидно, что можно выбрать любое другое значение пары I и C.
Определив основные соотношения параметров в схеме, переходим к рассмотрению конкретных узлов структурной схемы. Пример реализации входного модуля аттенюатора и защиты приведён на рис. 3. Аттенюатор на четыре положения, определяющий входное сопротивление нашего вольтметра (Rвх=10 МОм), реализован на четырех резисторах, которые необходимо подобрать с точностью до 1%. Следует отметить, что некоторое усложнение программного обеспечения позволяет отказаться от процедуры подбора резисторов, заменив его вводом дополнительных программных коэффициентов. Эта методика потребует подачи заранее известного эталонного напряжения для определения поправочных коэффициентов, которые заносятся в память микроконтроллера с помощью дополнительной прошивки.
 


Рис. 3


Расчет ограничительного резистора.
Функцию ограничительного резистора выполняет резистор R6. Для расчета необходимо задать некоторые начальные условия. Предположим, что максимальное входное напряжение будет 300 В. Ограничительные диоды могут без вреда для себя пропускать ток до 100 мА, тогда:
Rогр=(Uвх/Iмах диода)=(300/100*10-3)=3,0 кОм
Естественно, сопоротивление Rогр должно быть минимально возможным, так как падение напряжения на нем, из-за токов утечки диодов и входного тока операционного усилителя создает дополнительную погрешность при измерении малых значений входного напряжения.
На ограничительном резисторе может выделяться значительная мощность, поэтому необходимо установить резистор с мощностью рассеивания не менее трёх Вт (например, четыре последовательно включенных резистора по 820.Ом мощностью 1 Вт.)
Пример реализации генератора тока приведен на рис. 4. Величина тока заряда конденсатора задается подбором резистора в цепи истока полевого транзистора.
 


Рис. 4
На рис. 5 представлены те аппаратные ресурсы микроконтроллера, которые задействованы в базовой схеме. К выводу 7 микроконтроллера может быть подключен либо вход компаратора, либо цифровой выход порта P0.4. Подключение цифрового выхода к конденсатору, при записанном в данный бит порта значения ноль, эквивалентно заземлению конденсатора через внутренний полевой транзистор порта. Таким образом, обеспечивается подготовка конденсатора к началу измерения.
 


Рис. 5
Компаратор вызовет прерывание микроконтроллера при достижении напряжения на конденсаторе равного входному измеряемому напряжению.
Учитывая ограниченное количество выводов микроконтроллера P89LPC901, в качестве индикатора применен модуль WM-1611-62A, требующий для своей работы всего два управляющих сигнала. Схема подключения индикатора приведена на рис. 6.
 


Рис. 6

Реализация данного алгоритма выполнена с помощью восьми программных модулей.
1. Главный программный модуль ADC обеспечивает необходимые настройки процессора после сброса, последовательно вызывает необходимые подпрограммы и реализует последовательные переключения выводов микроконтроллера.
2. Для обслуживания индикатора используются два программных модуля INDIC и INDIC01. Модуль INDIC выполняет две функции. Первая функция заключается в предустановке индикатора после включения питания: четырехсекундной задержки и загрузке для индикации стартовых символов. Вторая функция обеспечивает последовательный вывод в процессор индикатора содержимого десяти ячеек ОЗУ, где будет храниться измеренное значение напряжения.
3. Для обслуживания кнопки используется программный модуль KNOPKA представляющий собой антидребезговую программу.
4. Для преобразования значения таймера счетчика к значению напряжения используется программные модули DIV16_8 и RLC, предназначенные для масштабирования.
5. Для преобразования двоичного кода в двоично-десятичный используется программный модуль FRUNZE2_10.
6. Обслуживание прерывания от компаратора и таймера реализовано в главном модуле, подпрограммами COMP и TIMER1.
7. Для усреднения измеряемых значений используется программный модуль SRED.
Процесс измерения основывается на сравнении псевдонеизменного входного измеряемого значения напряжения и линейно изменяющегося напряжения на ёмкости С1, заряжаемой от источника тока на полевом транзисторе VT1. Время заряда ёмкости С1 от 0 до момента срабатывания компаратора измеряется с помощью таймера 1 и пропорционально по линейному закону величине измеряемого напряжения. Если измеряемое напряжение находится вне допустимого диапазона, лимитированного в данном случае напряжением питания, то возникает прерывание от таймера. На индикатор в этом случае выводится символ «Р» во всех разрядах
Алгоритм работы микроконтроллера в режиме измерителя напряжения реализован в основном модуле ADC и распадается на следующие этапы:
1. Задание сегментов памяти. Назначение импортируемых переменных и подпрограмм расположенных в других модулях.
2. Назначение абсолютных адресов для обслуживания подпрограмм прерывания от таймера и компаратора.
3. Начальные установки и конфигурирование портов (загрузка регистров P0M1, P1M1 и P3M1).
4. Настройка порта Р1.2, обслуживания кнопки — «пуск измерения».
5. Вызов подпрограммы инициализации индикатора INDIC.
6. Подготовка компаратора к измерениям.
7. Подготовка таймера к началу измерения.
8. Цикл ожидания нажатия кнопки «пуск измерения».
9. Переконфигурирование порта Р0.4. К порту Р0.4 подключаются цифровые функции. Происходит сброс конденсатора С1. Задержка DEL12 обеспечивает паузу в работе микроконтроллера для гарантированного разряда конденсатора С1.
10. Переконфигурирование порта Р0.4. С этого момента к выводу Р0.4 микроконтроллера подключен аналоговый вход компаратора.
11. Разрешение прерываний от таймера и компоратора. Запуск таймера.
12. Цикл ожидания окончания измерения. Выход из цикла происходит по прерыванию от таймера или компаратора.
13. При успешном проведении первого измерения (прерывание от компаратора) цикл измерения повторяется шестнадцать раз. Измеренные значения накапливаются в ячейках SUM1..SUM3 и усредняются модулями RLC и SRED. В противном случае (прерывание от таймера) производится запись в индикатор символов «Р» и возврат в цикл ожидания нажатия кнопки.
14. Нормолизация измеренного значения производится умножением на коэффициент 4/7 двумя модулями DIV16_8 (деление на 7) и RLC (умножение на 4). Данный коэффициент определяется значением ёмкости конденсатора С1 и током его заряда.
15. Преобразование двоичного усредненного значения в двоично-десятичную форму.
16. Вывод измеренного значения на индикацию с помощью двух программных модулей INDIC и INDIС01.
По сути, вся тяжесть решения задачи, определенной в заголовке статьи, ложится на комплекс модулей — проект. Именно программы и внутренние ресурсы микроконтроллера обеспечивают простоту аппаратной реализации.
Все модули проекта написаны на языке ассемблера, отлажены в среде µVision—2. Проект состоит из главного модуля ADC и семи вспомогательных автономных модулей, являющихся универсальными подпрограммами, которые после некоторых косметических изменений можно использовать в других проектах. Ряд подпрограмм заимствован из других источников. Небольшие изменения в этих программах сделали их полноправными участниками нашего проекта. Подпрограммы FRUNZE2_10 и INDIC взяты из книги А. Фрунзе «Микроконтроллеры? Это же просто!» том 1, стр.274 и стр. 102 соответственно. Подпрограмма DIV16_8 заимствована с сайта 8052.ru. Данные действия предприняты авторами совершенно сознательно, чтобы подчеркнуть приемственность наработанного за почти два десятка лет программного обеспечения для среды проектирования µVision—2.
Текст программных модулей приводится ниже.
 

;-----------------------------------------------------------------------------------------------
; ОСНОВНОЙ МОДУЛЬ ПРГРАММЫ (ADC)
;-----------------------------------------------------------------------------------------------
$NOMOD51
$INCLUDE (D:\Keil3\C51\inc\Philips\REG922.H)

NAME ADC
EXTRN CODE (BN2BCD,KNOPKA,INIZ,INDIK01,INDVIV,SRED256,RLC_R6,DIV16)
EXTRN DATA (DIVIDEND, DIVISOR, QUOTIENT, REMAINDER)
EXTRN DATA (AD0,SUM1,SUM2,SUM3)
PUBLIC DEL12
PROGADC SEGMENT CODE
KLAV SEGMENT BIT
RSEG KLAV
KLAV1: DBIT 1
KLAV2: DBIT 1

?STACK SEGMENT IDATA
RSEG ?STACK
DS 016h

CSEG AT 43H ;Comparator
JMP COMP
CSEG AT 0BH ;Timer 0
RETI
CSEG AT 1BH ;Timer 1
JMP TIMER1
CSEG AT 0
JMP NACH

RSEG PROGADC
NACH: MOV SP,#?STACK-1 ;Начало программы
ANL P0M1,#00000000B ;Предустановка регистров
ANL P1M1,#00000000B ;Конфигурации портов
ANL P3M1,#00000000B

ANL P1M1,#11111000B ;Конфигурирование порта Р1.2
;2-направленный
ANL P1M2,#11111000B

MOV TMOD,#00010000B ;Инициализация таймера

RAZR SET P0.4 ;RAZR=P0.4

CALL INIZ ;Инициализация индикатора
MOV PT0AD,#030h ;Инициализация компаратора
ORL P0M1,#030h
ANL P0M2,#0CFh
MOV CMP1,#00100100B ;Отключен REF
CALL DELAY10US
ANL CMP1,#1111$1110b
CLR RAZR ;Запись нуля в P0.4

METKA:
ANL PT0AD,#0EFh ;Подключение цифрового входа P0.4
ANL P0M1,#0EFh
ANL P0M2,#0EFh
CALL DEL12 ;Задержка для разряда конденсатора

MOV SUM1,#0 ;Обнуленуие ячеек ОЗУ для
MOV SUM2,#0 ;Промежуточных результатов
MOV SUM3,#0
MOV R5,#16 ;Задание количества усреднений

;Ожидание включения кнопки
CALL KNOPKA

METKA2:
CLR KLAV ;Сброс битов ожидания от компаратора
CLR KLAV2 ;и таймера

CLR TR1 ;Подготовка таймера
MOV TL1,#0
MOV TH1,#0

CALL DEL12 ;Конфигурирование порта Р0.4
;Разряд конденсатора

ORL P0M1,#00010000B
ANL P0M2,#11101111B
;Переконфигурирование порта Р0.4
ORL PT0AD,#010h ;Подключение аналового входа P0.4
ANL CMP1,#11111110B ;Сброс бита прерывания от компаратора

;Начало измерения
SETB EC ;Разрешение прерывания от компаратора
SETB ET1 ;Разрешение прерывания от таймера
SETB EA ;Разрешение системного прерывания

SETB TR1 ;Запуск таймера

OJID:
JNB KLAV1,OJID ;Цикл, выход по прерыванию от компаратора
JB KLAV2,METKA1 ;или от таймера

ANL PT0AD,#0EFh ;Подключение цифрового входа P0.4
ANL P0M1,#0EFh
ANL P0M2,#0EFh

CALL SRED256 ;Подпрограммы усреднения
DJNZ R5,METKA2
MOV R6,#4
CALL RLC_R6

MOV DIVIDEND,SUM2 ;Подпрограммы нормализации результата
MOV DIVIDEND+1,SUM3
MOV DIVISOR,#07
CALL DIV16

MOV SUM2,QUOTIENT
MOV SUM3,QUOTIENT+1
MOV R6,#2
CALL RLC_R6

MOV R2,SUM2
MOV R3,SUM3
CALL BN2BCD ;Подпрограмма преобразования результата
;в двоично-десятичную форму
CALL INDIK01
METKA1:
CALL INDVIV ;Индикация результата (шесть разрядов) без
JMP METKA ;запятой

DELAY10US: ;Подпрограмма задержки инициализации
MOV R2,#37 ;компаратора

DE10US:
DJNZ R2,DE10US
RET

COMP: CLR TR1 ;Подпрограмма обработки прерывания от
CLR EA ;компаратора
CLR EC
CLR ET1
SETB KLAV1
RETI

TIMER1: CLR TR1 ;Подпрограмма обработки прерывания от
CLR EA ;таймера
CLR EC
CLR ET1
MOV R0,#AD0+2
MOV R7,#6
PERT1:
MOV @R0,#0EEh
INC R0
DJNZ R7,PERT1
SETB KLAV1
SETB KLAV2
RETI

DEL12: MOV R1,#51 ;Подпрограмма задержки для разряда
LREX1: MOV R2,#51 ;конденсатора
LRIN1: DJNZ R2,LRIN1
DJNZ R1,LREX1
RET
END


;-----------------------------------------------------------------------------------------------
; МОДУЛЬ ПРЕОБРАЗОВАНИЯ ИЗ ДВОИЧНОГО ФОРМАТА
; В ДВОИЧНО-ДЕСЯТИЧНЫЙ ФОРМАТ (FRUNZE2_10)
; ВХОДНЫЕ ДАННЫЕ В R3R2, ВЫХОДНЫЕ В R6R5R4, R0 И R1 СОХРАНЯЮТСЯ
;-----------------------------------------------------------------------------------------------
$NOMOD51
$INCLUDE (D:\Keil3\C51\inc\Philips\REG922.H)
NAME FRUNZE2_10
PUBLIC BN2BCD

FRUNZE2_10 SEGMENT CODE
RSEG FRUNZE2_10
BN2BCD: ;R3R2 -> R6R5R4, R0 И R1 СОХР.
MOV R7,#10H
MOV A,#0
MOV R4,A
MOV R5,A
MOV R6,A
BN2CKL: MOV A,R2
ADD A,R2
MOV R2,A
MOV A,R3
ADDC A,R3
MOV R3,A
;ДВОИЧНО-ДЕСЯТИЧНОЕ УДВОЕНИЕ СУММЫ С УЧЕТОМ ПЕРЕНОСА:
MOV A,R4
ADDC A,R4
DA A
MOV R4,A
MOV A,R5
ADDC A,R5
DA A
MOV R5,A
MOV A,R6
ADDC A,R6
DA A
MOV R6,A
;ПРОВЕРКА КОНЦА ЦИКЛА:
DJNZ R7,BN2CKL
RET
END


;-----------------------------------------------------------------------------------------------
; МОДУЛЬ ВЫВОДА НА ИНДИКАТОР (INDIC)
;-----------------------------------------------------------------------------------------------
$NOMOD51
$INCLUDE (D:\Keil3\C51\inc\Philips\REG922.H)

NAME INDIC
EXTRN DATA (AD0) ;Импорт информации для индикации
EXTRN CODE (DEL4C) ;Подпрограмма задержки
PUBLIC INDVIV, INIZ ;Разрешение входов в модуль
PUBLIC DEL1
PROG1 SEGMENT CODE
RSEG PROG1

DATIND EQU P3.0 ;К выводу DI_3
CLKIND EQU P3.1 ;К выводу SK_2

DEL1:
MOV R1,#5
LREX1: MOV R2,#5
LRIN1: DJNZ R2,LRIN1
DJNZ R1,LREX1
RET
;Инициализация при пуске
INIZ: CALL DEL4C ;Задержка для инициализации индикатора
MOV R7,#10
MOV R0,#AD0
M12:
MOV @R0,#0Ch ;Запись кода 0С в индикатор
INC R0
DJNZ R7,M12

INDVIV: MOV A,AD0+9 ;Последовательная передача цифр на
CALL SIMBOL1 ;индикацию из ОЗУ, начиная со старших
MOV A,AD0+8 ;разрядов
CALL SIMBOL1
MOV A,AD0+7
CALL SIMBOL1
MOV A,AD0+6
CALL SIMBOL1
MOV A,AD0+5
CALL SIMBOL1
MOV A,AD0+4
CALL SIMBOL1
MOV A,AD0+3
CALL SIMBOL1
MOV A,AD0+2
CALL SIMBOL1
MOV A,AD0+1
CALL SIMBOL1
MOV A,AD0+0
CALL SIMBOL1
RET

SIMBOL1: ANL A,#00001111B ;Вывод символа
CJNE A,#0,SIMB11
MOV A,#10
SJMP SIMB12
SIMB11: CJNE A,#0FH,SIMB12
MOV A,#0
SIMB12:
CLR CLKIND
SWAP A
MOV R3,#4
AA2: RLC A
MOV DATIND,C
SETB CLKIND
CALL DEL1
CLR CLKIND
CALL DEL1
DJNZ R3,AA2
RET
END


;-----------------------------------------------------------------------------------------------
; МОДУЛЬ ПОДГОТОВКИ ДЛЯ ВЫВОДА НА ИНДИКАТОР (INDIC01)
;-----------------------------------------------------------------------------------------------
$NOMOD51
$INCLUDE (D:\Keil3\C51\inc\Philips\REG922.H)
NAME INDIC01
EXTRN CODE (INDVIV)
PUBLIC AD0
PUBLIC INDIK01, DEL4C
PROG1 SEGMENT CODE
AD SEGMENT DATA
RSEG AD
AD0: DS 010H

RSEG PROG1
INDIK01: MOV A,#0 ;Потетрадная загрузка индецируемой
MOV AD0+8,A ;информации из регистров R6…R4
MOV A,R6
ANL A,#0f0h
SWAP A
MOV AD0+7,A
MOV A,R6
ANL A,#0fh
MOV AD0+6,A
MOV A,R5
ANL A,#0f0h
SWAP A
MOV AD0+5,A
MOV A,R5
ANL A,#0fh
MOV AD0+4,A
MOV A,R4
ANL A,#0f0h
SWAP A
MOV AD0+3,A
MOV A,R4
ANL A,#0fh
MOV AD0+2,A
RET

DEL4C:
CALL DEL1C
CALL DEL1C
CALL DEL1C
CALL DEL1C
RET
;
DEL1C:
MOV R3,#28
LREX1: MOV R1,#255
LREX: MOV R2,#255
LRIN: DJNZ R2,LRIN
DJNZ R1,LREX
DJNZ R3,LREX1
RET
END


;-----------------------------------------------------------------------------------------------
; МОДУЛЬ УСТРАНЕНИЯ ДРЕБЕЗГА (KNOPKA)
;-----------------------------------------------------------------------------------------------
$NOMOD51
$INCLUDE (D:\Keil3\C51\inc\Philips\REG922.H)

NAME KNOPKA
PUBLIC KNOPKA
EXTRN CODE (DEL12)
KNOPKA1 SEGMENT CODE
RSEG KNOPKA1
KNOPKA:
MOV R7,#5
M11: JB P1.2,M11 ;Выход из п\п если P1.2=0
CALL DEL12
DJNZ R7,M11
RET
END


;-----------------------------------------------------------------------------------------------
; МОДУЛЬ СУММИРОВАНИЯ ДЛЯ УСРЕДНЕНИЯ (SRED)
;-----------------------------------------------------------------------------------------------
$NOMOD51
$INCLUDE (D:\Keil3\C51\inc\Philips\REG932.H)

NAME SRED
PUBLIC SUM1, SUM2, SUM3
PUBLIC SRED256
PROGSRED SEGMENT CODE
SUM SEGMENT DATA
RSEG SUM
SUM1: DS 1
SUM2: DS 1
SUM3: DS 1

RSEG PROGSRED
SRED256: MOV A,SUM1 ;Двухбайтное значение таймера
ADD A,TL1 ;суммируется и сохраняется в ячейках ОЗУ
MOV SUM1,A ;SUM1…SUM3 (старший байт в SUM3)
MOV A,SUM2
ADDC A,TH1
MOV SUM2,A

MOV A,SUM3
ADDC A,#0
MOV SUM3,A
RET
END


;-----------------------------------------------------------------------------------------------
; МОДУЛЬ СДВИГА ДЛЯ УСРЕДНЕНИЯ (RLC)
;-----------------------------------------------------------------------------------------------
$NOMOD51
$INCLUDE (D:\Keil3\C51\inc\Philips\REG922.H)

NAME RLC
EXTRN DATA (SUM1, SUM2, SUM3)
PUBLIC RLC_R6
PROGRLC4 SEGMENT CODE

RSEG PROGRLC4
RLC_R6: MOV A,SUM1 ;Параметр сдвига задается в модуле ADC
RLC A ;через регистр R6
MOV SUM1,A
MOV A,SUM2
RLC A
MOV SUM2,A
MOV A,SUM3
RLC A
MOV SUM3,A
DJNZ R6,RLC_R6
RET
END


;-----------------------------------------------------------------------------------------------
; МОДУЛЬ ДЕЛЕНИЯ (DIV16_8)
;-----------------------------------------------------------------------------------------------
$NOMOD51
$INCLUDE (D:\Keil3\C51\inc\Philips\REG922.H)

NAME DIV16_8
PUBLIC DIV16
PROGDIV SEGMENT CODE
DIV_16 SEGMENT DATA
RSEG DIV_16
QUOTIENT: DS 2 ;Частное
DIVISOR: DS 2 ;Делитель
DIVIDEND: DS 2 ;Делимое
REMAINDER: DS 2 ;Остаток
PUBLIC REMAINDER, DIVIDEND, QUOTIENT, DIVISOR

RSEG PROGDIV
Div16: CLR A
CJNE A,DIVISOR,OK

DIVIDE_BY_ZERO:
SETB OV
RET

OK: MOV QUOTIENT,A
MOV R4,#8
MOV R5,DIVIDEND
MOV R6,DIVIDEND+1
MOV R7,A
MOV A,R6
MOV B,DIVISOR
DIV AB
MOV QUOTIENT+1,A
MOV R6,B
TIMES_TWO:
MOV A,R5
RLC A
MOV R5,A
MOV A,R6
RLC A
MOV R6,A
MOV A,R7
RLC A
MOV R7,A

COMPARE:
CJNE A,#0,DONE
MOV A,R6
CJNE A,DIVISOR,DONE
CJNE R5,#0,DONE
DONE: CPL C

BUILD_QUOTIENT:
MOV A,QUOTIENT
RLC A
MOV QUOTIENT,A
JNB ACC.0,LOOP

SUBTRACT:
MOV A,R6
SUBB A,DIVISOR
MOV R6,A
MOV A,R7
SUBB A,#0
MOV R7,A

LOOP: DJNZ R4,TIMES_TWO
MOV A,DIVISOR
MOV B,QUOTIENT
MUL AB
MOV B,A
MOV A,DIVIDEND
SUBB A,B
MOV REMAINDER,A
CLR OV
RET
END



Предложенное техническое решение и комплект программных модулей, как указывалось в заглавии статьи, является базовым. В данном проекте сознательно был использован микроконтроллер P89LPC901 имеющий всего восемь выводов, что ограничивает возможности прибора, но значительно уменьшает габариты прибора. В частности, при индикации не указывается место десятичной запятой. Для информирования контроллера о положении входного аттенюатора требуются два дополнительных вывода. Использование другой микросхемы из этого же семейства, например P89LP914, позволит после некоторых доработок реализовать не только выше названную функцию, но и сможет обеспечить автоматический выбор пределов.
Данная схема достаточно универсальна и может послужить основой при разработке других конструкций. Например, для построения схемы измерения ёмкости, при этом в качестве опорного напряжения можно использовать внутренний источник 1,23 В микроконтроллера. Но это, другая история...


Авторы:
Андрей Сошкин
Андрей Мамонтов