OK I have a plan; the design and phases below. Learning more about the capability of DCC++ documented by Gregg E. Berman. This falls under the heading of, WAEFRTFM, 'When all else fails, read the ... manual.'
Turns out that DCC++ has augmented DCC with a <S > command to monitor any number of sensors connected to unused pins of the Arduino (UNO or Maga). Defining a sensor allows you to refer to the sensor by id number vs the Arduino pin number. When a defined sensor transitions from HIGH to LOW (active), a <Q id> message is sent; LOW to HIGH (inactive) is reported with a <q id> message. By sending a <S> command without parameters, the status of all defined sensors will be reported. This will be used to monitor the IR sensors embedded in the layout to keep track of where the trains are.
Another addition to the DCC commands by DCC++ is the <Z> command to control Arduino output pins. Defining an output allows you to refer to the output by id number and control the output level (+5v-0v) of an Arduino output pin. The current status of each defined output is stored. The status of all outputs can be queried with the <s> command. This will be used to control the two relays needed to reverse the DCC power to the two sections of track needed.
DCC++ also augmented the DCC <a> command for all stationary decoders (i.e. A decoder NOT in a train) with the DCC++ <T> commands to define/delete/control turnouts. Defining a turnout allows you to refer to the turnout by id number vs its DCC accessory address/sub address and the current state of the turnout is stored and can be queried. The DCC accessory decoder command simply changes the state, active/inactive, of the given address/sub address. The state is not stored. The <T> command translates the given id to the stored DCC address/sub address, sends the DCC <a> command to control the turnout and stores the new state.
USPS delivered 2 "sample" semaphores this week one single arm and one double arm. Coming down the inside of the poles are a piano wire and two hair sized wires for each semaphore arm. The piano wire moves up and down to move the signal arm and moves a different colored lens in front of a small LED, the two wires.
As for controlling the semaphores using another Arduino or Raspberry with servo/PWM shield/HAT from Adafruit, seems to be the answer. Found one DCC answer that requires a ~$27 decoder board and $14+ Tortoise per semaphore arm. Sense the long-term plan is to use a Raspberry anyway using several servo HATs, ~$1/servo, and a micro servo $6, for each semaphore arm sounds good. Adafruit's servo HAT controls 16 servos for ~$17 and can be stacked 62 high. With up to 60 semaphores, the second option sounds REAL good. There are two issues: 1) brackets to hold the micro servos and 2) translating PWM pulses 1-2ms wide / 180° of rotations of the servo to ~1/8" movement of the semaphore arm control wire. That changes the aspect from RED to GREEN with YELLOW somewhere in the middle.
Finished building/powering the test track. Simple 27" piece of track with 4½" of dead track on each end (to catch run away trains). When all wired up to a DCC++ Arduino UNO and a Motor Shield, the track can be switched from "Main" to "Program" output of the DCC++. Decided to add switched power to one of the "dead" tracks. This stub track can be OFF, ON or reversed polarity of the test track. This gives me an insulated track joint to use in testing.
Parts ordered to lay track. Need to buy a sheet of plywood and get serious about doing the layout. Have the design in my head, time for proof of concept.