# Сборка и запуск

## Где находится проект

Keil:

```text
F:\set\workspace\setcorp\set506\AD\AD_Keil_Project\MDK-ARM\IHM08M.uvprojx
```

Simulink-модель:

```text
F:\set\workspace\setcorp\set506\AD\Inu_im_1wnd_3lvl\inu_im_1wnd_3lvl.slx
```

Отдельная помощь по модели:

```text
AD_Keil_Project\AD_docs\SIMULINK_MODEL_RUN_HELP.md
```

Карта Modbus RTU регистров:

```text
AD_Keil_Project\AD_docs\MODBUS_REGISTERS.md
```

## Как собрать

В Keil открыть `IHM08M.uvprojx` и выполнить `Rebuild`.

Командная сборка:

```powershell
C:\Keil_v5_41\UV4\UV4.exe -r F:\set\workspace\setcorp\set506\AD\AD_Keil_Project\MDK-ARM\IHM08M.uvprojx -t IHM08M -o F:\set\workspace\setcorp\set506\AD\AD_Keil_Project\MDK-ARM\rebuild_ad.log
```

Последняя проверка после добавления PWM-тестов и алгоритма измерения:

```text
"IHM08M\IHM08M.axf" - 0 Error(s), 0 Warning(s).
```

## Инициализация

В `main.c` выполняется:

```c
MX_GPIO_Init();
MX_TIM1_Init();
AD_Project_Init();
```

Внутри `AD_Project_Init()` поднимаются:

- `AD_Board_Init()`;
- `AD_Inverter_Init()`;
- `SimulinkInterface_Init()`;
- `AD_ParamID_Init()`;
- `AD_Debug_Init()`.

В основном цикле вызывается `AD_Project_Loop()`, где читаются ADC, обновляется Simulink-интерфейс, раз в 10 мс выполняется slow-step идентификации и обновляется `g_ad_debug`.

## Безопасный запуск без ключей

```c
AD_Board_StartDataLogging();
AD_Board_StopParamTest();
```

В этом режиме PWM не запускается.

## Включение тестового PWM

По умолчанию физические выходы выключены. Для стендовой проверки добавить в Keil `C/C++ -> Define`:

```text
AD_PROJECT_POWER_TEST_ENABLE=1
```

После этого можно запускать отдельные каналы:

```c
AD_Board_StartParamTestWithDuty(AD_PARAM_ID_MODE_PWM_TEST_UH, 0.08f);
AD_Board_StartParamTestWithDuty(AD_PARAM_ID_MODE_PWM_TEST_UL, 0.08f);
AD_Board_StopParamTest();
```

Физический PWM появится только если также выполнены runtime-условия: `enable=1`, заданы пределы тока и напряжения, нет fault, `BKIN` не активен.

## Запуск измерения параметров

Измерение сопротивления статора:

```c
AD_Board_StartParamTestWithDuty(AD_PARAM_ID_MODE_STATOR_RESISTANCE, 0.08f);
```

Измерение `Ls/Ll`:

```c
AD_ParamID_SetLockedRotorAllowed(1U);
AD_Board_StartParamTestWithDuty(AD_PARAM_ID_MODE_LOCKED_ROTOR_LEAKAGE, 0.08f);
```

Автоидентификация текущего уровня:

```c
AD_Board_StartParamTestWithDuty(AD_PARAM_ID_MODE_AUTO_IDENTIFICATION, 0.08f);
```

Результаты смотреть в:

```c
g_ad_debug.motor_parameters
g_ad_debug.motor_parameters.valid_mask
g_ad_debug.param_id_status
```

Флаг завершения: `AD_PARAM_ID_STATUS_COMPLETE`.

Если автоидентификация запущена без разрешения locked-rotor или без датчика скорости, нормален частичный результат: вместе с `AD_PARAM_ID_STATUS_COMPLETE` может стоять `AD_PARAM_ID_STATUS_PARTIAL_COMPLETE`. В этом случае смотреть `valid_mask`: уже измеренные параметры действительны, а пропущенные/неполученные параметры останутся без своих битов валидности.

## Важные ограничения

Сейчас проект умеет выдать тестовые PWM-импульсы и выполнить последовательную идентификацию `Rs`, `Ll`, `Rr`, `Lm`, затем `J/B`. Этап `Rr/Lr` требует разрешения locked-rotor; если `locked_rotor_allowed=0`, автоидентификация пропускает его и выставляет `AD_PARAM_ID_STATUS_LOCKED_ROTOR_SKIPPED`. Механические параметры `J` и `B` помечаются действительными только при наличии ненулевого `speed_rpm` во время разгона и выбега.

Перед запуском с двигателем сначала проверить режимы `PWM_TEST_UH..WL` осциллографом при малом duty и безопасном питании.
