ros2
runtime_error
ai_generated
true
RuntimeError: Cannot cancel goal that is already being cancelled
ID: ros2/nav2-cancel-goal-multiple-times
85%Fix Rate
85%Confidence
1Evidence
2024-02-15First Seen
Version Compatibility
| Version | Status | Introduced | Deprecated | Notes |
|---|---|---|---|---|
| ros2-humble | active | — | — | — |
| ros2-iron | active | — | — | — |
| ros2-rolling | active | — | — | — |
Root Cause
Nav2 action server does not support concurrent cancel requests on the same goal; calling cancel multiple times triggers a race condition in the action server's internal state machine.
generic中文
Nav2动作服务器不支持对同一目标并发取消请求;多次调用取消会触发动作服务器内部状态机的竞态条件。
Official Documentation
https://docs.nav2.org/behavior_trees/overview.htmlWorkarounds
-
90% success Check if the goal is already in a terminal state before calling cancel: if (goal_handle->get_status() == action_msgs::msg::GoalStatus::STATUS_ACCEPTED || goal_handle->get_status() == action_msgs::msg::GoalStatus::STATUS_EXECUTING) { goal_handle->cancel(); }
Check if the goal is already in a terminal state before calling cancel: if (goal_handle->get_status() == action_msgs::msg::GoalStatus::STATUS_ACCEPTED || goal_handle->get_status() == action_msgs::msg::GoalStatus::STATUS_EXECUTING) { goal_handle->cancel(); } -
85% success Use a mutex to serialize cancel calls: std::lock_guard<std::mutex> lock(cancel_mutex_); if (!cancel_in_progress_) { cancel_in_progress_ = true; goal_handle->cancel(); cancel_in_progress_ = false; }
Use a mutex to serialize cancel calls: std::lock_guard<std::mutex> lock(cancel_mutex_); if (!cancel_in_progress_) { cancel_in_progress_ = true; goal_handle->cancel(); cancel_in_progress_ = false; }
中文步骤
在取消前检查目标是否处于终端状态:if (goal_handle->get_status() == action_msgs::msg::GoalStatus::STATUS_ACCEPTED || goal_handle->get_status() == action_msgs::msg::GoalStatus::STATUS_EXECUTING) { goal_handle->cancel(); }使用互斥锁序列化取消调用:std::lock_guard<std::mutex> lock(cancel_mutex_); if (!cancel_in_progress_) { cancel_in_progress_ = true; goal_handle->cancel(); cancel_in_progress_ = false; }
Dead Ends
Common approaches that don't work:
-
70% fail
Race still occurs if two cancel calls happen within the sleep window; not a deterministic fix.
-
60% fail
Error is suppressed but the action server state may remain inconsistent, leading to future crashes.