Two interesting problems in nis_maplist(). First, it is possible that
clnt_create() will return NULL. This was being caught, but no Python
error was being set. I use clnt_spcreateerror() to generate the value
of the exception.
But why would clnt_create() fail? It's because no server was being
found. And why was this? It was because nis_maplist() tried only to
get the NIS master for the first map in the aliases list, which is
passwd.byname, and guess what? That's the one NIS map CNRI does *not*
export! So the yp_master() call was failing to return a valid
server. I now cycle through all the map aliases until I find a valid
master. If not, a different exception is set.
I'm not sure this is the completely correct way to do all this, but
short of rewriting the entire nismodule.c (to expose the proper API to
Python), it should do the trick.
object pointers. Should be a bit faster than the C library's qsort(),
and doesn't have the prohibition on recursion that Solaris qsort() has
in the threaded version of their C library.
Thanks to discussions with Tim Peters.
(testall.out): obsolete. see individual test output files in the
Output directory.
(testall.py): now contains only the list of all tests
(autotest.py): The new testing harness. Supports -g option to
generate output files instead of verifying; -w option to warn about
non-tested optional modules; additional command line arguments to
generate or test individual tests (useful for generating output file
of new tests).
The raise logic has one additional feature: if you raise <class>,
<value> where <value> is not an instance, it will construct an
instance using <value> as argument. If <value> is None, <class> is
instantiated without arguments. If <value> is a tuple, it is used as
the argument list.
This feature is intended to make it easier to upgrade code from using
string exceptions to using class exceptions; without this feature,
you'd have to change every raise statement from ``raise X'' to ``raise
X()'' and from ``raise X, y'' to ``raise X(y)''. The latter is still
the recommended form (because it has no ambiguities about the number
of arguments), but this change makes the transition less painful.
I'm really not sure what the proper inputs are. I do flex the
function call though by passing in arguments of the proper type. I
don't try to exec the code object that gets returned!
Currently fairly minimal, but I'll be adding to this as needed. I
think it's pretty darn close.
To use this, just load the file and in a C buffer type:
M-x c-set-style RET python RET
[there are ways to automate much of this!]