64 lines
4.8 KiB
Markdown
64 lines
4.8 KiB
Markdown
# GOHOME 상태 머신 분석
|
|
|
|
## 개요
|
|
`GOHOME` 상태 머신(`_SM_RUN_GOHOME`)은 AGV를 현재 위치에서 미리 정의된 "Home" 노드로 이동시키는 역할을 합니다. 이 과정은 `_Util.cs`와 `VirtualAGV.cs`에 정의된 공유 경로 탐색 및 이동 로직을 활용합니다.
|
|
|
|
## 로직 흐름
|
|
|
|
### 1. 초기화 및 안전 점검
|
|
- **하드웨어 확인:** `PUB.AGV.IsOpen`을 확인합니다. 연결이 끊겨 있으면 에러 상태로 설정합니다.
|
|
- **충전 해제:** `_SM_RUN_CHGOFF`를 호출하여 AGV가 물리적으로 충전기에 연결되어 있지 않은지 확인합니다.
|
|
- *잠재적 문제:* 충전 센서가 고착(stuck)된 경우, 이 단계에서 무한 대기할 수 있습니다.
|
|
- **Lidar 안전:** `PUB.AGV.system1.stop_by_front_detect`를 확인합니다. 장애물이 감지되면 제거될 때까지 실행을 일시 중지(false 반환)합니다.
|
|
|
|
### 2. 1단계: 목적지 설정
|
|
- **홈 위치 조회:** `PUB.setting.NodeMAP_RFID_Home`에서 홈 노드 ID를 가져옵니다.
|
|
- **유효성 검사:** 맵에서 홈 노드를 찾을 수 없는 경우, 에러를 기록하고 `READY` 상태로 초기화합니다.
|
|
- **타겟 할당:** `PUB._virtualAGV.TargetNode`를 홈 노드로 설정합니다.
|
|
|
|
### 3. 2단계: 이동 실행
|
|
- **위임:** `_Util.cs`의 `UpdateMotionPositionForMark("_SM_RUN_GOHOME")`를 호출합니다.
|
|
- **경로 탐색:**
|
|
- 경로가 없거나 현재 경로가 유효하지 않은 경우, `_Util.cs`가 `CurrentNode`에서 `TargetNode`까지의 새로운 경로를 계산합니다.
|
|
- **예측 및 제어:**
|
|
- `VirtualAGV.Predict()`가 현재 노드와 경로를 기반으로 다음 행동을 결정합니다.
|
|
- **정지 조건:** `Predict()`가 `Stop`을 반환하는 경우:
|
|
- `IsPositionConfirmed`가 true인지 확인합니다.
|
|
- `CurrentNodeId`가 `TargetNode.NodeId`와 일치하는지 확인합니다.
|
|
- 둘 다 true이면 `true`(도착)를 반환합니다.
|
|
- **이동 조건:** `Predict()`가 이동 명령을 반환하는 경우:
|
|
- 논리적 명령(좌/우/직진, 전진/후진, 속도)을 하드웨어 명령(`AGVMoveSet`)으로 변환합니다.
|
|
- **최적화:** 상태가 변경된 경우에만 명령을 전송합니다 (최근 `_Util.cs` 업데이트에 구현됨).
|
|
- AGV가 구동 중인지 확인합니다 (`AGVMoveRun`).
|
|
|
|
### 4. 3단계: 완료
|
|
- **알림:** "홈 검색 완료" 음성을 출력합니다.
|
|
- **로깅:** 데이터베이스에 기록을 추가합니다.
|
|
- **전환:** 시퀀스를 업데이트하여 `GOHOME` 상태를 사실상 종료합니다.
|
|
|
|
## 잠재적 문제 및 위험 요소
|
|
|
|
### 1. 충전 센서에 의한 무한 대기
|
|
- **위험:** 충전 신호가 활성화되어 있는 한 `_SM_RUN_CHGOFF` 호출은 계속 `false`를 반환합니다.
|
|
- **시나리오:** 센서가 고장 나거나 시스템이 모르는 사이에 AGV가 수동으로 충전기에 밀려 올라간 경우, 여기서 멈출 수 있습니다.
|
|
- **완화:** `_SM_RUN_CHGOFF` 확인에 타임아웃이나 수동 오버라이드 기능을 추가해야 합니다 (현재 스니펫에서는 보이지 않음).
|
|
|
|
### 2. 위치 상실 복구
|
|
- **위험:** `_SM_RUN_POSCHK`(`UpdateMotionPositionForMark`에서 호출됨)가 태그를 찾지 못하면, AGV가 무한히 기어갈(crawl) 수 있거나 멈출 수 있습니다.
|
|
- **메커니즘:** `_SM_RUN_POSCHK`는 태그를 찾기 위해 저속 전진 명령을 내립니다.
|
|
- **시나리오:** AGV가 경로를 벗어났거나 데드존에 있는 경우, Lidar가 감지하지 못하면 충돌하거나 배회할 수 있습니다.
|
|
|
|
### 3. 경로 재계산 루프 (확인됨: 안전함)
|
|
- **분석:** `_Util.cs` 코드를 확인한 결과, `CalcPath`가 실패하여 경로가 생성되지 않으면(`PathResult.result == null`) 즉시 `PUB.sm.SetNewRunStep(ERunStep.READY)`를 호출합니다.
|
|
- **결론:** 경로 계산 실패 시 상태 머신이 `READY` 상태로 전환되므로, 무한 루프나 반복적인 재계산 시도는 발생하지 않습니다. 안전하게 정지합니다.
|
|
|
|
### 4. 통신 폭주 (해결됨)
|
|
- **이전 위험:** 동일한 이동 명령의 지속적인 전송.
|
|
- **해결:** 최근 `_Util.cs` 업데이트에서 `PUB.AGV.data`를 새 명령과 비교하여 변경 시에만 전송하도록 수정되었습니다.
|
|
|
|
## 권장 사항
|
|
1. **충전 해제 타임아웃:** 센서 고장 시 무한 대기를 방지하기 위해 `_SM_RUN_CHGOFF` 확인에 타임아웃을 추가하십시오.
|
|
2. **경로 실패 처리:** `CalcPath`가 null/empty를 반환하는지 명시적으로 확인하고, 무한 재시도 대신 에러와 함께 `GOHOME` 시퀀스를 중단하십시오.
|
|
3. **도착 확인:** `_Util.cs`의 "도착" 확인이 "거의 도착" 시나리오(예: 태그 약간 앞에서 정지)에 대해 견고한지 확인하십시오. 현재 로직은 `CurrentNodeId` 업데이트에 의존하며, 이는 양호해 보입니다.
|
|
|