A sound and complete chase procedure for constrained tuple-generating dependencies