Skip to content

homing: dead race-prevention guard in base_write_homing_out_pins (double write) #4289

Description

@grandixximo

Found while reviewing the getter/setter conversion of the motion module (#4286), which faithfully reproduces this master code.

src/emc/motion/homing.c, base_write_homing_out_pins() (around line 547):

if(!(*(addr->homing) && !H[jno].homing && homing_active)) {
    // Prevent race condition.
    // ... Do not update the homing status when going from homing --> not homing
    // and the state machine is still active. The homing status deassertion
    // must be delayed until the state machine is done.
    *(addr->homing) = H[jno].homing;
}
*(addr->homing) = H[jno].homing;       // OUT

The if guard exists to skip the pin update in one specific case (homing -> not homing while the state machine is still active), so the homing pin deassertion is delayed and a new homing command cannot fail on a stale state.

But the very next line writes the same value to the same pin unconditionally. Whenever the guard skips its own write, the following line does it anyway. The guard has no effect; the race it describes is not actually prevented.

Two possible fixes, depending on which behavior is intended:

  1. The delayed deassertion is needed: delete the unconditional write (keep only the guarded one).
  2. The eager update has proven fine in practice: delete the dead guard and its comment.

I do not know which is correct; the comment suggests (1), but the code has effectively been doing (2) for a long time without obvious fallout.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions