Files
Balsam_167/Doc/PHASE_COMPARISON_BALSAM_165_167.md

24 KiB
Raw Blame History

@page phase_comparison_balsam Сравнение фазовой части Balsam 165 и Balsam 167

Сравнение фазовой части Balsam 165 и Balsam 167

Область сравнения

Сравнивались:

  • захват фазных сигналов АЦП;
  • удаление нулевого смещения;
  • масштабирование в физические единицы;
  • расчёт общего действующего значения;
  • расчёт уровней отдельных фаз A, B и C;
  • диагностика перекоса и обрыва фаз;
  • диагностические биты и регистры Modbus;
  • пороги напряжения и выдержки времени.

Исходные проекты:

  • K:/git_project/Balsam_165_periph;
  • K:/git_project/Balsam_167_periph.

Основные файлы:

Проект Файл
Balsam 165 K:/git_project/Balsam_165_periph/Source/Internal/measure.c
Balsam 165 K:/git_project/Balsam_165_periph/Source/Internal/ADC.c
Balsam 165 K:/git_project/Balsam_165_periph/Source/Internal/Include/measure.h
Balsam 165 K:/git_project/Balsam_165_periph/Doc/Balsam 165 data stru.xls
Balsam 167 Source/Internal/measure.c
Balsam 167 Source/Internal/ADC.c
Balsam 167 Source/Internal/Include/measure.h
Balsam 167 Doc/Balsam 167 data stru.xls

Вывод

Balsam 167 использует более правильный способ расчёта действующих значений отдельных фаз: усреднение квадрата с последующим извлечением корня. Balsam 165 сглаживает модуль сигнала, что не является настоящим RMS.

При этом в Balsam 167 появились две ошибки индексации:

  1. Парный канал записывается по абсолютному индексу, но читается по относительному.
  2. Бит Ignor устанавливается у абсолютного номера датчика, но проверяется у относительного chan.

Для УМП, где pow_addr == 0, первая ошибка не проявляется. Для силового блока она может приводить к дублированию фазных уровней и ложному Wry + Stop.

Рекомендуемый вариант: сохранить RMS-алгоритм Balsam 167, исправить индексацию и выполнять диагностику трёх фаз один раз после обработки всей пары каналов.

Сводная таблица

Параметр Balsam 165 Balsam 167 Оценка
Частота АЦП 5000 Гц 3750 Гц Изменена
Выбор фазных входов АЦП CONV02…CONV05 CONV02…CONV05 Одинаковый
Формула im_calc() Одинаковая Одинаковая Без изменений
Фаза B -A-C, для dsk_COMM эквивалентная разность -A-C после смены знака A По модулю эквивалентно
Уровень отдельной фазы EMA от abs(x) sqrt(EMA(x²)) 167 корректнее
Частота фильтра результата 5 Гц 3 Гц 167 медленнее
Тип lev_count[] float int В 167 раньше теряется дробная часть
Порог перекоса 20% 30% 167 менее чувствителен
Выдержка измеряемой фазы около 1,5 с около 3 с 167 медленнее
Выдержка восстановленной фазы около 0,75 с около 1,5 с В обеих версиях вдвое короче
Curr_Edge, УМП 100 300 Порог существенно повышен
Curr_Edge, силовой блок 40 200 Порог существенно повышен
Низкое Utr без выдержки счётчик около 3 с Улучшено, но блокируется Ignor
Верхнее Utr без выдержки без выдержки Без улучшения
Калибровка входов жёсткий curK[] Modbus/EEPROM Caliber[] 167 гибче
Пары каналов силового блока корректные относительные индексы несогласованные индексы Регрессия 167
Обработка Ignor правильный абсолютный датчик проверяется chan Регрессия 167
Отдельные биты фаз A/B/C нет нет Общий недостаток
Контроль пределов АЦП U/I нет нет Общий недостаток

1. Захват сигналов АЦП

Для УМП обе версии используют одинаковые входы:

CONV02 = 0x5; // напряжение 1
CONV03 = 0x4; // напряжение 2
CONV04 = 0x7; // ток 1
CONV05 = 0x2; // ток 2

Данные читаются из результатов ADCRESULT2…ADCRESULT5, после чего вызывается Current_count(i).

Различается частота обработки:

Balsam 165: ADC_FREQ = 5000 Гц
Balsam 167: ADC_FREQ = 3750 Гц

Назначение входов УМП:

chan Сигнал
0 Utr A
1 Utr C
2 Itr A
3 Itr C

Фаза B физически не измеряется.

