Above is undefined behaviour in C/C++.
Actually, the program has merely UB in C++ prior to C++11. Since C++11, the program is also ill-formed (i.e. compilers are allowed to refuse to compile it, and are required to diagnose the issue).
But it it seems pretty defined to me. You try to change a spot in read only memory, Operating system says no and that's the end of it.
Except that operating system says nothing when there is no operating system. The standards committees cannot simply decide that because one OS has certain behaviour that all language implementations - including those that have no concept of read only memory or even have an OS - should have that same behaviour.
But in reality, sometimes the change goes through and your string actually changes. How does that work
Simply, that language implementation didn't store the string literal in read only memory. It's not more complicated than that.
why is this undefined?
Because the language standards say so. They say so because the committees decided so. In case you are interested in their rationale, you're in luck since in this case it has been documented:
String literals are specified to be unmodifiable. This specification allows implementations to share copies of strings with identical text, to place string literals in read-only memory, and perform certain optimizations. However, string literals do not have the type array of const char, in order to avoid the problems of pointer type checking, particularly with library functions, since assigning a pointer to const char to a plain pointer to char is not valid. Those members of the Committee who insisted that string literals should be modifiable were content to have this practice designated a common extension (see F.5.5).