I was wondering if tainted and constant are just special cases of having general properties on values. If a taint property was set, and the relevant commands checked it, and operators and other built-in functions propagated it, that would be the same thing. Likewise for constant: the relevant primitive (store to an lvalue, other modification primitives) would check it, and other things would propagate it according to the rules required (e.g. a constant container gives constant items when indexed).
So, generalize that idea, and it might be possible to have a richer security model, with attributes tagging individual values rather than globally for the thread.