2. Нулевое смещение

В обеих версиях используется медленное усреднение:

zero[n] = zero[n-1] + (ADC-zero[n-1]) / (5 * ADC_FREQ)

Balsam 165

Ноль записывается постоянно:

Zero_lev[chan] = filterbat(&out_filter[chan], zer_count[chan]);

Для подстройки используются те же out_filter[], которые участвуют в другой обработке сигналов.

Balsam 167

Добавлены отдельные фильтры zer_filter[]:

Zer = filterbat(&zer_filter[chan], zer_count[chan]);
if (WAKE < (WAKE_TIME / 2)) Zero_lev[chan] = Zer;

Разделение фильтров является улучшением. Однако после того как WAKE достиг нуля, условие остаётся истинным. Подстройка нуля фактически продолжается во время всей работы.

Если подстройка нужна только при запуске, должно проверяться также WAKE > 0.

3. Масштабирование

Balsam 165

Используются жёстко заданные коэффициенты curK[]:

Устройство Напряжение Ток
УМП 1/2 0.386 4.82
Силовой блок 0.402

Коэффициенты одинаковы для однотипных каналов и не берутся из EEPROM.

Balsam 167

Коэффициенты вычисляются из Caliber[0…3]:

напряжение: powK = Caliber / 10000
ток:        powK = Caliber / 1000

Преимущества:

  • индивидуальная калибровка каждого входа;
  • отдельные значения для экземпляров устройств;
  • сохранение и загрузка через EEPROM.

Значения тока заметно отличаются от Balsam 165. Например, для УМП 1 в Balsam 167 используются 3.505 и 3.380 вместо 4.82. Это может быть связано с изменением аппаратной части или новой калибровкой и требует стендовой сверки.

4. Общий уровень трёхфазного сигнала

Функция im_calc() в проектах совпадает:

isA = -1.5 * (a + b)
isB = cos(π/6) * (a - b)
Amplitude = 2/3 * sqrt(isA² + isB²)
Level = Amplitude / sqrt(2)

Эквивалентная формула амплитуды:

Amplitude = 2/sqrt(3) * sqrt(a² + a*b + b²)

Фильтрация общего уровня

Balsam 165 сначала делит амплитуду на sqrt(2), затем фильтрует Level фильтром 5 Гц. Для тока и всех каналов dsk_COMM используется дополнительная статическая переменная ffLev.

ffLev одна на все вызовы функции. На силовом блоке результаты разных пар могут влиять друг на друга.

Balsam 167 фильтрует амплитуду отдельным фильтром текущего датчика:

Amplitude = filterbat(&out_filter[sens], im_calc(Current, aCurrent));
Level = Amplitude / RADIX2;

Это устраняет общий ffLev и разделяет состояния фильтров разных пар.

Зона нечувствительности

Balsam 165:

Level < Curr_Edge -> Level = 0

Для УМП порог равен 100 единицам RMS.

Balsam 167:

напряжение: Amplitude < 20 -> 0
ток:        Amplitude < 75 -> 0

В пересчёте на RMS это примерно 14,1 для напряжения и 53,0 для тока. Поэтому Balsam 167 публикует слабые сигналы, которые Balsam 165 обнулял.

5. Уровни отдельных фаз

Balsam 165: среднее модуля

lev_count[chan] +=
    (fabs(Current) - lev_count[chan]) / (ADC_FREQ / 5);

Для синусоиды установившееся значение соответствует среднему модулю:

MeanAbs = 2/π * Amplitude ≈ 0.6366 * Amplitude

Balsam 167: настоящий RMS

lev_quadr[chan] +=
    (Current * Current - lev_quadr[chan]) / ADC_FREQ;
lev_count[chan] = sqrt(lev_quadr[chan]);

Для синусоиды:

RMS = 1/sqrt(2) * Amplitude ≈ 0.7071 * Amplitude

При одинаковом входном масштабе Balsam 167 показывает примерно в 1,1107 раза, или на 11,1%, больше Balsam 165.

Это изменение влияет на абсолютные фазные уровни, но почти не влияет на отношение минимальной фазы к максимальной, используемое для Wry.

Скорость сглаживания

Balsam 165 использует коэффициент 5/ADC_FREQ, что соответствует постоянной времени около 0,2 с.

Balsam 167 использует коэффициент 1/ADC_FREQ, что соответствует постоянной времени около 1 с. Фазные уровни Balsam 167 изменяются медленнее и стабильнее.

6. Восстановление фазы B

Для УМП в обеих версиях:

B = -A - C

