fix #543 rewrite some code, make some fixes