Paul Du Bois wrote:
Perhaps it's the "cocall" keyword that could be removed, rather than "codef"? A revised semantics for "codef" could cause the body to use the most recent PEP revisions's "__cocall__ or __call__" mechanism for all function calls, perhaps at the expense of some runtime efficiency.
Thinking about it overnight, I came to exactly the same conclusion! This is actually the idea I had in mind right back at the beginning.
I think there are some good arguments in favour of it. If cocall sites have to be marked in some way, then when you change your mind about whether a function is a generator or not, you have to track down all the places where the function is called and change them as well. If that causes the enclosing functions to also become generators, then you have to track down all the calls to them as well, etc. etc. I can envisage this being a major hassle in a large program.
Whereas if we mark the functions instead of the calls, although some changes will still be necessary, there ought to be far fewer of them. Generally one tends to call functions more often than one defines them.
Also, it seems to me that changing 'def' into 'codef' is a far less intrusive change than sprinkling some kind of call marker throughout the body. It means we don't have to invent a weird new calling syntax. It also means you can read the function and think about it as normal code instead of having to be aware at every point of what kind of thing you're calling. It's more duck-typish.
So now I'm thinking that my original instinct was right: cofunctions should be functions that call things in a different way.