Для силового блока в Balsam 165 используется:

third = current_channel - first_channel

В Balsam 167 сначала меняется знак сохранённого первого канала, затем применяется общая формула -Current-aCurrent. Результат отличается знаком, но для RMS знак не имеет значения.

Основной недостаток общий: фаза B не измеряется. Неисправность B определяется только через математическую связь с A и C.

7. Карта фазных регистров

В Balsam 165 код записывает:

0x68 + n*3 + 0 = текущий нечётный канал, для УМП фаза C
0x68 + n*3 + 1 = парный канал, для УМП фаза A
0x68 + n*3 + 2 = восстановленная фаза B

То есть фактический порядок для УМП:

C, A, B

В Balsam 167 первые две записи переставлены:

0x68 + n*3 + 0 = парный канал A
0x68 + n*3 + 1 = текущий канал C
0x68 + n*3 + 2 = восстановленная фаза B

Порядок соответствует карте Balsam 167:

Регистр УМП
0x68 Utr A
0x69 Utr C
0x6A Utr B
0x6B Itr A
0x6C Itr C
0x6D Itr B

В карте Balsam 165 эти регистры не описаны как фазные. Адрес 0x68 обозначен как яркость ламп, хотя исходный код записывает туда фазный уровень. Это риск несовместимости прошивки с внешним ПО и документацией.

8. Диагностика Wry

В обеих версиях используется отношение:

Max = max(phase_A, phase_C, phase_B)
deviation = (Max - phase) / Max

Balsam 165

deviation > 20%
Max > Curr_Edge
выдержка измеряемой фазы ≈ 1,5 с

Curr_Edge:

Режим Значение
УМП 100
Силовой блок 40

Balsam 167

deviation > 30%
Max > Curr_Edge
выдержка измеряемой фазы ≈ 3 с

Curr_Edge:

Режим Значение
УМП 300
Силовой блок 200

Balsam 167 значительно менее чувствителен к перекосу и реагирует медленнее.

Ошибка выдержки восстановленной фазы

Один счётчик err_count[thrd] вызывается при обработке обоих каналов пары. Поэтому он увеличивается дважды за цикл АЦП.

Фактическая выдержка постоянного дефекта фазы B:

Проект Заданная Фактическая для B
Balsam 165 1,5 с около 0,75 с
Balsam 167 3 с около 1,5 с

Проблема присутствует в обеих версиях.

Деление на ноль

Обе версии сначала вычисляют отношение с делением на Max, а затем проверяют нижний порог:

((Max - phase) / Max > limit) && (Max > Curr_Edge)

При Max == 0 выполняется 0/0. Безопасный порядок:

(Max > Curr_Edge) && (((Max - phase) / Max) > limit)

9. Различия обработки Ignor

Balsam 165

Используется правильный абсолютный номер датчика:

sens = tpl_cans + chan;
ignor = sens_error[sens].bit.Ignor;

Ошибки Wry, Out и Hyper продолжают вычисляться и передаваться, но Stop не устанавливается для игнорируемого канала.

Balsam 167

Проверяется относительный индекс:

sens = pow_addr + chan;
if (WAKE || sens_error[chan].bit.Ignor) goto fin;

Последствия различаются по типу устройства.

УМП

Для УМП pow_addr == 0, поэтому индекс формально совпадает. Каналам напряжения 0x00 и 0x01 по умолчанию устанавливается Ignor. В результате Balsam 167 полностью пропускает для напряжения:

  • Wry;
  • Out при Utr < 300 В;
  • Hyper при Utr > 420 В;
  • Stop.

В Balsam 165 эти информационные биты вычислялись, но Stop блокировался.

Силовой блок

На силовом блоке pow_addr != 0. Ignor устанавливается в sens_error[pow_addr+chan], но проверяется sens_error[chan].

Из-за этого игнорирование может не сработать, а Wry + Stop сформироваться для канала, который должен быть исключён из диагностики.

10. Регрессия sens_pair в Balsam 167

В Balsam 165 пары хранятся относительно chan:

sens_pair[0] = 1;
sens_pair[1] = 0;
sens_pair[2] = 3;
sens_pair[3] = 2;
pair = sens_pair[chan];

В Balsam 167 пары записываются по абсолютному индексу:

sens_pair[pow_addr+i] = pow_addr+(i^1);

Но чтение осталось старым:

pair = sens_pair[chan];

Для силового блока элементы sens_pair[0…3] после общей инициализации равны 0, 1, 2, 3. Следовательно, pair указывает на текущий канал, а не на соседний.

