RegionBranchOpInterface and BranchOpInterface are allowed to make implicit type conversions along control-flow edges. In effect, this adds an interface method, areTypesCompatible, to both interfaces, which should return whether the types of corresponding successor operands and block arguments are compatible. Users of the interfaces, here on forth, must be aware that types may mismatch, although current users (in MLIR core), are not affected by this change. By default, type equality is used.
async.execute already has unequal types along control-flow edges (!async.value<f32> vs. f32), but it opted out of calling RegionBranchOpInterface::verifyTypes in its verifier. That method has now been removed and RegionBranchOpInterface will verify types along control edges by default in its verifier.
Can you sink this down to where it is actually used?