It is not that there is anything intrinsically wrong with these functions. You can technically use all of them and I have been using all of them, safely, for decades.
The issue is they are huge traps to the point that in a larger piece of software one can say "well, it's just not worth it".
You can go much, much, much further than that.
In couple embedded projects I worked some of the rules were:
* dynamic allocation after application has started is banned -- any heap buffers and data structures must be allocated at the start of the application and after that any allocation is a compile time error,
* any constructs that would prevent statically calculating stack usage were banned (for example any form of recursion except when exact recursion depth is ensured statically),
* any locks were banned,
* absolutely every data structure must have size ensured, in a simple way, beyond any reasonable doubt,
etc.