Последствия:

  • один фазный уровень может записываться дважды;
  • максимальная фаза выбирается из неполного набора;
  • Wry может быть пропущен или сформирован ошибочно;
  • карта 0x68…0x6D для силового блока не соответствует ожидаемой.

Вероятное исправление:

pair = sens_pair[sens] - pow_addr;

Окончательный вариант следует подтвердить стендовым тестом и ожидаемым порядком фаз в регистрах.

11. Пороговые уровни УМП

Заводские уставки в проектах совпадают:

Сигнал Нижний порог Верхний порог
Utr 300 В 420 В
Itr 800 А, предупреждение 900 А, авария

Различается обработка нижнего напряжения:

Проект Реакция Utr < 300 В
Balsam 165 Out сразу; Stop блокируется при штатном Ignor
Balsam 167 счётчик около 3 с, но при штатном Ignor проверка не выполняется

Верхний порог Utr > 420 В в обеих версиях не имеет отдельной выдержки и гистерезиса.

12. Диагностические биты

Расположение основных битов не изменилось:

Бит Маска Имя Назначение
0 0x0001 Tear обрыв датчика/предельное значение АЦП
2 0x0004 Wry перекос фаз
3 0x0008 Out ниже нижнего порога
4 0x0010 Over выше предупредительного порога
5 0x0020 Hyper выше аварийного порога
8 0x0100 Stop авария
9 0x0200 Ready готовность
14 0x4000 Ignor игнорировать аварию
15 0x8000 Bypas отключить канал

В обеих версиях Current_count() не формирует Tear для фазных входов U/I. Поэтому неисправность измерительного тракта нельзя надёжно отличить от пропадания напряжения или тока.

13. Что следует перенести из Balsam 165

В Balsam 167 полезно вернуть следующие свойства реализации 165:

  1. Согласованную систему индексов sens_pair.
  2. Проверку Ignor через абсолютный индекс sens_error[sens].
  3. Использование float для внутренних фазных уровней до момента публикации.

Не следует возвращать:

  • усреднение fabs() вместо RMS;
  • общий статический фильтр ffLev;
  • немедленное срабатывание нижнего напряжения;
  • жёсткие коэффициенты curK[].

14. Рекомендуемая итоговая реализация

  1. Считать все абсолютные номера датчиков один раз:

    sens = pow_addr + chan;
    
  2. Хранить sens_pair[] либо полностью в относительных, либо полностью в абсолютных индексах. Не смешивать системы адресации.

  3. Сохранить RMS Balsam 167, но хранить lev_count[] как float.

  4. После поступления обоих отсчётов пары вычислять A, C и B в одном месте.

  5. Один раз за цикл обновлять три RMS и три диагностических счётчика.

  6. Проверять Max > Curr_Edge до деления.

  7. Проверять Ignor через sens_error[sens].

  8. Разделить понятия:

    • информационная ошибка присутствует;
    • ошибка участвует в формировании Stop.
  9. Добавить отдельную маску фаз A/B/C.

  10. Добавить Tear по сырому значению АЦП.

  11. Добавить выдержку и гистерезис для 300/420 В.

  12. Явно определить, должна ли подстройка нуля работать после запуска.

15. Минимальные сравнительные тесты

Тест Что проверить
Одинаковая синусоида на обеих версиях Разницу MeanAbs и RMS около 11,1%
Номинальные A и C Правильный порядок A/C/B в 0x68…0x6D
Обрыв A RMS A, Wry, выдержку
Обрыв C RMS C, Wry, выдержку
Нарушение вычисленной B Отсутствие двойной скорости счётчика
Перекос 20%, 25%, 30%, 35% Различия порогов 165 и 167
Max == 0 Отсутствие деления на ноль
Utr = 299 В Out и выдержку
Utr = 421 В Hyper и отсутствие дребезга
Ignor = 1 Ошибка видна, но не создаёт Stop, если это требуемая семантика
Силовой блок, две пары Отсутствие дублирования фазных RMS
АЦП около 0 и 4095 Формирование Tear

Заключение

Фазовый расчёт Balsam 167 является хорошей основой благодаря настоящему RMS, раздельным фильтрам и калибровке из регистров. Главный риск версии 167 находится не в математике RMS, а в адресации состояния каналов.

До исправления sens_pair и Ignor фазные регистры и Wry силового блока нельзя считать надёжными. Для УМП необходимо отдельно решить, должны ли напряжения с установленным Ignor продолжать формировать информационные Wry, Out и Hyper, как это происходило в Balsam 165.