Weird, I'm 99.9% sure I wrote a detailed response yesterday
Let's try again. It's good that you are able to work around this using normal overrides, but leaves unexplained why the "user" ones weren't working. I'm not clear why that is, and am unlikely to make a useful guess without actually sitting down and debugging with controlled tests and logs.
So instead, I'll try to explain how the _user and regular overrides are differ. In particular, the set calls you have after the snap() call may not be doing what you expect.
Normal CHDK overrides for Tv, Av, Sv and ND (set_tv96* etc, as opposed to the _user ones in the previous version) have more complicated logic than just setting a setting.
If called outside of shoot half (when get_shooting() is false) they just save the value in internal CHDK variables. Then, when the next shoot half happens and get_shooting goes true, the values are transferred to the propcases to override whatever the Canon firmware would have done. The CHDK variables are then cleared, so the override are only applied to one shot or half shoot cycle. They are also effectively cleared if the script ends before a shoot half happens. (Technically there's a bunch of other, sometimes camera specific subtleties I'm ignoring for brevity)
The above means that if you use something like set_tv96_direct outside of half shoot, and then read back the Tv value (from the propcase or get_tv96), you won't see the value you just set.
If called while get_shooting is true, these overrides are applied immediately (setting the propcases and, for things like ND and Av, potentially moving actuators), and the CHDK variables aren't touched. This allows you to override exposure where multiple shots are taken in a single half press cycle, like continuous mode, or when holding half and clicking full.
The reason it's done this was is that the normal exposure propcases (PROPACASE_TV etc) are normally updated by the Canon firmware at that point in half shoot. If auto-exposure is enabled, the values come from the camera AE calculation, if a setting is manually controlled, the value comes from the "user" propcases. To be effective, CHDK overrides need to be applied after the Canon firmware does its thing.
In contrast to the above, the CHDK "user" functions just set the corresponding "user" propcase immediately, which should be mostly equivalent to setting the value in the UI. The Canon firmware should take care of transferring these values into the standard propcases on shoot half, assuming the shooting mode allows manual control of the setting and no CHDK overrides interfere.
So getting back to your script, since "snap" waits for get_shooting to go false, the set_tv96_direct(s_start) and set_av96_direct(av) calls after snap are setting values that would be applied in the next half shoot cycle, wherever that may happen in the script, but it won't, for example, affect the live preview or UI display. This may be harmless, but it also may lead to confusion, especially in functions like bookend that can be called in multiple places.
Generally, I would recommend thinking of the normal overrides (again, set_tv96_direct and friends) as "set the exposure for the next half press or shot", as opposed to thinking of them like setting the controls in the UI. If you need to track values between shots, I'd suggest doing that in script variables rather than trying to "restore" them after a shot.
That said, calling an override function multiple times outside of half press doesn't *break* anything, it just updates the CHDK values, so whatever was set closest to the half shoot is the one that takes effect.