From c8042e10763bca064df257547d04ae3dfcdfaf91 Mon Sep 17 00:00:00 2001 From: Daryl McDaniel Date: Sat, 7 Nov 2015 19:19:19 +0000 Subject: [PATCH] AppPkg/Applications/Python/Python-2.7.10: Initial Checkin part 1/5. The Include, Parser, and Python directories from the cPython 2.7.10 distribution. These files are unchanged and set the baseline for subsequent commits. Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Daryl McDaniel git-svn-id: https://svn.code.sf.net/p/edk2/code/trunk/edk2@18737 6f19259b-4bc3-4df7-8a09-765794883524 --- .../Python/Python-2.7.10/Include/Python-ast.h | 535 ++ .../Python/Python-2.7.10/Include/Python.h | 178 + .../Python/Python-2.7.10/Include/abstract.h | 1396 ++++ .../Python/Python-2.7.10/Include/asdl.h | 45 + .../Python/Python-2.7.10/Include/ast.h | 13 + .../Python/Python-2.7.10/Include/bitset.h | 32 + .../Python/Python-2.7.10/Include/boolobject.h | 36 + .../Python-2.7.10/Include/bufferobject.h | 33 + .../Python-2.7.10/Include/bytearrayobject.h | 57 + .../Python-2.7.10/Include/bytes_methods.h | 75 + .../Python-2.7.10/Include/bytesobject.h | 27 + .../Python/Python-2.7.10/Include/cStringIO.h | 73 + .../Python/Python-2.7.10/Include/cellobject.h | 28 + .../Python/Python-2.7.10/Include/ceval.h | 153 + .../Python-2.7.10/Include/classobject.h | 83 + .../Python/Python-2.7.10/Include/cobject.h | 89 + .../Python/Python-2.7.10/Include/code.h | 107 + .../Python/Python-2.7.10/Include/codecs.h | 167 + .../Python/Python-2.7.10/Include/compile.h | 40 + .../Python-2.7.10/Include/complexobject.h | 66 + .../Python/Python-2.7.10/Include/datetime.h | 239 + .../Python-2.7.10/Include/descrobject.h | 94 + .../Python/Python-2.7.10/Include/dictobject.h | 156 + .../Python/Python-2.7.10/Include/dtoa.h | 15 + .../Python/Python-2.7.10/Include/enumobject.h | 17 + .../Python/Python-2.7.10/Include/errcode.h | 36 + .../Python/Python-2.7.10/Include/eval.h | 25 + .../Python/Python-2.7.10/Include/fileobject.h | 97 + .../Python-2.7.10/Include/floatobject.h | 140 + .../Python-2.7.10/Include/frameobject.h | 89 + .../Python/Python-2.7.10/Include/funcobject.h | 76 + .../Python/Python-2.7.10/Include/genobject.h | 40 + .../Python/Python-2.7.10/Include/graminit.h | 87 + .../Python/Python-2.7.10/Include/grammar.h | 93 + .../Python/Python-2.7.10/Include/import.h | 71 + .../Python/Python-2.7.10/Include/intobject.h | 81 + .../Python/Python-2.7.10/Include/intrcheck.h | 15 + .../Python/Python-2.7.10/Include/iterobject.h | 23 + .../Python/Python-2.7.10/Include/listobject.h | 68 + .../Python-2.7.10/Include/longintrepr.h | 103 + .../Python/Python-2.7.10/Include/longobject.h | 135 + .../Python/Python-2.7.10/Include/marshal.h | 25 + .../Python-2.7.10/Include/memoryobject.h | 74 + .../Python-2.7.10/Include/metagrammar.h | 18 + .../Python-2.7.10/Include/methodobject.h | 93 + .../Python/Python-2.7.10/Include/modsupport.h | 134 + .../Python-2.7.10/Include/moduleobject.h | 24 + .../Python/Python-2.7.10/Include/node.h | 41 + .../Python/Python-2.7.10/Include/object.h | 1013 +++ .../Python/Python-2.7.10/Include/objimpl.h | 354 + .../Python/Python-2.7.10/Include/opcode.h | 162 + .../Python/Python-2.7.10/Include/osdefs.h | 63 + .../Python/Python-2.7.10/Include/parsetok.h | 64 + .../Python/Python-2.7.10/Include/patchlevel.h | 43 + .../Python/Python-2.7.10/Include/pgen.h | 18 + .../Python-2.7.10/Include/pgenheaders.h | 42 + .../Python/Python-2.7.10/Include/py_curses.h | 176 + .../Python/Python-2.7.10/Include/pyarena.h | 62 + .../Python/Python-2.7.10/Include/pycapsule.h | 56 + .../Python/Python-2.7.10/Include/pyctype.h | 31 + .../Python/Python-2.7.10/Include/pydebug.h | 41 + .../Python/Python-2.7.10/Include/pyerrors.h | 329 + .../Python/Python-2.7.10/Include/pyexpat.h | 48 + .../Python/Python-2.7.10/Include/pyfpe.h | 176 + .../Python/Python-2.7.10/Include/pygetopt.h | 18 + .../Python-2.7.10/Include/pymacconfig.h | 102 + .../Python-2.7.10/Include/pymactoolbox.h | 217 + .../Python/Python-2.7.10/Include/pymath.h | 192 + .../Python/Python-2.7.10/Include/pymem.h | 122 + .../Python/Python-2.7.10/Include/pyport.h | 941 +++ .../Python/Python-2.7.10/Include/pystate.h | 200 + .../Python/Python-2.7.10/Include/pystrcmp.h | 23 + .../Python/Python-2.7.10/Include/pystrtod.h | 45 + .../Python/Python-2.7.10/Include/pythonrun.h | 182 + .../Python/Python-2.7.10/Include/pythread.h | 41 + .../Python-2.7.10/Include/rangeobject.h | 28 + .../Python/Python-2.7.10/Include/setobject.h | 99 + .../Python-2.7.10/Include/sliceobject.h | 44 + .../Python-2.7.10/Include/stringobject.h | 210 + .../Python-2.7.10/Include/structmember.h | 99 + .../Python/Python-2.7.10/Include/structseq.h | 41 + .../Python/Python-2.7.10/Include/symtable.h | 98 + .../Python/Python-2.7.10/Include/sysmodule.h | 31 + .../Python/Python-2.7.10/Include/timefuncs.h | 26 + .../Python/Python-2.7.10/Include/token.h | 85 + .../Python/Python-2.7.10/Include/traceback.h | 31 + .../Python-2.7.10/Include/tupleobject.h | 61 + .../Python/Python-2.7.10/Include/ucnhash.h | 33 + .../Python-2.7.10/Include/unicodeobject.h | 1413 ++++ .../Python/Python-2.7.10/Include/warnings.h | 23 + .../Python-2.7.10/Include/weakrefobject.h | 82 + .../Python/Python-2.7.10/Parser/acceler.c | 125 + .../Python/Python-2.7.10/Parser/bitset.c | 66 + .../Python/Python-2.7.10/Parser/firstsets.c | 113 + .../Python/Python-2.7.10/Parser/grammar.c | 254 + .../Python/Python-2.7.10/Parser/grammar1.c | 57 + .../Python/Python-2.7.10/Parser/listnode.c | 66 + .../Python/Python-2.7.10/Parser/metagrammar.c | 159 + .../Python/Python-2.7.10/Parser/myreadline.c | 218 + .../Python/Python-2.7.10/Parser/node.c | 164 + .../Python/Python-2.7.10/Parser/parser.c | 436 ++ .../Python/Python-2.7.10/Parser/parser.h | 42 + .../Python/Python-2.7.10/Parser/parsetok.c | 282 + .../Python/Python-2.7.10/Parser/tokenizer.c | 1755 +++++ .../Python/Python-2.7.10/Parser/tokenizer.h | 70 + .../Python/Python-2.7.10/Python/Python-ast.c | 6788 +++++++++++++++++ .../Python/Python-2.7.10/Python/_warnings.c | 911 +++ .../Python/Python-2.7.10/Python/asdl.c | 64 + .../Python/Python-2.7.10/Python/ast.c | 3587 +++++++++ .../Python/Python-2.7.10/Python/bltinmodule.c | 3061 ++++++++ .../Python/Python-2.7.10/Python/ceval.c | 4917 ++++++++++++ .../Python/Python-2.7.10/Python/codecs.c | 889 +++ .../Python/Python-2.7.10/Python/compile.c | 4003 ++++++++++ .../Python/Python-2.7.10/Python/dtoa.c | 2949 +++++++ .../Python-2.7.10/Python/dynload_stub.c | 11 + .../Python/Python-2.7.10/Python/errors.c | 827 ++ .../Python-2.7.10/Python/formatter_string.c | 17 + .../Python-2.7.10/Python/formatter_unicode.c | 18 + .../Python/Python-2.7.10/Python/frozen.c | 38 + .../Python/Python-2.7.10/Python/future.c | 137 + .../Python/Python-2.7.10/Python/getargs.c | 1908 +++++ .../Python/Python-2.7.10/Python/getcompiler.c | 28 + .../Python/Python-2.7.10/Python/getopt.c | 136 + .../Python/Python-2.7.10/Python/getplatform.c | 12 + .../Python/Python-2.7.10/Python/getversion.c | 15 + .../Python/Python-2.7.10/Python/graminit.c | 2177 ++++++ .../Python/Python-2.7.10/Python/import.c | 3481 +++++++++ .../Python/Python-2.7.10/Python/importdl.c | 78 + .../Python/Python-2.7.10/Python/importdl.h | 53 + .../Python/Python-2.7.10/Python/modsupport.c | 644 ++ .../Python/Python-2.7.10/Python/mysnprintf.c | 105 + .../Python/Python-2.7.10/Python/mystrtoul.c | 285 + .../Python/Python-2.7.10/Python/peephole.c | 667 ++ .../Python/Python-2.7.10/Python/pyarena.c | 213 + .../Python/Python-2.7.10/Python/pyctype.c | 214 + .../Python/Python-2.7.10/Python/pyfpe.c | 23 + .../Python/Python-2.7.10/Python/pymath.c | 79 + .../Python/Python-2.7.10/Python/pystate.c | 665 ++ .../Python/Python-2.7.10/Python/pystrcmp.c | 26 + .../Python/Python-2.7.10/Python/pystrtod.c | 1249 +++ .../Python/Python-2.7.10/Python/pythonrun.c | 2029 +++++ .../Python-2.7.10/Python/structmember.c | 363 + .../Python/Python-2.7.10/Python/symtable.c | 1556 ++++ .../Python/Python-2.7.10/Python/sysmodule.c | 1800 +++++ .../Python/Python-2.7.10/Python/traceback.c | 283 + 145 files changed, 62620 insertions(+) create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/Python-ast.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/Python.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/abstract.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/asdl.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/ast.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/bitset.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/boolobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/bufferobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/bytearrayobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/bytes_methods.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/bytesobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/cStringIO.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/cellobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/ceval.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/classobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/cobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/code.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/codecs.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/compile.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/complexobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/datetime.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/descrobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/dictobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/dtoa.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/enumobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/errcode.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/eval.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/fileobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/floatobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/frameobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/funcobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/genobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/graminit.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/grammar.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/import.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/intobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/intrcheck.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/iterobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/listobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/longintrepr.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/longobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/marshal.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/memoryobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/metagrammar.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/methodobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/modsupport.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/moduleobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/node.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/object.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/objimpl.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/opcode.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/osdefs.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/parsetok.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/patchlevel.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/pgen.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/pgenheaders.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/py_curses.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/pyarena.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/pycapsule.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/pyctype.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/pydebug.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/pyerrors.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/pyexpat.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/pyfpe.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/pygetopt.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/pymacconfig.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/pymactoolbox.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/pymath.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/pymem.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/pyport.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/pystate.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/pystrcmp.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/pystrtod.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/pythonrun.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/pythread.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/rangeobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/setobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/sliceobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/stringobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/structmember.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/structseq.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/symtable.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/sysmodule.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/timefuncs.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/token.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/traceback.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/tupleobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/ucnhash.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/unicodeobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/warnings.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Include/weakrefobject.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Parser/acceler.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Parser/bitset.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Parser/firstsets.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Parser/grammar.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Parser/grammar1.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Parser/listnode.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Parser/metagrammar.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Parser/myreadline.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Parser/node.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Parser/parser.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Parser/parser.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Parser/parsetok.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Parser/tokenizer.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Parser/tokenizer.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/Python-ast.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/_warnings.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/asdl.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/ast.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/bltinmodule.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/ceval.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/codecs.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/compile.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/dtoa.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/dynload_stub.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/errors.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/formatter_string.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/formatter_unicode.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/frozen.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/future.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/getargs.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/getcompiler.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/getopt.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/getplatform.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/getversion.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/graminit.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/import.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/importdl.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/importdl.h create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/modsupport.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/mysnprintf.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/mystrtoul.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/peephole.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/pyarena.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/pyctype.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/pyfpe.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/pymath.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/pystate.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/pystrcmp.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/pystrtod.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/pythonrun.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/structmember.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/symtable.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/sysmodule.c create mode 100644 AppPkg/Applications/Python/Python-2.7.10/Python/traceback.c diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/Python-ast.h b/AppPkg/Applications/Python/Python-2.7.10/Include/Python-ast.h new file mode 100644 index 0000000000..d794c3273f --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/Python-ast.h @@ -0,0 +1,535 @@ +/* File automatically generated by Parser/asdl_c.py. */ + +#include "asdl.h" + +typedef struct _mod *mod_ty; + +typedef struct _stmt *stmt_ty; + +typedef struct _expr *expr_ty; + +typedef enum _expr_context { Load=1, Store=2, Del=3, AugLoad=4, AugStore=5, + Param=6 } expr_context_ty; + +typedef struct _slice *slice_ty; + +typedef enum _boolop { And=1, Or=2 } boolop_ty; + +typedef enum _operator { Add=1, Sub=2, Mult=3, Div=4, Mod=5, Pow=6, LShift=7, + RShift=8, BitOr=9, BitXor=10, BitAnd=11, FloorDiv=12 } + operator_ty; + +typedef enum _unaryop { Invert=1, Not=2, UAdd=3, USub=4 } unaryop_ty; + +typedef enum _cmpop { Eq=1, NotEq=2, Lt=3, LtE=4, Gt=5, GtE=6, Is=7, IsNot=8, + In=9, NotIn=10 } cmpop_ty; + +typedef struct _comprehension *comprehension_ty; + +typedef struct _excepthandler *excepthandler_ty; + +typedef struct _arguments *arguments_ty; + +typedef struct _keyword *keyword_ty; + +typedef struct _alias *alias_ty; + + +enum _mod_kind {Module_kind=1, Interactive_kind=2, Expression_kind=3, + Suite_kind=4}; +struct _mod { + enum _mod_kind kind; + union { + struct { + asdl_seq *body; + } Module; + + struct { + asdl_seq *body; + } Interactive; + + struct { + expr_ty body; + } Expression; + + struct { + asdl_seq *body; + } Suite; + + } v; +}; + +enum _stmt_kind {FunctionDef_kind=1, ClassDef_kind=2, Return_kind=3, + Delete_kind=4, Assign_kind=5, AugAssign_kind=6, Print_kind=7, + For_kind=8, While_kind=9, If_kind=10, With_kind=11, + Raise_kind=12, TryExcept_kind=13, TryFinally_kind=14, + Assert_kind=15, Import_kind=16, ImportFrom_kind=17, + Exec_kind=18, Global_kind=19, Expr_kind=20, Pass_kind=21, + Break_kind=22, Continue_kind=23}; +struct _stmt { + enum _stmt_kind kind; + union { + struct { + identifier name; + arguments_ty args; + asdl_seq *body; + asdl_seq *decorator_list; + } FunctionDef; + + struct { + identifier name; + asdl_seq *bases; + asdl_seq *body; + asdl_seq *decorator_list; + } ClassDef; + + struct { + expr_ty value; + } Return; + + struct { + asdl_seq *targets; + } Delete; + + struct { + asdl_seq *targets; + expr_ty value; + } Assign; + + struct { + expr_ty target; + operator_ty op; + expr_ty value; + } AugAssign; + + struct { + expr_ty dest; + asdl_seq *values; + bool nl; + } Print; + + struct { + expr_ty target; + expr_ty iter; + asdl_seq *body; + asdl_seq *orelse; + } For; + + struct { + expr_ty test; + asdl_seq *body; + asdl_seq *orelse; + } While; + + struct { + expr_ty test; + asdl_seq *body; + asdl_seq *orelse; + } If; + + struct { + expr_ty context_expr; + expr_ty optional_vars; + asdl_seq *body; + } With; + + struct { + expr_ty type; + expr_ty inst; + expr_ty tback; + } Raise; + + struct { + asdl_seq *body; + asdl_seq *handlers; + asdl_seq *orelse; + } TryExcept; + + struct { + asdl_seq *body; + asdl_seq *finalbody; + } TryFinally; + + struct { + expr_ty test; + expr_ty msg; + } Assert; + + struct { + asdl_seq *names; + } Import; + + struct { + identifier module; + asdl_seq *names; + int level; + } ImportFrom; + + struct { + expr_ty body; + expr_ty globals; + expr_ty locals; + } Exec; + + struct { + asdl_seq *names; + } Global; + + struct { + expr_ty value; + } Expr; + + } v; + int lineno; + int col_offset; +}; + +enum _expr_kind {BoolOp_kind=1, BinOp_kind=2, UnaryOp_kind=3, Lambda_kind=4, + IfExp_kind=5, Dict_kind=6, Set_kind=7, ListComp_kind=8, + SetComp_kind=9, DictComp_kind=10, GeneratorExp_kind=11, + Yield_kind=12, Compare_kind=13, Call_kind=14, Repr_kind=15, + Num_kind=16, Str_kind=17, Attribute_kind=18, + Subscript_kind=19, Name_kind=20, List_kind=21, Tuple_kind=22}; +struct _expr { + enum _expr_kind kind; + union { + struct { + boolop_ty op; + asdl_seq *values; + } BoolOp; + + struct { + expr_ty left; + operator_ty op; + expr_ty right; + } BinOp; + + struct { + unaryop_ty op; + expr_ty operand; + } UnaryOp; + + struct { + arguments_ty args; + expr_ty body; + } Lambda; + + struct { + expr_ty test; + expr_ty body; + expr_ty orelse; + } IfExp; + + struct { + asdl_seq *keys; + asdl_seq *values; + } Dict; + + struct { + asdl_seq *elts; + } Set; + + struct { + expr_ty elt; + asdl_seq *generators; + } ListComp; + + struct { + expr_ty elt; + asdl_seq *generators; + } SetComp; + + struct { + expr_ty key; + expr_ty value; + asdl_seq *generators; + } DictComp; + + struct { + expr_ty elt; + asdl_seq *generators; + } GeneratorExp; + + struct { + expr_ty value; + } Yield; + + struct { + expr_ty left; + asdl_int_seq *ops; + asdl_seq *comparators; + } Compare; + + struct { + expr_ty func; + asdl_seq *args; + asdl_seq *keywords; + expr_ty starargs; + expr_ty kwargs; + } Call; + + struct { + expr_ty value; + } Repr; + + struct { + object n; + } Num; + + struct { + string s; + } Str; + + struct { + expr_ty value; + identifier attr; + expr_context_ty ctx; + } Attribute; + + struct { + expr_ty value; + slice_ty slice; + expr_context_ty ctx; + } Subscript; + + struct { + identifier id; + expr_context_ty ctx; + } Name; + + struct { + asdl_seq *elts; + expr_context_ty ctx; + } List; + + struct { + asdl_seq *elts; + expr_context_ty ctx; + } Tuple; + + } v; + int lineno; + int col_offset; +}; + +enum _slice_kind {Ellipsis_kind=1, Slice_kind=2, ExtSlice_kind=3, Index_kind=4}; +struct _slice { + enum _slice_kind kind; + union { + struct { + expr_ty lower; + expr_ty upper; + expr_ty step; + } Slice; + + struct { + asdl_seq *dims; + } ExtSlice; + + struct { + expr_ty value; + } Index; + + } v; +}; + +struct _comprehension { + expr_ty target; + expr_ty iter; + asdl_seq *ifs; +}; + +enum _excepthandler_kind {ExceptHandler_kind=1}; +struct _excepthandler { + enum _excepthandler_kind kind; + union { + struct { + expr_ty type; + expr_ty name; + asdl_seq *body; + } ExceptHandler; + + } v; + int lineno; + int col_offset; +}; + +struct _arguments { + asdl_seq *args; + identifier vararg; + identifier kwarg; + asdl_seq *defaults; +}; + +struct _keyword { + identifier arg; + expr_ty value; +}; + +struct _alias { + identifier name; + identifier asname; +}; + + +#define Module(a0, a1) _Py_Module(a0, a1) +mod_ty _Py_Module(asdl_seq * body, PyArena *arena); +#define Interactive(a0, a1) _Py_Interactive(a0, a1) +mod_ty _Py_Interactive(asdl_seq * body, PyArena *arena); +#define Expression(a0, a1) _Py_Expression(a0, a1) +mod_ty _Py_Expression(expr_ty body, PyArena *arena); +#define Suite(a0, a1) _Py_Suite(a0, a1) +mod_ty _Py_Suite(asdl_seq * body, PyArena *arena); +#define FunctionDef(a0, a1, a2, a3, a4, a5, a6) _Py_FunctionDef(a0, a1, a2, a3, a4, a5, a6) +stmt_ty _Py_FunctionDef(identifier name, arguments_ty args, asdl_seq * body, + asdl_seq * decorator_list, int lineno, int col_offset, + PyArena *arena); +#define ClassDef(a0, a1, a2, a3, a4, a5, a6) _Py_ClassDef(a0, a1, a2, a3, a4, a5, a6) +stmt_ty _Py_ClassDef(identifier name, asdl_seq * bases, asdl_seq * body, + asdl_seq * decorator_list, int lineno, int col_offset, + PyArena *arena); +#define Return(a0, a1, a2, a3) _Py_Return(a0, a1, a2, a3) +stmt_ty _Py_Return(expr_ty value, int lineno, int col_offset, PyArena *arena); +#define Delete(a0, a1, a2, a3) _Py_Delete(a0, a1, a2, a3) +stmt_ty _Py_Delete(asdl_seq * targets, int lineno, int col_offset, PyArena + *arena); +#define Assign(a0, a1, a2, a3, a4) _Py_Assign(a0, a1, a2, a3, a4) +stmt_ty _Py_Assign(asdl_seq * targets, expr_ty value, int lineno, int + col_offset, PyArena *arena); +#define AugAssign(a0, a1, a2, a3, a4, a5) _Py_AugAssign(a0, a1, a2, a3, a4, a5) +stmt_ty _Py_AugAssign(expr_ty target, operator_ty op, expr_ty value, int + lineno, int col_offset, PyArena *arena); +#define Print(a0, a1, a2, a3, a4, a5) _Py_Print(a0, a1, a2, a3, a4, a5) +stmt_ty _Py_Print(expr_ty dest, asdl_seq * values, bool nl, int lineno, int + col_offset, PyArena *arena); +#define For(a0, a1, a2, a3, a4, a5, a6) _Py_For(a0, a1, a2, a3, a4, a5, a6) +stmt_ty _Py_For(expr_ty target, expr_ty iter, asdl_seq * body, asdl_seq * + orelse, int lineno, int col_offset, PyArena *arena); +#define While(a0, a1, a2, a3, a4, a5) _Py_While(a0, a1, a2, a3, a4, a5) +stmt_ty _Py_While(expr_ty test, asdl_seq * body, asdl_seq * orelse, int lineno, + int col_offset, PyArena *arena); +#define If(a0, a1, a2, a3, a4, a5) _Py_If(a0, a1, a2, a3, a4, a5) +stmt_ty _Py_If(expr_ty test, asdl_seq * body, asdl_seq * orelse, int lineno, + int col_offset, PyArena *arena); +#define With(a0, a1, a2, a3, a4, a5) _Py_With(a0, a1, a2, a3, a4, a5) +stmt_ty _Py_With(expr_ty context_expr, expr_ty optional_vars, asdl_seq * body, + int lineno, int col_offset, PyArena *arena); +#define Raise(a0, a1, a2, a3, a4, a5) _Py_Raise(a0, a1, a2, a3, a4, a5) +stmt_ty _Py_Raise(expr_ty type, expr_ty inst, expr_ty tback, int lineno, int + col_offset, PyArena *arena); +#define TryExcept(a0, a1, a2, a3, a4, a5) _Py_TryExcept(a0, a1, a2, a3, a4, a5) +stmt_ty _Py_TryExcept(asdl_seq * body, asdl_seq * handlers, asdl_seq * orelse, + int lineno, int col_offset, PyArena *arena); +#define TryFinally(a0, a1, a2, a3, a4) _Py_TryFinally(a0, a1, a2, a3, a4) +stmt_ty _Py_TryFinally(asdl_seq * body, asdl_seq * finalbody, int lineno, int + col_offset, PyArena *arena); +#define Assert(a0, a1, a2, a3, a4) _Py_Assert(a0, a1, a2, a3, a4) +stmt_ty _Py_Assert(expr_ty test, expr_ty msg, int lineno, int col_offset, + PyArena *arena); +#define Import(a0, a1, a2, a3) _Py_Import(a0, a1, a2, a3) +stmt_ty _Py_Import(asdl_seq * names, int lineno, int col_offset, PyArena + *arena); +#define ImportFrom(a0, a1, a2, a3, a4, a5) _Py_ImportFrom(a0, a1, a2, a3, a4, a5) +stmt_ty _Py_ImportFrom(identifier module, asdl_seq * names, int level, int + lineno, int col_offset, PyArena *arena); +#define Exec(a0, a1, a2, a3, a4, a5) _Py_Exec(a0, a1, a2, a3, a4, a5) +stmt_ty _Py_Exec(expr_ty body, expr_ty globals, expr_ty locals, int lineno, int + col_offset, PyArena *arena); +#define Global(a0, a1, a2, a3) _Py_Global(a0, a1, a2, a3) +stmt_ty _Py_Global(asdl_seq * names, int lineno, int col_offset, PyArena + *arena); +#define Expr(a0, a1, a2, a3) _Py_Expr(a0, a1, a2, a3) +stmt_ty _Py_Expr(expr_ty value, int lineno, int col_offset, PyArena *arena); +#define Pass(a0, a1, a2) _Py_Pass(a0, a1, a2) +stmt_ty _Py_Pass(int lineno, int col_offset, PyArena *arena); +#define Break(a0, a1, a2) _Py_Break(a0, a1, a2) +stmt_ty _Py_Break(int lineno, int col_offset, PyArena *arena); +#define Continue(a0, a1, a2) _Py_Continue(a0, a1, a2) +stmt_ty _Py_Continue(int lineno, int col_offset, PyArena *arena); +#define BoolOp(a0, a1, a2, a3, a4) _Py_BoolOp(a0, a1, a2, a3, a4) +expr_ty _Py_BoolOp(boolop_ty op, asdl_seq * values, int lineno, int col_offset, + PyArena *arena); +#define BinOp(a0, a1, a2, a3, a4, a5) _Py_BinOp(a0, a1, a2, a3, a4, a5) +expr_ty _Py_BinOp(expr_ty left, operator_ty op, expr_ty right, int lineno, int + col_offset, PyArena *arena); +#define UnaryOp(a0, a1, a2, a3, a4) _Py_UnaryOp(a0, a1, a2, a3, a4) +expr_ty _Py_UnaryOp(unaryop_ty op, expr_ty operand, int lineno, int col_offset, + PyArena *arena); +#define Lambda(a0, a1, a2, a3, a4) _Py_Lambda(a0, a1, a2, a3, a4) +expr_ty _Py_Lambda(arguments_ty args, expr_ty body, int lineno, int col_offset, + PyArena *arena); +#define IfExp(a0, a1, a2, a3, a4, a5) _Py_IfExp(a0, a1, a2, a3, a4, a5) +expr_ty _Py_IfExp(expr_ty test, expr_ty body, expr_ty orelse, int lineno, int + col_offset, PyArena *arena); +#define Dict(a0, a1, a2, a3, a4) _Py_Dict(a0, a1, a2, a3, a4) +expr_ty _Py_Dict(asdl_seq * keys, asdl_seq * values, int lineno, int + col_offset, PyArena *arena); +#define Set(a0, a1, a2, a3) _Py_Set(a0, a1, a2, a3) +expr_ty _Py_Set(asdl_seq * elts, int lineno, int col_offset, PyArena *arena); +#define ListComp(a0, a1, a2, a3, a4) _Py_ListComp(a0, a1, a2, a3, a4) +expr_ty _Py_ListComp(expr_ty elt, asdl_seq * generators, int lineno, int + col_offset, PyArena *arena); +#define SetComp(a0, a1, a2, a3, a4) _Py_SetComp(a0, a1, a2, a3, a4) +expr_ty _Py_SetComp(expr_ty elt, asdl_seq * generators, int lineno, int + col_offset, PyArena *arena); +#define DictComp(a0, a1, a2, a3, a4, a5) _Py_DictComp(a0, a1, a2, a3, a4, a5) +expr_ty _Py_DictComp(expr_ty key, expr_ty value, asdl_seq * generators, int + lineno, int col_offset, PyArena *arena); +#define GeneratorExp(a0, a1, a2, a3, a4) _Py_GeneratorExp(a0, a1, a2, a3, a4) +expr_ty _Py_GeneratorExp(expr_ty elt, asdl_seq * generators, int lineno, int + col_offset, PyArena *arena); +#define Yield(a0, a1, a2, a3) _Py_Yield(a0, a1, a2, a3) +expr_ty _Py_Yield(expr_ty value, int lineno, int col_offset, PyArena *arena); +#define Compare(a0, a1, a2, a3, a4, a5) _Py_Compare(a0, a1, a2, a3, a4, a5) +expr_ty _Py_Compare(expr_ty left, asdl_int_seq * ops, asdl_seq * comparators, + int lineno, int col_offset, PyArena *arena); +#define Call(a0, a1, a2, a3, a4, a5, a6, a7) _Py_Call(a0, a1, a2, a3, a4, a5, a6, a7) +expr_ty _Py_Call(expr_ty func, asdl_seq * args, asdl_seq * keywords, expr_ty + starargs, expr_ty kwargs, int lineno, int col_offset, PyArena + *arena); +#define Repr(a0, a1, a2, a3) _Py_Repr(a0, a1, a2, a3) +expr_ty _Py_Repr(expr_ty value, int lineno, int col_offset, PyArena *arena); +#define Num(a0, a1, a2, a3) _Py_Num(a0, a1, a2, a3) +expr_ty _Py_Num(object n, int lineno, int col_offset, PyArena *arena); +#define Str(a0, a1, a2, a3) _Py_Str(a0, a1, a2, a3) +expr_ty _Py_Str(string s, int lineno, int col_offset, PyArena *arena); +#define Attribute(a0, a1, a2, a3, a4, a5) _Py_Attribute(a0, a1, a2, a3, a4, a5) +expr_ty _Py_Attribute(expr_ty value, identifier attr, expr_context_ty ctx, int + lineno, int col_offset, PyArena *arena); +#define Subscript(a0, a1, a2, a3, a4, a5) _Py_Subscript(a0, a1, a2, a3, a4, a5) +expr_ty _Py_Subscript(expr_ty value, slice_ty slice, expr_context_ty ctx, int + lineno, int col_offset, PyArena *arena); +#define Name(a0, a1, a2, a3, a4) _Py_Name(a0, a1, a2, a3, a4) +expr_ty _Py_Name(identifier id, expr_context_ty ctx, int lineno, int + col_offset, PyArena *arena); +#define List(a0, a1, a2, a3, a4) _Py_List(a0, a1, a2, a3, a4) +expr_ty _Py_List(asdl_seq * elts, expr_context_ty ctx, int lineno, int + col_offset, PyArena *arena); +#define Tuple(a0, a1, a2, a3, a4) _Py_Tuple(a0, a1, a2, a3, a4) +expr_ty _Py_Tuple(asdl_seq * elts, expr_context_ty ctx, int lineno, int + col_offset, PyArena *arena); +#define Ellipsis(a0) _Py_Ellipsis(a0) +slice_ty _Py_Ellipsis(PyArena *arena); +#define Slice(a0, a1, a2, a3) _Py_Slice(a0, a1, a2, a3) +slice_ty _Py_Slice(expr_ty lower, expr_ty upper, expr_ty step, PyArena *arena); +#define ExtSlice(a0, a1) _Py_ExtSlice(a0, a1) +slice_ty _Py_ExtSlice(asdl_seq * dims, PyArena *arena); +#define Index(a0, a1) _Py_Index(a0, a1) +slice_ty _Py_Index(expr_ty value, PyArena *arena); +#define comprehension(a0, a1, a2, a3) _Py_comprehension(a0, a1, a2, a3) +comprehension_ty _Py_comprehension(expr_ty target, expr_ty iter, asdl_seq * + ifs, PyArena *arena); +#define ExceptHandler(a0, a1, a2, a3, a4, a5) _Py_ExceptHandler(a0, a1, a2, a3, a4, a5) +excepthandler_ty _Py_ExceptHandler(expr_ty type, expr_ty name, asdl_seq * body, + int lineno, int col_offset, PyArena *arena); +#define arguments(a0, a1, a2, a3, a4) _Py_arguments(a0, a1, a2, a3, a4) +arguments_ty _Py_arguments(asdl_seq * args, identifier vararg, identifier + kwarg, asdl_seq * defaults, PyArena *arena); +#define keyword(a0, a1, a2) _Py_keyword(a0, a1, a2) +keyword_ty _Py_keyword(identifier arg, expr_ty value, PyArena *arena); +#define alias(a0, a1, a2) _Py_alias(a0, a1, a2) +alias_ty _Py_alias(identifier name, identifier asname, PyArena *arena); + +PyObject* PyAST_mod2obj(mod_ty t); +mod_ty PyAST_obj2mod(PyObject* ast, PyArena* arena, int mode); +int PyAST_Check(PyObject* obj); diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/Python.h b/AppPkg/Applications/Python/Python-2.7.10/Include/Python.h new file mode 100644 index 0000000000..5abad474c2 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/Python.h @@ -0,0 +1,178 @@ +#ifndef Py_PYTHON_H +#define Py_PYTHON_H +/* Since this is a "meta-include" file, no #ifdef __cplusplus / extern "C" { */ + +/* Include nearly all Python header files */ + +#include "patchlevel.h" +#include "pyconfig.h" +#include "pymacconfig.h" + +/* Cyclic gc is always enabled, starting with release 2.3a1. Supply the + * old symbol for the benefit of extension modules written before then + * that may be conditionalizing on it. The core doesn't use it anymore. + */ +#ifndef WITH_CYCLE_GC +#define WITH_CYCLE_GC 1 +#endif + +#include + +#ifndef UCHAR_MAX +#error "Something's broken. UCHAR_MAX should be defined in limits.h." +#endif + +#if UCHAR_MAX != 255 +#error "Python's source code assumes C's unsigned char is an 8-bit type." +#endif + +#if defined(__sgi) && defined(WITH_THREAD) && !defined(_SGI_MP_SOURCE) +#define _SGI_MP_SOURCE +#endif + +#include +#ifndef NULL +# error "Python.h requires that stdio.h define NULL." +#endif + +#include +#ifdef HAVE_ERRNO_H +#include +#endif +#include +#ifdef HAVE_UNISTD_H +#include +#endif + +/* For size_t? */ +#ifdef HAVE_STDDEF_H +#include +#endif + +/* CAUTION: Build setups should ensure that NDEBUG is defined on the + * compiler command line when building Python in release mode; else + * assert() calls won't be removed. + */ +#include + +#include "pyport.h" + +/* pyconfig.h or pyport.h may or may not define DL_IMPORT */ +#ifndef DL_IMPORT /* declarations for DLL import/export */ +#define DL_IMPORT(RTYPE) RTYPE +#endif +#ifndef DL_EXPORT /* declarations for DLL import/export */ +#define DL_EXPORT(RTYPE) RTYPE +#endif + +/* Debug-mode build with pymalloc implies PYMALLOC_DEBUG. + * PYMALLOC_DEBUG is in error if pymalloc is not in use. + */ +#if defined(Py_DEBUG) && defined(WITH_PYMALLOC) && !defined(PYMALLOC_DEBUG) +#define PYMALLOC_DEBUG +#endif +#if defined(PYMALLOC_DEBUG) && !defined(WITH_PYMALLOC) +#error "PYMALLOC_DEBUG requires WITH_PYMALLOC" +#endif +#include "pymath.h" +#include "pymem.h" + +#include "object.h" +#include "objimpl.h" + +#include "pydebug.h" + +#include "unicodeobject.h" +#include "intobject.h" +#include "boolobject.h" +#include "longobject.h" +#include "floatobject.h" +#ifndef WITHOUT_COMPLEX +#include "complexobject.h" +#endif +#include "rangeobject.h" +#include "stringobject.h" +#include "memoryobject.h" +#include "bufferobject.h" +#include "bytesobject.h" +#include "bytearrayobject.h" +#include "tupleobject.h" +#include "listobject.h" +#include "dictobject.h" +#include "enumobject.h" +#include "setobject.h" +#include "methodobject.h" +#include "moduleobject.h" +#include "funcobject.h" +#include "classobject.h" +#include "fileobject.h" +#include "cobject.h" +#include "pycapsule.h" +#include "traceback.h" +#include "sliceobject.h" +#include "cellobject.h" +#include "iterobject.h" +#include "genobject.h" +#include "descrobject.h" +#include "warnings.h" +#include "weakrefobject.h" + +#include "codecs.h" +#include "pyerrors.h" + +#include "pystate.h" + +#include "pyarena.h" +#include "modsupport.h" +#include "pythonrun.h" +#include "ceval.h" +#include "sysmodule.h" +#include "intrcheck.h" +#include "import.h" + +#include "abstract.h" + +#include "compile.h" +#include "eval.h" + +#include "pyctype.h" +#include "pystrtod.h" +#include "pystrcmp.h" +#include "dtoa.h" + +/* _Py_Mangle is defined in compile.c */ +PyAPI_FUNC(PyObject*) _Py_Mangle(PyObject *p, PyObject *name); + +/* PyArg_GetInt is deprecated and should not be used, use PyArg_Parse(). */ +#define PyArg_GetInt(v, a) PyArg_Parse((v), "i", (a)) + +/* PyArg_NoArgs should not be necessary. + Set ml_flags in the PyMethodDef to METH_NOARGS. */ +#define PyArg_NoArgs(v) PyArg_Parse(v, "") + +/* Argument must be a char or an int in [-128, 127] or [0, 255]. */ +#define Py_CHARMASK(c) ((unsigned char)((c) & 0xff)) + +#include "pyfpe.h" + +/* These definitions must match corresponding definitions in graminit.h. + There's code in compile.c that checks that they are the same. */ +#define Py_single_input 256 +#define Py_file_input 257 +#define Py_eval_input 258 + +#ifdef HAVE_PTH +/* GNU pth user-space thread support */ +#include +#endif + +/* Define macros for inline documentation. */ +#define PyDoc_VAR(name) static char name[] +#define PyDoc_STRVAR(name,str) PyDoc_VAR(name) = PyDoc_STR(str) +#ifdef WITH_DOC_STRINGS +#define PyDoc_STR(str) str +#else +#define PyDoc_STR(str) "" +#endif + +#endif /* !Py_PYTHON_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/abstract.h b/AppPkg/Applications/Python/Python-2.7.10/Include/abstract.h new file mode 100644 index 0000000000..61d56ff1a5 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/abstract.h @@ -0,0 +1,1396 @@ +#ifndef Py_ABSTRACTOBJECT_H +#define Py_ABSTRACTOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +#ifdef PY_SSIZE_T_CLEAN +#define PyObject_CallFunction _PyObject_CallFunction_SizeT +#define PyObject_CallMethod _PyObject_CallMethod_SizeT +#endif + +/* Abstract Object Interface (many thanks to Jim Fulton) */ + +/* + PROPOSAL: A Generic Python Object Interface for Python C Modules + +Problem + + Python modules written in C that must access Python objects must do + so through routines whose interfaces are described by a set of + include files. Unfortunately, these routines vary according to the + object accessed. To use these routines, the C programmer must check + the type of the object being used and must call a routine based on + the object type. For example, to access an element of a sequence, + the programmer must determine whether the sequence is a list or a + tuple: + + if(is_tupleobject(o)) + e=gettupleitem(o,i) + else if(is_listitem(o)) + e=getlistitem(o,i) + + If the programmer wants to get an item from another type of object + that provides sequence behavior, there is no clear way to do it + correctly. + + The persistent programmer may peruse object.h and find that the + _typeobject structure provides a means of invoking up to (currently + about) 41 special operators. So, for example, a routine can get an + item from any object that provides sequence behavior. However, to + use this mechanism, the programmer must make their code dependent on + the current Python implementation. + + Also, certain semantics, especially memory management semantics, may + differ by the type of object being used. Unfortunately, these + semantics are not clearly described in the current include files. + An abstract interface providing more consistent semantics is needed. + +Proposal + + I propose the creation of a standard interface (with an associated + library of routines and/or macros) for generically obtaining the + services of Python objects. This proposal can be viewed as one + components of a Python C interface consisting of several components. + + From the viewpoint of C access to Python services, we have (as + suggested by Guido in off-line discussions): + + - "Very high level layer": two or three functions that let you exec or + eval arbitrary Python code given as a string in a module whose name is + given, passing C values in and getting C values out using + mkvalue/getargs style format strings. This does not require the user + to declare any variables of type "PyObject *". This should be enough + to write a simple application that gets Python code from the user, + execs it, and returns the output or errors. (Error handling must also + be part of this API.) + + - "Abstract objects layer": which is the subject of this proposal. + It has many functions operating on objects, and lest you do many + things from C that you can also write in Python, without going + through the Python parser. + + - "Concrete objects layer": This is the public type-dependent + interface provided by the standard built-in types, such as floats, + strings, and lists. This interface exists and is currently + documented by the collection of include files provided with the + Python distributions. + + From the point of view of Python accessing services provided by C + modules: + + - "Python module interface": this interface consist of the basic + routines used to define modules and their members. Most of the + current extensions-writing guide deals with this interface. + + - "Built-in object interface": this is the interface that a new + built-in type must provide and the mechanisms and rules that a + developer of a new built-in type must use and follow. + + This proposal is a "first-cut" that is intended to spur + discussion. See especially the lists of notes. + + The Python C object interface will provide four protocols: object, + numeric, sequence, and mapping. Each protocol consists of a + collection of related operations. If an operation that is not + provided by a particular type is invoked, then a standard exception, + NotImplementedError is raised with a operation name as an argument. + In addition, for convenience this interface defines a set of + constructors for building objects of built-in types. This is needed + so new objects can be returned from C functions that otherwise treat + objects generically. + +Memory Management + + For all of the functions described in this proposal, if a function + retains a reference to a Python object passed as an argument, then the + function will increase the reference count of the object. It is + unnecessary for the caller to increase the reference count of an + argument in anticipation of the object's retention. + + All Python objects returned from functions should be treated as new + objects. Functions that return objects assume that the caller will + retain a reference and the reference count of the object has already + been incremented to account for this fact. A caller that does not + retain a reference to an object that is returned from a function + must decrement the reference count of the object (using + DECREF(object)) to prevent memory leaks. + + Note that the behavior mentioned here is different from the current + behavior for some objects (e.g. lists and tuples) when certain + type-specific routines are called directly (e.g. setlistitem). The + proposed abstraction layer will provide a consistent memory + management interface, correcting for inconsistent behavior for some + built-in types. + +Protocols + +xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx*/ + +/* Object Protocol: */ + + /* Implemented elsewhere: + + int PyObject_Print(PyObject *o, FILE *fp, int flags); + + Print an object, o, on file, fp. Returns -1 on + error. The flags argument is used to enable certain printing + options. The only option currently supported is Py_Print_RAW. + + (What should be said about Py_Print_RAW?) + + */ + + /* Implemented elsewhere: + + int PyObject_HasAttrString(PyObject *o, char *attr_name); + + Returns 1 if o has the attribute attr_name, and 0 otherwise. + This is equivalent to the Python expression: + hasattr(o,attr_name). + + This function always succeeds. + + */ + + /* Implemented elsewhere: + + PyObject* PyObject_GetAttrString(PyObject *o, char *attr_name); + + Retrieve an attributed named attr_name form object o. + Returns the attribute value on success, or NULL on failure. + This is the equivalent of the Python expression: o.attr_name. + + */ + + /* Implemented elsewhere: + + int PyObject_HasAttr(PyObject *o, PyObject *attr_name); + + Returns 1 if o has the attribute attr_name, and 0 otherwise. + This is equivalent to the Python expression: + hasattr(o,attr_name). + + This function always succeeds. + + */ + + /* Implemented elsewhere: + + PyObject* PyObject_GetAttr(PyObject *o, PyObject *attr_name); + + Retrieve an attributed named attr_name form object o. + Returns the attribute value on success, or NULL on failure. + This is the equivalent of the Python expression: o.attr_name. + + */ + + + /* Implemented elsewhere: + + int PyObject_SetAttrString(PyObject *o, char *attr_name, PyObject *v); + + Set the value of the attribute named attr_name, for object o, + to the value, v. Returns -1 on failure. This is + the equivalent of the Python statement: o.attr_name=v. + + */ + + /* Implemented elsewhere: + + int PyObject_SetAttr(PyObject *o, PyObject *attr_name, PyObject *v); + + Set the value of the attribute named attr_name, for object o, + to the value, v. Returns -1 on failure. This is + the equivalent of the Python statement: o.attr_name=v. + + */ + + /* implemented as a macro: + + int PyObject_DelAttrString(PyObject *o, char *attr_name); + + Delete attribute named attr_name, for object o. Returns + -1 on failure. This is the equivalent of the Python + statement: del o.attr_name. + + */ +#define PyObject_DelAttrString(O,A) PyObject_SetAttrString((O),(A),NULL) + + /* implemented as a macro: + + int PyObject_DelAttr(PyObject *o, PyObject *attr_name); + + Delete attribute named attr_name, for object o. Returns -1 + on failure. This is the equivalent of the Python + statement: del o.attr_name. + + */ +#define PyObject_DelAttr(O,A) PyObject_SetAttr((O),(A),NULL) + + PyAPI_FUNC(int) PyObject_Cmp(PyObject *o1, PyObject *o2, int *result); + + /* + Compare the values of o1 and o2 using a routine provided by + o1, if one exists, otherwise with a routine provided by o2. + The result of the comparison is returned in result. Returns + -1 on failure. This is the equivalent of the Python + statement: result=cmp(o1,o2). + + */ + + /* Implemented elsewhere: + + int PyObject_Compare(PyObject *o1, PyObject *o2); + + Compare the values of o1 and o2 using a routine provided by + o1, if one exists, otherwise with a routine provided by o2. + Returns the result of the comparison on success. On error, + the value returned is undefined. This is equivalent to the + Python expression: cmp(o1,o2). + + */ + + /* Implemented elsewhere: + + PyObject *PyObject_Repr(PyObject *o); + + Compute the string representation of object, o. Returns the + string representation on success, NULL on failure. This is + the equivalent of the Python expression: repr(o). + + Called by the repr() built-in function and by reverse quotes. + + */ + + /* Implemented elsewhere: + + PyObject *PyObject_Str(PyObject *o); + + Compute the string representation of object, o. Returns the + string representation on success, NULL on failure. This is + the equivalent of the Python expression: str(o).) + + Called by the str() built-in function and by the print + statement. + + */ + + /* Implemented elsewhere: + + PyObject *PyObject_Unicode(PyObject *o); + + Compute the unicode representation of object, o. Returns the + unicode representation on success, NULL on failure. This is + the equivalent of the Python expression: unistr(o).) + + Called by the unistr() built-in function. + + */ + + /* Declared elsewhere + + PyAPI_FUNC(int) PyCallable_Check(PyObject *o); + + Determine if the object, o, is callable. Return 1 if the + object is callable and 0 otherwise. + + This function always succeeds. + + */ + + + + PyAPI_FUNC(PyObject *) PyObject_Call(PyObject *callable_object, + PyObject *args, PyObject *kw); + + /* + Call a callable Python object, callable_object, with + arguments and keywords arguments. The 'args' argument can not be + NULL, but the 'kw' argument can be NULL. + + */ + + PyAPI_FUNC(PyObject *) PyObject_CallObject(PyObject *callable_object, + PyObject *args); + + /* + Call a callable Python object, callable_object, with + arguments given by the tuple, args. If no arguments are + needed, then args may be NULL. Returns the result of the + call on success, or NULL on failure. This is the equivalent + of the Python expression: apply(o,args). + + */ + + PyAPI_FUNC(PyObject *) PyObject_CallFunction(PyObject *callable_object, + char *format, ...); + + /* + Call a callable Python object, callable_object, with a + variable number of C arguments. The C arguments are described + using a mkvalue-style format string. The format may be NULL, + indicating that no arguments are provided. Returns the + result of the call on success, or NULL on failure. This is + the equivalent of the Python expression: apply(o,args). + + */ + + + PyAPI_FUNC(PyObject *) PyObject_CallMethod(PyObject *o, char *m, + char *format, ...); + + /* + Call the method named m of object o with a variable number of + C arguments. The C arguments are described by a mkvalue + format string. The format may be NULL, indicating that no + arguments are provided. Returns the result of the call on + success, or NULL on failure. This is the equivalent of the + Python expression: o.method(args). + */ + + PyAPI_FUNC(PyObject *) _PyObject_CallFunction_SizeT(PyObject *callable, + char *format, ...); + PyAPI_FUNC(PyObject *) _PyObject_CallMethod_SizeT(PyObject *o, + char *name, + char *format, ...); + + PyAPI_FUNC(PyObject *) PyObject_CallFunctionObjArgs(PyObject *callable, + ...); + + /* + Call a callable Python object, callable_object, with a + variable number of C arguments. The C arguments are provided + as PyObject * values, terminated by a NULL. Returns the + result of the call on success, or NULL on failure. This is + the equivalent of the Python expression: apply(o,args). + */ + + + PyAPI_FUNC(PyObject *) PyObject_CallMethodObjArgs(PyObject *o, + PyObject *m, ...); + + /* + Call the method named m of object o with a variable number of + C arguments. The C arguments are provided as PyObject * + values, terminated by NULL. Returns the result of the call + on success, or NULL on failure. This is the equivalent of + the Python expression: o.method(args). + */ + + + /* Implemented elsewhere: + + long PyObject_Hash(PyObject *o); + + Compute and return the hash, hash_value, of an object, o. On + failure, return -1. This is the equivalent of the Python + expression: hash(o). + + */ + + + /* Implemented elsewhere: + + int PyObject_IsTrue(PyObject *o); + + Returns 1 if the object, o, is considered to be true, 0 if o is + considered to be false and -1 on failure. This is equivalent to the + Python expression: not not o + + */ + + /* Implemented elsewhere: + + int PyObject_Not(PyObject *o); + + Returns 0 if the object, o, is considered to be true, 1 if o is + considered to be false and -1 on failure. This is equivalent to the + Python expression: not o + + */ + + PyAPI_FUNC(PyObject *) PyObject_Type(PyObject *o); + + /* + On success, returns a type object corresponding to the object + type of object o. On failure, returns NULL. This is + equivalent to the Python expression: type(o). + */ + + PyAPI_FUNC(Py_ssize_t) PyObject_Size(PyObject *o); + + /* + Return the size of object o. If the object, o, provides + both sequence and mapping protocols, the sequence size is + returned. On error, -1 is returned. This is the equivalent + to the Python expression: len(o). + + */ + + /* For DLL compatibility */ +#undef PyObject_Length + PyAPI_FUNC(Py_ssize_t) PyObject_Length(PyObject *o); +#define PyObject_Length PyObject_Size + + PyAPI_FUNC(Py_ssize_t) _PyObject_LengthHint(PyObject *o, Py_ssize_t); + + /* + Guess the size of object o using len(o) or o.__length_hint__(). + If neither of those return a non-negative value, then return the + default value. If one of the calls fails, this function returns -1. + */ + + PyAPI_FUNC(PyObject *) PyObject_GetItem(PyObject *o, PyObject *key); + + /* + Return element of o corresponding to the object, key, or NULL + on failure. This is the equivalent of the Python expression: + o[key]. + + */ + + PyAPI_FUNC(int) PyObject_SetItem(PyObject *o, PyObject *key, PyObject *v); + + /* + Map the object, key, to the value, v. Returns + -1 on failure. This is the equivalent of the Python + statement: o[key]=v. + */ + + PyAPI_FUNC(int) PyObject_DelItemString(PyObject *o, char *key); + + /* + Remove the mapping for object, key, from the object *o. + Returns -1 on failure. This is equivalent to + the Python statement: del o[key]. + */ + + PyAPI_FUNC(int) PyObject_DelItem(PyObject *o, PyObject *key); + + /* + Delete the mapping for key from *o. Returns -1 on failure. + This is the equivalent of the Python statement: del o[key]. + */ + + PyAPI_FUNC(int) PyObject_AsCharBuffer(PyObject *obj, + const char **buffer, + Py_ssize_t *buffer_len); + + /* + Takes an arbitrary object which must support the (character, + single segment) buffer interface and returns a pointer to a + read-only memory location useable as character based input + for subsequent processing. + + 0 is returned on success. buffer and buffer_len are only + set in case no error occurs. Otherwise, -1 is returned and + an exception set. + + */ + + PyAPI_FUNC(int) PyObject_CheckReadBuffer(PyObject *obj); + + /* + Checks whether an arbitrary object supports the (character, + single segment) buffer interface. Returns 1 on success, 0 + on failure. + + */ + + PyAPI_FUNC(int) PyObject_AsReadBuffer(PyObject *obj, + const void **buffer, + Py_ssize_t *buffer_len); + + /* + Same as PyObject_AsCharBuffer() except that this API expects + (readable, single segment) buffer interface and returns a + pointer to a read-only memory location which can contain + arbitrary data. + + 0 is returned on success. buffer and buffer_len are only + set in case no error occurs. Otherwise, -1 is returned and + an exception set. + + */ + + PyAPI_FUNC(int) PyObject_AsWriteBuffer(PyObject *obj, + void **buffer, + Py_ssize_t *buffer_len); + + /* + Takes an arbitrary object which must support the (writeable, + single segment) buffer interface and returns a pointer to a + writeable memory location in buffer of size buffer_len. + + 0 is returned on success. buffer and buffer_len are only + set in case no error occurs. Otherwise, -1 is returned and + an exception set. + + */ + + /* new buffer API */ + +#define PyObject_CheckBuffer(obj) \ + (((obj)->ob_type->tp_as_buffer != NULL) && \ + (PyType_HasFeature((obj)->ob_type, Py_TPFLAGS_HAVE_NEWBUFFER)) && \ + ((obj)->ob_type->tp_as_buffer->bf_getbuffer != NULL)) + + /* Return 1 if the getbuffer function is available, otherwise + return 0 */ + + PyAPI_FUNC(int) PyObject_GetBuffer(PyObject *obj, Py_buffer *view, + int flags); + + /* This is a C-API version of the getbuffer function call. It checks + to make sure object has the required function pointer and issues the + call. Returns -1 and raises an error on failure and returns 0 on + success + */ + + + PyAPI_FUNC(void *) PyBuffer_GetPointer(Py_buffer *view, Py_ssize_t *indices); + + /* Get the memory area pointed to by the indices for the buffer given. + Note that view->ndim is the assumed size of indices + */ + + PyAPI_FUNC(int) PyBuffer_SizeFromFormat(const char *); + + /* Return the implied itemsize of the data-format area from a + struct-style description */ + + + + PyAPI_FUNC(int) PyBuffer_ToContiguous(void *buf, Py_buffer *view, + Py_ssize_t len, char fort); + + PyAPI_FUNC(int) PyBuffer_FromContiguous(Py_buffer *view, void *buf, + Py_ssize_t len, char fort); + + + /* Copy len bytes of data from the contiguous chunk of memory + pointed to by buf into the buffer exported by obj. Return + 0 on success and return -1 and raise a PyBuffer_Error on + error (i.e. the object does not have a buffer interface or + it is not working). + + If fort is 'F' and the object is multi-dimensional, + then the data will be copied into the array in + Fortran-style (first dimension varies the fastest). If + fort is 'C', then the data will be copied into the array + in C-style (last dimension varies the fastest). If fort + is 'A', then it does not matter and the copy will be made + in whatever way is more efficient. + + */ + + PyAPI_FUNC(int) PyObject_CopyData(PyObject *dest, PyObject *src); + + /* Copy the data from the src buffer to the buffer of destination + */ + + PyAPI_FUNC(int) PyBuffer_IsContiguous(Py_buffer *view, char fort); + + + PyAPI_FUNC(void) PyBuffer_FillContiguousStrides(int ndims, + Py_ssize_t *shape, + Py_ssize_t *strides, + int itemsize, + char fort); + + /* Fill the strides array with byte-strides of a contiguous + (Fortran-style if fort is 'F' or C-style otherwise) + array of the given shape with the given number of bytes + per element. + */ + + PyAPI_FUNC(int) PyBuffer_FillInfo(Py_buffer *view, PyObject *o, void *buf, + Py_ssize_t len, int readonly, + int flags); + + /* Fills in a buffer-info structure correctly for an exporter + that can only share a contiguous chunk of memory of + "unsigned bytes" of the given length. Returns 0 on success + and -1 (with raising an error) on error. + */ + + PyAPI_FUNC(void) PyBuffer_Release(Py_buffer *view); + + /* Releases a Py_buffer obtained from getbuffer ParseTuple's s*. + */ + + PyAPI_FUNC(PyObject *) PyObject_Format(PyObject* obj, + PyObject *format_spec); + /* + Takes an arbitrary object and returns the result of + calling obj.__format__(format_spec). + */ + +/* Iterators */ + + PyAPI_FUNC(PyObject *) PyObject_GetIter(PyObject *); + /* Takes an object and returns an iterator for it. + This is typically a new iterator but if the argument + is an iterator, this returns itself. */ + +#define PyIter_Check(obj) \ + (PyType_HasFeature((obj)->ob_type, Py_TPFLAGS_HAVE_ITER) && \ + (obj)->ob_type->tp_iternext != NULL && \ + (obj)->ob_type->tp_iternext != &_PyObject_NextNotImplemented) + + PyAPI_FUNC(PyObject *) PyIter_Next(PyObject *); + /* Takes an iterator object and calls its tp_iternext slot, + returning the next value. If the iterator is exhausted, + this returns NULL without setting an exception. + NULL with an exception means an error occurred. */ + +/* Number Protocol:*/ + + PyAPI_FUNC(int) PyNumber_Check(PyObject *o); + + /* + Returns 1 if the object, o, provides numeric protocols, and + false otherwise. + + This function always succeeds. + + */ + + PyAPI_FUNC(PyObject *) PyNumber_Add(PyObject *o1, PyObject *o2); + + /* + Returns the result of adding o1 and o2, or null on failure. + This is the equivalent of the Python expression: o1+o2. + + + */ + + PyAPI_FUNC(PyObject *) PyNumber_Subtract(PyObject *o1, PyObject *o2); + + /* + Returns the result of subtracting o2 from o1, or null on + failure. This is the equivalent of the Python expression: + o1-o2. + + */ + + PyAPI_FUNC(PyObject *) PyNumber_Multiply(PyObject *o1, PyObject *o2); + + /* + Returns the result of multiplying o1 and o2, or null on + failure. This is the equivalent of the Python expression: + o1*o2. + + + */ + + PyAPI_FUNC(PyObject *) PyNumber_Divide(PyObject *o1, PyObject *o2); + + /* + Returns the result of dividing o1 by o2, or null on failure. + This is the equivalent of the Python expression: o1/o2. + + + */ + + PyAPI_FUNC(PyObject *) PyNumber_FloorDivide(PyObject *o1, PyObject *o2); + + /* + Returns the result of dividing o1 by o2 giving an integral result, + or null on failure. + This is the equivalent of the Python expression: o1//o2. + + + */ + + PyAPI_FUNC(PyObject *) PyNumber_TrueDivide(PyObject *o1, PyObject *o2); + + /* + Returns the result of dividing o1 by o2 giving a float result, + or null on failure. + This is the equivalent of the Python expression: o1/o2. + + + */ + + PyAPI_FUNC(PyObject *) PyNumber_Remainder(PyObject *o1, PyObject *o2); + + /* + Returns the remainder of dividing o1 by o2, or null on + failure. This is the equivalent of the Python expression: + o1%o2. + + + */ + + PyAPI_FUNC(PyObject *) PyNumber_Divmod(PyObject *o1, PyObject *o2); + + /* + See the built-in function divmod. Returns NULL on failure. + This is the equivalent of the Python expression: + divmod(o1,o2). + + + */ + + PyAPI_FUNC(PyObject *) PyNumber_Power(PyObject *o1, PyObject *o2, + PyObject *o3); + + /* + See the built-in function pow. Returns NULL on failure. + This is the equivalent of the Python expression: + pow(o1,o2,o3), where o3 is optional. + + */ + + PyAPI_FUNC(PyObject *) PyNumber_Negative(PyObject *o); + + /* + Returns the negation of o on success, or null on failure. + This is the equivalent of the Python expression: -o. + + */ + + PyAPI_FUNC(PyObject *) PyNumber_Positive(PyObject *o); + + /* + Returns the (what?) of o on success, or NULL on failure. + This is the equivalent of the Python expression: +o. + + */ + + PyAPI_FUNC(PyObject *) PyNumber_Absolute(PyObject *o); + + /* + Returns the absolute value of o, or null on failure. This is + the equivalent of the Python expression: abs(o). + + */ + + PyAPI_FUNC(PyObject *) PyNumber_Invert(PyObject *o); + + /* + Returns the bitwise negation of o on success, or NULL on + failure. This is the equivalent of the Python expression: + ~o. + + + */ + + PyAPI_FUNC(PyObject *) PyNumber_Lshift(PyObject *o1, PyObject *o2); + + /* + Returns the result of left shifting o1 by o2 on success, or + NULL on failure. This is the equivalent of the Python + expression: o1 << o2. + + + */ + + PyAPI_FUNC(PyObject *) PyNumber_Rshift(PyObject *o1, PyObject *o2); + + /* + Returns the result of right shifting o1 by o2 on success, or + NULL on failure. This is the equivalent of the Python + expression: o1 >> o2. + + */ + + PyAPI_FUNC(PyObject *) PyNumber_And(PyObject *o1, PyObject *o2); + + /* + Returns the result of bitwise and of o1 and o2 on success, or + NULL on failure. This is the equivalent of the Python + expression: o1&o2. + + + */ + + PyAPI_FUNC(PyObject *) PyNumber_Xor(PyObject *o1, PyObject *o2); + + /* + Returns the bitwise exclusive or of o1 by o2 on success, or + NULL on failure. This is the equivalent of the Python + expression: o1^o2. + + + */ + + PyAPI_FUNC(PyObject *) PyNumber_Or(PyObject *o1, PyObject *o2); + + /* + Returns the result of bitwise or on o1 and o2 on success, or + NULL on failure. This is the equivalent of the Python + expression: o1|o2. + + */ + + /* Implemented elsewhere: + + int PyNumber_Coerce(PyObject **p1, PyObject **p2); + + This function takes the addresses of two variables of type + PyObject*. + + If the objects pointed to by *p1 and *p2 have the same type, + increment their reference count and return 0 (success). + If the objects can be converted to a common numeric type, + replace *p1 and *p2 by their converted value (with 'new' + reference counts), and return 0. + If no conversion is possible, or if some other error occurs, + return -1 (failure) and don't increment the reference counts. + The call PyNumber_Coerce(&o1, &o2) is equivalent to the Python + statement o1, o2 = coerce(o1, o2). + + */ + +#define PyIndex_Check(obj) \ + ((obj)->ob_type->tp_as_number != NULL && \ + PyType_HasFeature((obj)->ob_type, Py_TPFLAGS_HAVE_INDEX) && \ + (obj)->ob_type->tp_as_number->nb_index != NULL) + + PyAPI_FUNC(PyObject *) PyNumber_Index(PyObject *o); + + /* + Returns the object converted to a Python long or int + or NULL with an error raised on failure. + */ + + PyAPI_FUNC(Py_ssize_t) PyNumber_AsSsize_t(PyObject *o, PyObject *exc); + + /* + Returns the Integral instance converted to an int. The + instance is expected to be int or long or have an __int__ + method. Steals integral's reference. error_format will be + used to create the TypeError if integral isn't actually an + Integral instance. error_format should be a format string + that can accept a char* naming integral's type. + */ + + PyAPI_FUNC(PyObject *) _PyNumber_ConvertIntegralToInt( + PyObject *integral, + const char* error_format); + + /* + Returns the object converted to Py_ssize_t by going through + PyNumber_Index first. If an overflow error occurs while + converting the int-or-long to Py_ssize_t, then the second argument + is the error-type to return. If it is NULL, then the overflow error + is cleared and the value is clipped. + */ + + PyAPI_FUNC(PyObject *) PyNumber_Int(PyObject *o); + + /* + Returns the o converted to an integer object on success, or + NULL on failure. This is the equivalent of the Python + expression: int(o). + + */ + + PyAPI_FUNC(PyObject *) PyNumber_Long(PyObject *o); + + /* + Returns the o converted to a long integer object on success, + or NULL on failure. This is the equivalent of the Python + expression: long(o). + + */ + + PyAPI_FUNC(PyObject *) PyNumber_Float(PyObject *o); + + /* + Returns the o converted to a float object on success, or NULL + on failure. This is the equivalent of the Python expression: + float(o). + */ + +/* In-place variants of (some of) the above number protocol functions */ + + PyAPI_FUNC(PyObject *) PyNumber_InPlaceAdd(PyObject *o1, PyObject *o2); + + /* + Returns the result of adding o2 to o1, possibly in-place, or null + on failure. This is the equivalent of the Python expression: + o1 += o2. + + */ + + PyAPI_FUNC(PyObject *) PyNumber_InPlaceSubtract(PyObject *o1, PyObject *o2); + + /* + Returns the result of subtracting o2 from o1, possibly in-place or + null on failure. This is the equivalent of the Python expression: + o1 -= o2. + + */ + + PyAPI_FUNC(PyObject *) PyNumber_InPlaceMultiply(PyObject *o1, PyObject *o2); + + /* + Returns the result of multiplying o1 by o2, possibly in-place, or + null on failure. This is the equivalent of the Python expression: + o1 *= o2. + + */ + + PyAPI_FUNC(PyObject *) PyNumber_InPlaceDivide(PyObject *o1, PyObject *o2); + + /* + Returns the result of dividing o1 by o2, possibly in-place, or null + on failure. This is the equivalent of the Python expression: + o1 /= o2. + + */ + + PyAPI_FUNC(PyObject *) PyNumber_InPlaceFloorDivide(PyObject *o1, + PyObject *o2); + + /* + Returns the result of dividing o1 by o2 giving an integral result, + possibly in-place, or null on failure. + This is the equivalent of the Python expression: + o1 /= o2. + + */ + + PyAPI_FUNC(PyObject *) PyNumber_InPlaceTrueDivide(PyObject *o1, + PyObject *o2); + + /* + Returns the result of dividing o1 by o2 giving a float result, + possibly in-place, or null on failure. + This is the equivalent of the Python expression: + o1 /= o2. + + */ + + PyAPI_FUNC(PyObject *) PyNumber_InPlaceRemainder(PyObject *o1, PyObject *o2); + + /* + Returns the remainder of dividing o1 by o2, possibly in-place, or + null on failure. This is the equivalent of the Python expression: + o1 %= o2. + + */ + + PyAPI_FUNC(PyObject *) PyNumber_InPlacePower(PyObject *o1, PyObject *o2, + PyObject *o3); + + /* + Returns the result of raising o1 to the power of o2, possibly + in-place, or null on failure. This is the equivalent of the Python + expression: o1 **= o2, or pow(o1, o2, o3) if o3 is present. + + */ + + PyAPI_FUNC(PyObject *) PyNumber_InPlaceLshift(PyObject *o1, PyObject *o2); + + /* + Returns the result of left shifting o1 by o2, possibly in-place, or + null on failure. This is the equivalent of the Python expression: + o1 <<= o2. + + */ + + PyAPI_FUNC(PyObject *) PyNumber_InPlaceRshift(PyObject *o1, PyObject *o2); + + /* + Returns the result of right shifting o1 by o2, possibly in-place or + null on failure. This is the equivalent of the Python expression: + o1 >>= o2. + + */ + + PyAPI_FUNC(PyObject *) PyNumber_InPlaceAnd(PyObject *o1, PyObject *o2); + + /* + Returns the result of bitwise and of o1 and o2, possibly in-place, + or null on failure. This is the equivalent of the Python + expression: o1 &= o2. + + */ + + PyAPI_FUNC(PyObject *) PyNumber_InPlaceXor(PyObject *o1, PyObject *o2); + + /* + Returns the bitwise exclusive or of o1 by o2, possibly in-place, or + null on failure. This is the equivalent of the Python expression: + o1 ^= o2. + + */ + + PyAPI_FUNC(PyObject *) PyNumber_InPlaceOr(PyObject *o1, PyObject *o2); + + /* + Returns the result of bitwise or of o1 and o2, possibly in-place, + or null on failure. This is the equivalent of the Python + expression: o1 |= o2. + + */ + + + PyAPI_FUNC(PyObject *) PyNumber_ToBase(PyObject *n, int base); + + /* + Returns the integer n converted to a string with a base, with a base + marker of 0b, 0o or 0x prefixed if applicable. + If n is not an int object, it is converted with PyNumber_Index first. + */ + + +/* Sequence protocol:*/ + + PyAPI_FUNC(int) PySequence_Check(PyObject *o); + + /* + Return 1 if the object provides sequence protocol, and zero + otherwise. + + This function always succeeds. + + */ + + PyAPI_FUNC(Py_ssize_t) PySequence_Size(PyObject *o); + + /* + Return the size of sequence object o, or -1 on failure. + + */ + + /* For DLL compatibility */ +#undef PySequence_Length + PyAPI_FUNC(Py_ssize_t) PySequence_Length(PyObject *o); +#define PySequence_Length PySequence_Size + + + PyAPI_FUNC(PyObject *) PySequence_Concat(PyObject *o1, PyObject *o2); + + /* + Return the concatenation of o1 and o2 on success, and NULL on + failure. This is the equivalent of the Python + expression: o1+o2. + + */ + + PyAPI_FUNC(PyObject *) PySequence_Repeat(PyObject *o, Py_ssize_t count); + + /* + Return the result of repeating sequence object o count times, + or NULL on failure. This is the equivalent of the Python + expression: o1*count. + + */ + + PyAPI_FUNC(PyObject *) PySequence_GetItem(PyObject *o, Py_ssize_t i); + + /* + Return the ith element of o, or NULL on failure. This is the + equivalent of the Python expression: o[i]. + */ + + PyAPI_FUNC(PyObject *) PySequence_GetSlice(PyObject *o, Py_ssize_t i1, Py_ssize_t i2); + + /* + Return the slice of sequence object o between i1 and i2, or + NULL on failure. This is the equivalent of the Python + expression: o[i1:i2]. + + */ + + PyAPI_FUNC(int) PySequence_SetItem(PyObject *o, Py_ssize_t i, PyObject *v); + + /* + Assign object v to the ith element of o. Returns + -1 on failure. This is the equivalent of the Python + statement: o[i]=v. + + */ + + PyAPI_FUNC(int) PySequence_DelItem(PyObject *o, Py_ssize_t i); + + /* + Delete the ith element of object v. Returns + -1 on failure. This is the equivalent of the Python + statement: del o[i]. + */ + + PyAPI_FUNC(int) PySequence_SetSlice(PyObject *o, Py_ssize_t i1, Py_ssize_t i2, + PyObject *v); + + /* + Assign the sequence object, v, to the slice in sequence + object, o, from i1 to i2. Returns -1 on failure. This is the + equivalent of the Python statement: o[i1:i2]=v. + */ + + PyAPI_FUNC(int) PySequence_DelSlice(PyObject *o, Py_ssize_t i1, Py_ssize_t i2); + + /* + Delete the slice in sequence object, o, from i1 to i2. + Returns -1 on failure. This is the equivalent of the Python + statement: del o[i1:i2]. + */ + + PyAPI_FUNC(PyObject *) PySequence_Tuple(PyObject *o); + + /* + Returns the sequence, o, as a tuple on success, and NULL on failure. + This is equivalent to the Python expression: tuple(o) + */ + + + PyAPI_FUNC(PyObject *) PySequence_List(PyObject *o); + /* + Returns the sequence, o, as a list on success, and NULL on failure. + This is equivalent to the Python expression: list(o) + */ + + PyAPI_FUNC(PyObject *) PySequence_Fast(PyObject *o, const char* m); + /* + Return the sequence, o, as a list, unless it's already a + tuple or list. Use PySequence_Fast_GET_ITEM to access the + members of this list, and PySequence_Fast_GET_SIZE to get its length. + + Returns NULL on failure. If the object does not support iteration, + raises a TypeError exception with m as the message text. + */ + +#define PySequence_Fast_GET_SIZE(o) \ + (PyList_Check(o) ? PyList_GET_SIZE(o) : PyTuple_GET_SIZE(o)) + /* + Return the size of o, assuming that o was returned by + PySequence_Fast and is not NULL. + */ + +#define PySequence_Fast_GET_ITEM(o, i)\ + (PyList_Check(o) ? PyList_GET_ITEM(o, i) : PyTuple_GET_ITEM(o, i)) + /* + Return the ith element of o, assuming that o was returned by + PySequence_Fast, and that i is within bounds. + */ + +#define PySequence_ITEM(o, i)\ + ( Py_TYPE(o)->tp_as_sequence->sq_item(o, i) ) + /* Assume tp_as_sequence and sq_item exist and that i does not + need to be corrected for a negative index + */ + +#define PySequence_Fast_ITEMS(sf) \ + (PyList_Check(sf) ? ((PyListObject *)(sf))->ob_item \ + : ((PyTupleObject *)(sf))->ob_item) + /* Return a pointer to the underlying item array for + an object retured by PySequence_Fast */ + + PyAPI_FUNC(Py_ssize_t) PySequence_Count(PyObject *o, PyObject *value); + + /* + Return the number of occurrences on value on o, that is, + return the number of keys for which o[key]==value. On + failure, return -1. This is equivalent to the Python + expression: o.count(value). + */ + + PyAPI_FUNC(int) PySequence_Contains(PyObject *seq, PyObject *ob); + /* + Return -1 if error; 1 if ob in seq; 0 if ob not in seq. + Use __contains__ if possible, else _PySequence_IterSearch(). + */ + +#define PY_ITERSEARCH_COUNT 1 +#define PY_ITERSEARCH_INDEX 2 +#define PY_ITERSEARCH_CONTAINS 3 + PyAPI_FUNC(Py_ssize_t) _PySequence_IterSearch(PyObject *seq, + PyObject *obj, int operation); + /* + Iterate over seq. Result depends on the operation: + PY_ITERSEARCH_COUNT: return # of times obj appears in seq; -1 if + error. + PY_ITERSEARCH_INDEX: return 0-based index of first occurrence of + obj in seq; set ValueError and return -1 if none found; + also return -1 on error. + PY_ITERSEARCH_CONTAINS: return 1 if obj in seq, else 0; -1 on + error. + */ + +/* For DLL-level backwards compatibility */ +#undef PySequence_In + PyAPI_FUNC(int) PySequence_In(PyObject *o, PyObject *value); + +/* For source-level backwards compatibility */ +#define PySequence_In PySequence_Contains + + /* + Determine if o contains value. If an item in o is equal to + X, return 1, otherwise return 0. On error, return -1. This + is equivalent to the Python expression: value in o. + */ + + PyAPI_FUNC(Py_ssize_t) PySequence_Index(PyObject *o, PyObject *value); + + /* + Return the first index for which o[i]=value. On error, + return -1. This is equivalent to the Python + expression: o.index(value). + */ + +/* In-place versions of some of the above Sequence functions. */ + + PyAPI_FUNC(PyObject *) PySequence_InPlaceConcat(PyObject *o1, PyObject *o2); + + /* + Append o2 to o1, in-place when possible. Return the resulting + object, which could be o1, or NULL on failure. This is the + equivalent of the Python expression: o1 += o2. + + */ + + PyAPI_FUNC(PyObject *) PySequence_InPlaceRepeat(PyObject *o, Py_ssize_t count); + + /* + Repeat o1 by count, in-place when possible. Return the resulting + object, which could be o1, or NULL on failure. This is the + equivalent of the Python expression: o1 *= count. + + */ + +/* Mapping protocol:*/ + + PyAPI_FUNC(int) PyMapping_Check(PyObject *o); + + /* + Return 1 if the object provides mapping protocol, and zero + otherwise. + + This function always succeeds. + */ + + PyAPI_FUNC(Py_ssize_t) PyMapping_Size(PyObject *o); + + /* + Returns the number of keys in object o on success, and -1 on + failure. For objects that do not provide sequence protocol, + this is equivalent to the Python expression: len(o). + */ + + /* For DLL compatibility */ +#undef PyMapping_Length + PyAPI_FUNC(Py_ssize_t) PyMapping_Length(PyObject *o); +#define PyMapping_Length PyMapping_Size + + + /* implemented as a macro: + + int PyMapping_DelItemString(PyObject *o, char *key); + + Remove the mapping for object, key, from the object *o. + Returns -1 on failure. This is equivalent to + the Python statement: del o[key]. + */ +#define PyMapping_DelItemString(O,K) PyObject_DelItemString((O),(K)) + + /* implemented as a macro: + + int PyMapping_DelItem(PyObject *o, PyObject *key); + + Remove the mapping for object, key, from the object *o. + Returns -1 on failure. This is equivalent to + the Python statement: del o[key]. + */ +#define PyMapping_DelItem(O,K) PyObject_DelItem((O),(K)) + + PyAPI_FUNC(int) PyMapping_HasKeyString(PyObject *o, char *key); + + /* + On success, return 1 if the mapping object has the key, key, + and 0 otherwise. This is equivalent to the Python expression: + o.has_key(key). + + This function always succeeds. + */ + + PyAPI_FUNC(int) PyMapping_HasKey(PyObject *o, PyObject *key); + + /* + Return 1 if the mapping object has the key, key, + and 0 otherwise. This is equivalent to the Python expression: + o.has_key(key). + + This function always succeeds. + + */ + + /* Implemented as macro: + + PyObject *PyMapping_Keys(PyObject *o); + + On success, return a list of the keys in object o. On + failure, return NULL. This is equivalent to the Python + expression: o.keys(). + */ +#define PyMapping_Keys(O) PyObject_CallMethod(O,"keys",NULL) + + /* Implemented as macro: + + PyObject *PyMapping_Values(PyObject *o); + + On success, return a list of the values in object o. On + failure, return NULL. This is equivalent to the Python + expression: o.values(). + */ +#define PyMapping_Values(O) PyObject_CallMethod(O,"values",NULL) + + /* Implemented as macro: + + PyObject *PyMapping_Items(PyObject *o); + + On success, return a list of the items in object o, where + each item is a tuple containing a key-value pair. On + failure, return NULL. This is equivalent to the Python + expression: o.items(). + + */ +#define PyMapping_Items(O) PyObject_CallMethod(O,"items",NULL) + + PyAPI_FUNC(PyObject *) PyMapping_GetItemString(PyObject *o, char *key); + + /* + Return element of o corresponding to the object, key, or NULL + on failure. This is the equivalent of the Python expression: + o[key]. + */ + + PyAPI_FUNC(int) PyMapping_SetItemString(PyObject *o, char *key, + PyObject *value); + + /* + Map the object, key, to the value, v. Returns + -1 on failure. This is the equivalent of the Python + statement: o[key]=v. + */ + + +PyAPI_FUNC(int) PyObject_IsInstance(PyObject *object, PyObject *typeorclass); + /* isinstance(object, typeorclass) */ + +PyAPI_FUNC(int) PyObject_IsSubclass(PyObject *object, PyObject *typeorclass); + /* issubclass(object, typeorclass) */ + + +PyAPI_FUNC(int) _PyObject_RealIsInstance(PyObject *inst, PyObject *cls); + +PyAPI_FUNC(int) _PyObject_RealIsSubclass(PyObject *derived, PyObject *cls); + + +/* For internal use by buffer API functions */ +PyAPI_FUNC(void) _Py_add_one_to_index_F(int nd, Py_ssize_t *index, + const Py_ssize_t *shape); +PyAPI_FUNC(void) _Py_add_one_to_index_C(int nd, Py_ssize_t *index, + const Py_ssize_t *shape); + + +#ifdef __cplusplus +} +#endif +#endif /* Py_ABSTRACTOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/asdl.h b/AppPkg/Applications/Python/Python-2.7.10/Include/asdl.h new file mode 100644 index 0000000000..d72b2f81ea --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/asdl.h @@ -0,0 +1,45 @@ +#ifndef Py_ASDL_H +#define Py_ASDL_H + +typedef PyObject * identifier; +typedef PyObject * string; +typedef PyObject * object; + +#ifndef __cplusplus +typedef enum {false, true} bool; +#endif + +/* It would be nice if the code generated by asdl_c.py was completely + independent of Python, but it is a goal the requires too much work + at this stage. So, for example, I'll represent identifiers as + interned Python strings. +*/ + +/* XXX A sequence should be typed so that its use can be typechecked. */ + +typedef struct { + int size; + void *elements[1]; +} asdl_seq; + +typedef struct { + int size; + int elements[1]; +} asdl_int_seq; + +asdl_seq *asdl_seq_new(int size, PyArena *arena); +asdl_int_seq *asdl_int_seq_new(int size, PyArena *arena); + +#define asdl_seq_GET(S, I) (S)->elements[(I)] +#define asdl_seq_LEN(S) ((S) == NULL ? 0 : (S)->size) +#ifdef Py_DEBUG +#define asdl_seq_SET(S, I, V) { \ + int _asdl_i = (I); \ + assert((S) && _asdl_i < (S)->size); \ + (S)->elements[_asdl_i] = (V); \ +} +#else +#define asdl_seq_SET(S, I, V) (S)->elements[I] = (V) +#endif + +#endif /* !Py_ASDL_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/ast.h b/AppPkg/Applications/Python/Python-2.7.10/Include/ast.h new file mode 100644 index 0000000000..77dbe5ffc6 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/ast.h @@ -0,0 +1,13 @@ +#ifndef Py_AST_H +#define Py_AST_H +#ifdef __cplusplus +extern "C" { +#endif + +PyAPI_FUNC(mod_ty) PyAST_FromNode(const node *, PyCompilerFlags *flags, + const char *, PyArena *); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_AST_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/bitset.h b/AppPkg/Applications/Python/Python-2.7.10/Include/bitset.h new file mode 100644 index 0000000000..028acdf042 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/bitset.h @@ -0,0 +1,32 @@ + +#ifndef Py_BITSET_H +#define Py_BITSET_H +#ifdef __cplusplus +extern "C" { +#endif + +/* Bitset interface */ + +#define BYTE char + +typedef BYTE *bitset; + +bitset newbitset(int nbits); +void delbitset(bitset bs); +#define testbit(ss, ibit) (((ss)[BIT2BYTE(ibit)] & BIT2MASK(ibit)) != 0) +int addbit(bitset bs, int ibit); /* Returns 0 if already set */ +int samebitset(bitset bs1, bitset bs2, int nbits); +void mergebitset(bitset bs1, bitset bs2, int nbits); + +#define BITSPERBYTE (8*sizeof(BYTE)) +#define NBYTES(nbits) (((nbits) + BITSPERBYTE - 1) / BITSPERBYTE) + +#define BIT2BYTE(ibit) ((ibit) / BITSPERBYTE) +#define BIT2SHIFT(ibit) ((ibit) % BITSPERBYTE) +#define BIT2MASK(ibit) (1 << BIT2SHIFT(ibit)) +#define BYTE2BIT(ibyte) ((ibyte) * BITSPERBYTE) + +#ifdef __cplusplus +} +#endif +#endif /* !Py_BITSET_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/boolobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/boolobject.h new file mode 100644 index 0000000000..9dd0e43501 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/boolobject.h @@ -0,0 +1,36 @@ +/* Boolean object interface */ + +#ifndef Py_BOOLOBJECT_H +#define Py_BOOLOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + + +typedef PyIntObject PyBoolObject; + +PyAPI_DATA(PyTypeObject) PyBool_Type; + +#define PyBool_Check(x) (Py_TYPE(x) == &PyBool_Type) + +/* Py_False and Py_True are the only two bools in existence. +Don't forget to apply Py_INCREF() when returning either!!! */ + +/* Don't use these directly */ +PyAPI_DATA(PyIntObject) _Py_ZeroStruct, _Py_TrueStruct; + +/* Use these macros */ +#define Py_False ((PyObject *) &_Py_ZeroStruct) +#define Py_True ((PyObject *) &_Py_TrueStruct) + +/* Macros for returning Py_True or Py_False, respectively */ +#define Py_RETURN_TRUE return Py_INCREF(Py_True), Py_True +#define Py_RETURN_FALSE return Py_INCREF(Py_False), Py_False + +/* Function to return a bool from a C long */ +PyAPI_FUNC(PyObject *) PyBool_FromLong(long); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_BOOLOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/bufferobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/bufferobject.h new file mode 100644 index 0000000000..6c33a8b023 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/bufferobject.h @@ -0,0 +1,33 @@ + +/* Buffer object interface */ + +/* Note: the object's structure is private */ + +#ifndef Py_BUFFEROBJECT_H +#define Py_BUFFEROBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + + +PyAPI_DATA(PyTypeObject) PyBuffer_Type; + +#define PyBuffer_Check(op) (Py_TYPE(op) == &PyBuffer_Type) + +#define Py_END_OF_BUFFER (-1) + +PyAPI_FUNC(PyObject *) PyBuffer_FromObject(PyObject *base, + Py_ssize_t offset, Py_ssize_t size); +PyAPI_FUNC(PyObject *) PyBuffer_FromReadWriteObject(PyObject *base, + Py_ssize_t offset, + Py_ssize_t size); + +PyAPI_FUNC(PyObject *) PyBuffer_FromMemory(void *ptr, Py_ssize_t size); +PyAPI_FUNC(PyObject *) PyBuffer_FromReadWriteMemory(void *ptr, Py_ssize_t size); + +PyAPI_FUNC(PyObject *) PyBuffer_New(Py_ssize_t size); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_BUFFEROBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/bytearrayobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/bytearrayobject.h new file mode 100644 index 0000000000..6d5af4d87d --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/bytearrayobject.h @@ -0,0 +1,57 @@ +/* ByteArray object interface */ + +#ifndef Py_BYTEARRAYOBJECT_H +#define Py_BYTEARRAYOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +#include + +/* Type PyByteArrayObject represents a mutable array of bytes. + * The Python API is that of a sequence; + * the bytes are mapped to ints in [0, 256). + * Bytes are not characters; they may be used to encode characters. + * The only way to go between bytes and str/unicode is via encoding + * and decoding. + * For the convenience of C programmers, the bytes type is considered + * to contain a char pointer, not an unsigned char pointer. + */ + +/* Object layout */ +typedef struct { + PyObject_VAR_HEAD + /* XXX(nnorwitz): should ob_exports be Py_ssize_t? */ + int ob_exports; /* how many buffer exports */ + Py_ssize_t ob_alloc; /* How many bytes allocated */ + char *ob_bytes; +} PyByteArrayObject; + +/* Type object */ +PyAPI_DATA(PyTypeObject) PyByteArray_Type; +PyAPI_DATA(PyTypeObject) PyByteArrayIter_Type; + +/* Type check macros */ +#define PyByteArray_Check(self) PyObject_TypeCheck(self, &PyByteArray_Type) +#define PyByteArray_CheckExact(self) (Py_TYPE(self) == &PyByteArray_Type) + +/* Direct API functions */ +PyAPI_FUNC(PyObject *) PyByteArray_FromObject(PyObject *); +PyAPI_FUNC(PyObject *) PyByteArray_Concat(PyObject *, PyObject *); +PyAPI_FUNC(PyObject *) PyByteArray_FromStringAndSize(const char *, Py_ssize_t); +PyAPI_FUNC(Py_ssize_t) PyByteArray_Size(PyObject *); +PyAPI_FUNC(char *) PyByteArray_AsString(PyObject *); +PyAPI_FUNC(int) PyByteArray_Resize(PyObject *, Py_ssize_t); + +/* Macros, trading safety for speed */ +#define PyByteArray_AS_STRING(self) \ + (assert(PyByteArray_Check(self)), \ + Py_SIZE(self) ? ((PyByteArrayObject *)(self))->ob_bytes : _PyByteArray_empty_string) +#define PyByteArray_GET_SIZE(self) (assert(PyByteArray_Check(self)),Py_SIZE(self)) + +PyAPI_DATA(char) _PyByteArray_empty_string[]; + +#ifdef __cplusplus +} +#endif +#endif /* !Py_BYTEARRAYOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/bytes_methods.h b/AppPkg/Applications/Python/Python-2.7.10/Include/bytes_methods.h new file mode 100644 index 0000000000..64ba0aa76c --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/bytes_methods.h @@ -0,0 +1,75 @@ +#ifndef Py_BYTES_CTYPE_H +#define Py_BYTES_CTYPE_H + +/* + * The internal implementation behind PyString (bytes) and PyBytes (buffer) + * methods of the given names, they operate on ASCII byte strings. + */ +extern PyObject* _Py_bytes_isspace(const char *cptr, Py_ssize_t len); +extern PyObject* _Py_bytes_isalpha(const char *cptr, Py_ssize_t len); +extern PyObject* _Py_bytes_isalnum(const char *cptr, Py_ssize_t len); +extern PyObject* _Py_bytes_isdigit(const char *cptr, Py_ssize_t len); +extern PyObject* _Py_bytes_islower(const char *cptr, Py_ssize_t len); +extern PyObject* _Py_bytes_isupper(const char *cptr, Py_ssize_t len); +extern PyObject* _Py_bytes_istitle(const char *cptr, Py_ssize_t len); + +/* These store their len sized answer in the given preallocated *result arg. */ +extern void _Py_bytes_lower(char *result, const char *cptr, Py_ssize_t len); +extern void _Py_bytes_upper(char *result, const char *cptr, Py_ssize_t len); +extern void _Py_bytes_title(char *result, char *s, Py_ssize_t len); +extern void _Py_bytes_capitalize(char *result, char *s, Py_ssize_t len); +extern void _Py_bytes_swapcase(char *result, char *s, Py_ssize_t len); + +/* Shared __doc__ strings. */ +extern const char _Py_isspace__doc__[]; +extern const char _Py_isalpha__doc__[]; +extern const char _Py_isalnum__doc__[]; +extern const char _Py_isdigit__doc__[]; +extern const char _Py_islower__doc__[]; +extern const char _Py_isupper__doc__[]; +extern const char _Py_istitle__doc__[]; +extern const char _Py_lower__doc__[]; +extern const char _Py_upper__doc__[]; +extern const char _Py_title__doc__[]; +extern const char _Py_capitalize__doc__[]; +extern const char _Py_swapcase__doc__[]; + +/* These are left in for backward compatibility and will be removed + in 2.8/3.2 */ +#define ISLOWER(c) Py_ISLOWER(c) +#define ISUPPER(c) Py_ISUPPER(c) +#define ISALPHA(c) Py_ISALPHA(c) +#define ISDIGIT(c) Py_ISDIGIT(c) +#define ISXDIGIT(c) Py_ISXDIGIT(c) +#define ISALNUM(c) Py_ISALNUM(c) +#define ISSPACE(c) Py_ISSPACE(c) + +#undef islower +#define islower(c) undefined_islower(c) +#undef isupper +#define isupper(c) undefined_isupper(c) +#undef isalpha +#define isalpha(c) undefined_isalpha(c) +#undef isdigit +#define isdigit(c) undefined_isdigit(c) +#undef isxdigit +#define isxdigit(c) undefined_isxdigit(c) +#undef isalnum +#define isalnum(c) undefined_isalnum(c) +#undef isspace +#define isspace(c) undefined_isspace(c) + +/* These are left in for backward compatibility and will be removed + in 2.8/3.2 */ +#define TOLOWER(c) Py_TOLOWER(c) +#define TOUPPER(c) Py_TOUPPER(c) + +#undef tolower +#define tolower(c) undefined_tolower(c) +#undef toupper +#define toupper(c) undefined_toupper(c) + +/* this is needed because some docs are shared from the .o, not static */ +#define PyDoc_STRVAR_shared(name,str) const char name[] = PyDoc_STR(str) + +#endif /* !Py_BYTES_CTYPE_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/bytesobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/bytesobject.h new file mode 100644 index 0000000000..d60bdc0af0 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/bytesobject.h @@ -0,0 +1,27 @@ +#define PyBytesObject PyStringObject +#define PyBytes_Type PyString_Type + +#define PyBytes_Check PyString_Check +#define PyBytes_CheckExact PyString_CheckExact +#define PyBytes_CHECK_INTERNED PyString_CHECK_INTERNED +#define PyBytes_AS_STRING PyString_AS_STRING +#define PyBytes_GET_SIZE PyString_GET_SIZE +#define Py_TPFLAGS_BYTES_SUBCLASS Py_TPFLAGS_STRING_SUBCLASS + +#define PyBytes_FromStringAndSize PyString_FromStringAndSize +#define PyBytes_FromString PyString_FromString +#define PyBytes_FromFormatV PyString_FromFormatV +#define PyBytes_FromFormat PyString_FromFormat +#define PyBytes_Size PyString_Size +#define PyBytes_AsString PyString_AsString +#define PyBytes_Repr PyString_Repr +#define PyBytes_Concat PyString_Concat +#define PyBytes_ConcatAndDel PyString_ConcatAndDel +#define _PyBytes_Resize _PyString_Resize +#define _PyBytes_Eq _PyString_Eq +#define PyBytes_Format PyString_Format +#define _PyBytes_FormatLong _PyString_FormatLong +#define PyBytes_DecodeEscape PyString_DecodeEscape +#define _PyBytes_Join _PyString_Join +#define PyBytes_AsStringAndSize PyString_AsStringAndSize +#define _PyBytes_InsertThousandsGrouping _PyString_InsertThousandsGrouping diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/cStringIO.h b/AppPkg/Applications/Python/Python-2.7.10/Include/cStringIO.h new file mode 100644 index 0000000000..391309a0ba --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/cStringIO.h @@ -0,0 +1,73 @@ +#ifndef Py_CSTRINGIO_H +#define Py_CSTRINGIO_H +#ifdef __cplusplus +extern "C" { +#endif +/* + + This header provides access to cStringIO objects from C. + Functions are provided for calling cStringIO objects and + macros are provided for testing whether you have cStringIO + objects. + + Before calling any of the functions or macros, you must initialize + the routines with: + + PycString_IMPORT + + This would typically be done in your init function. + +*/ + +#define PycStringIO_CAPSULE_NAME "cStringIO.cStringIO_CAPI" + +#define PycString_IMPORT \ + PycStringIO = ((struct PycStringIO_CAPI*)PyCapsule_Import(\ + PycStringIO_CAPSULE_NAME, 0)) + +/* Basic functions to manipulate cStringIO objects from C */ + +static struct PycStringIO_CAPI { + + /* Read a string from an input object. If the last argument + is -1, the remainder will be read. + */ + int(*cread)(PyObject *, char **, Py_ssize_t); + + /* Read a line from an input object. Returns the length of the read + line as an int and a pointer inside the object buffer as char** (so + the caller doesn't have to provide its own buffer as destination). + */ + int(*creadline)(PyObject *, char **); + + /* Write a string to an output object*/ + int(*cwrite)(PyObject *, const char *, Py_ssize_t); + + /* Get the output object as a Python string (returns new reference). */ + PyObject *(*cgetvalue)(PyObject *); + + /* Create a new output object */ + PyObject *(*NewOutput)(int); + + /* Create an input object from a Python string + (copies the Python string reference). + */ + PyObject *(*NewInput)(PyObject *); + + /* The Python types for cStringIO input and output objects. + Note that you can do input on an output object. + */ + PyTypeObject *InputType, *OutputType; + +} *PycStringIO; + +/* These can be used to test if you have one */ +#define PycStringIO_InputCheck(O) \ + (Py_TYPE(O)==PycStringIO->InputType) +#define PycStringIO_OutputCheck(O) \ + (Py_TYPE(O)==PycStringIO->OutputType) + +#ifdef __cplusplus +} +#endif +#endif /* !Py_CSTRINGIO_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/cellobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/cellobject.h new file mode 100644 index 0000000000..8d27f35ad4 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/cellobject.h @@ -0,0 +1,28 @@ +/* Cell object interface */ + +#ifndef Py_CELLOBJECT_H +#define Py_CELLOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +typedef struct { + PyObject_HEAD + PyObject *ob_ref; /* Content of the cell or NULL when empty */ +} PyCellObject; + +PyAPI_DATA(PyTypeObject) PyCell_Type; + +#define PyCell_Check(op) (Py_TYPE(op) == &PyCell_Type) + +PyAPI_FUNC(PyObject *) PyCell_New(PyObject *); +PyAPI_FUNC(PyObject *) PyCell_Get(PyObject *); +PyAPI_FUNC(int) PyCell_Set(PyObject *, PyObject *); + +#define PyCell_GET(op) (((PyCellObject *)(op))->ob_ref) +#define PyCell_SET(op, v) (((PyCellObject *)(op))->ob_ref = v) + +#ifdef __cplusplus +} +#endif +#endif /* !Py_TUPLEOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/ceval.h b/AppPkg/Applications/Python/Python-2.7.10/Include/ceval.h new file mode 100644 index 0000000000..58b2dedf6d --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/ceval.h @@ -0,0 +1,153 @@ +#ifndef Py_CEVAL_H +#define Py_CEVAL_H +#ifdef __cplusplus +extern "C" { +#endif + + +/* Interface to random parts in ceval.c */ + +PyAPI_FUNC(PyObject *) PyEval_CallObjectWithKeywords( + PyObject *, PyObject *, PyObject *); + +/* Inline this */ +#define PyEval_CallObject(func,arg) \ + PyEval_CallObjectWithKeywords(func, arg, (PyObject *)NULL) + +PyAPI_FUNC(PyObject *) PyEval_CallFunction(PyObject *obj, + const char *format, ...); +PyAPI_FUNC(PyObject *) PyEval_CallMethod(PyObject *obj, + const char *methodname, + const char *format, ...); + +PyAPI_FUNC(void) PyEval_SetProfile(Py_tracefunc, PyObject *); +PyAPI_FUNC(void) PyEval_SetTrace(Py_tracefunc, PyObject *); + +struct _frame; /* Avoid including frameobject.h */ + +PyAPI_FUNC(PyObject *) PyEval_GetBuiltins(void); +PyAPI_FUNC(PyObject *) PyEval_GetGlobals(void); +PyAPI_FUNC(PyObject *) PyEval_GetLocals(void); +PyAPI_FUNC(struct _frame *) PyEval_GetFrame(void); +PyAPI_FUNC(int) PyEval_GetRestricted(void); + +/* Look at the current frame's (if any) code's co_flags, and turn on + the corresponding compiler flags in cf->cf_flags. Return 1 if any + flag was set, else return 0. */ +PyAPI_FUNC(int) PyEval_MergeCompilerFlags(PyCompilerFlags *cf); + +PyAPI_FUNC(int) Py_FlushLine(void); + +PyAPI_FUNC(int) Py_AddPendingCall(int (*func)(void *), void *arg); +PyAPI_FUNC(int) Py_MakePendingCalls(void); + +/* Protection against deeply nested recursive calls */ +PyAPI_FUNC(void) Py_SetRecursionLimit(int); +PyAPI_FUNC(int) Py_GetRecursionLimit(void); + +#define Py_EnterRecursiveCall(where) \ + (_Py_MakeRecCheck(PyThreadState_GET()->recursion_depth) && \ + _Py_CheckRecursiveCall(where)) +#define Py_LeaveRecursiveCall() \ + (--PyThreadState_GET()->recursion_depth) +PyAPI_FUNC(int) _Py_CheckRecursiveCall(char *where); +PyAPI_DATA(int) _Py_CheckRecursionLimit; +#ifdef USE_STACKCHECK +# define _Py_MakeRecCheck(x) (++(x) > --_Py_CheckRecursionLimit) +#else +# define _Py_MakeRecCheck(x) (++(x) > _Py_CheckRecursionLimit) +#endif + +PyAPI_FUNC(const char *) PyEval_GetFuncName(PyObject *); +PyAPI_FUNC(const char *) PyEval_GetFuncDesc(PyObject *); + +PyAPI_FUNC(PyObject *) PyEval_GetCallStats(PyObject *); +PyAPI_FUNC(PyObject *) PyEval_EvalFrame(struct _frame *); +PyAPI_FUNC(PyObject *) PyEval_EvalFrameEx(struct _frame *f, int exc); + +/* this used to be handled on a per-thread basis - now just two globals */ +PyAPI_DATA(volatile int) _Py_Ticker; +PyAPI_DATA(int) _Py_CheckInterval; + +/* Interface for threads. + + A module that plans to do a blocking system call (or something else + that lasts a long time and doesn't touch Python data) can allow other + threads to run as follows: + + ...preparations here... + Py_BEGIN_ALLOW_THREADS + ...blocking system call here... + Py_END_ALLOW_THREADS + ...interpret result here... + + The Py_BEGIN_ALLOW_THREADS/Py_END_ALLOW_THREADS pair expands to a + {}-surrounded block. + To leave the block in the middle (e.g., with return), you must insert + a line containing Py_BLOCK_THREADS before the return, e.g. + + if (...premature_exit...) { + Py_BLOCK_THREADS + PyErr_SetFromErrno(PyExc_IOError); + return NULL; + } + + An alternative is: + + Py_BLOCK_THREADS + if (...premature_exit...) { + PyErr_SetFromErrno(PyExc_IOError); + return NULL; + } + Py_UNBLOCK_THREADS + + For convenience, that the value of 'errno' is restored across + Py_END_ALLOW_THREADS and Py_BLOCK_THREADS. + + WARNING: NEVER NEST CALLS TO Py_BEGIN_ALLOW_THREADS AND + Py_END_ALLOW_THREADS!!! + + The function PyEval_InitThreads() should be called only from + initthread() in "threadmodule.c". + + Note that not yet all candidates have been converted to use this + mechanism! +*/ + +PyAPI_FUNC(PyThreadState *) PyEval_SaveThread(void); +PyAPI_FUNC(void) PyEval_RestoreThread(PyThreadState *); + +#ifdef WITH_THREAD + +PyAPI_FUNC(int) PyEval_ThreadsInitialized(void); +PyAPI_FUNC(void) PyEval_InitThreads(void); +PyAPI_FUNC(void) PyEval_AcquireLock(void); +PyAPI_FUNC(void) PyEval_ReleaseLock(void); +PyAPI_FUNC(void) PyEval_AcquireThread(PyThreadState *tstate); +PyAPI_FUNC(void) PyEval_ReleaseThread(PyThreadState *tstate); +PyAPI_FUNC(void) PyEval_ReInitThreads(void); + +#define Py_BEGIN_ALLOW_THREADS { \ + PyThreadState *_save; \ + _save = PyEval_SaveThread(); +#define Py_BLOCK_THREADS PyEval_RestoreThread(_save); +#define Py_UNBLOCK_THREADS _save = PyEval_SaveThread(); +#define Py_END_ALLOW_THREADS PyEval_RestoreThread(_save); \ + } + +#else /* !WITH_THREAD */ + +#define Py_BEGIN_ALLOW_THREADS { +#define Py_BLOCK_THREADS +#define Py_UNBLOCK_THREADS +#define Py_END_ALLOW_THREADS } + +#endif /* !WITH_THREAD */ + +PyAPI_FUNC(int) _PyEval_SliceIndex(PyObject *, Py_ssize_t *); + + +#ifdef __cplusplus +} +#endif +#endif /* !Py_CEVAL_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/classobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/classobject.h new file mode 100644 index 0000000000..8e42e53edc --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/classobject.h @@ -0,0 +1,83 @@ + +/* Class object interface */ + +/* Revealing some structures (not for general use) */ + +#ifndef Py_CLASSOBJECT_H +#define Py_CLASSOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +typedef struct { + PyObject_HEAD + PyObject *cl_bases; /* A tuple of class objects */ + PyObject *cl_dict; /* A dictionary */ + PyObject *cl_name; /* A string */ + /* The following three are functions or NULL */ + PyObject *cl_getattr; + PyObject *cl_setattr; + PyObject *cl_delattr; + PyObject *cl_weakreflist; /* List of weak references */ +} PyClassObject; + +typedef struct { + PyObject_HEAD + PyClassObject *in_class; /* The class object */ + PyObject *in_dict; /* A dictionary */ + PyObject *in_weakreflist; /* List of weak references */ +} PyInstanceObject; + +typedef struct { + PyObject_HEAD + PyObject *im_func; /* The callable object implementing the method */ + PyObject *im_self; /* The instance it is bound to, or NULL */ + PyObject *im_class; /* The class that asked for the method */ + PyObject *im_weakreflist; /* List of weak references */ +} PyMethodObject; + +PyAPI_DATA(PyTypeObject) PyClass_Type, PyInstance_Type, PyMethod_Type; + +#define PyClass_Check(op) ((op)->ob_type == &PyClass_Type) +#define PyInstance_Check(op) ((op)->ob_type == &PyInstance_Type) +#define PyMethod_Check(op) ((op)->ob_type == &PyMethod_Type) + +PyAPI_FUNC(PyObject *) PyClass_New(PyObject *, PyObject *, PyObject *); +PyAPI_FUNC(PyObject *) PyInstance_New(PyObject *, PyObject *, + PyObject *); +PyAPI_FUNC(PyObject *) PyInstance_NewRaw(PyObject *, PyObject *); +PyAPI_FUNC(PyObject *) PyMethod_New(PyObject *, PyObject *, PyObject *); + +PyAPI_FUNC(PyObject *) PyMethod_Function(PyObject *); +PyAPI_FUNC(PyObject *) PyMethod_Self(PyObject *); +PyAPI_FUNC(PyObject *) PyMethod_Class(PyObject *); + +/* Look up attribute with name (a string) on instance object pinst, using + * only the instance and base class dicts. If a descriptor is found in + * a class dict, the descriptor is returned without calling it. + * Returns NULL if nothing found, else a borrowed reference to the + * value associated with name in the dict in which name was found. + * The point of this routine is that it never calls arbitrary Python + * code, so is always "safe": all it does is dict lookups. The function + * can't fail, never sets an exception, and NULL is not an error (it just + * means "not found"). + */ +PyAPI_FUNC(PyObject *) _PyInstance_Lookup(PyObject *pinst, PyObject *name); + +/* Macros for direct access to these values. Type checks are *not* + done, so use with care. */ +#define PyMethod_GET_FUNCTION(meth) \ + (((PyMethodObject *)meth) -> im_func) +#define PyMethod_GET_SELF(meth) \ + (((PyMethodObject *)meth) -> im_self) +#define PyMethod_GET_CLASS(meth) \ + (((PyMethodObject *)meth) -> im_class) + +PyAPI_FUNC(int) PyClass_IsSubclass(PyObject *, PyObject *); + +PyAPI_FUNC(int) PyMethod_ClearFreeList(void); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_CLASSOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/cobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/cobject.h new file mode 100644 index 0000000000..11a8b434ee --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/cobject.h @@ -0,0 +1,89 @@ +/* + CObjects are marked Pending Deprecation as of Python 2.7. + The full schedule for 2.x is as follows: + - CObjects are marked Pending Deprecation in Python 2.7. + - CObjects will be marked Deprecated in Python 2.8 + (if there is one). + - CObjects will be removed in Python 2.9 (if there is one). + + Additionally, for the Python 3.x series: + - CObjects were marked Deprecated in Python 3.1. + - CObjects will be removed in Python 3.2. + + You should switch all use of CObjects to capsules. Capsules + have a safer and more consistent API. For more information, + see Include/pycapsule.h, or read the "Capsules" topic in + the "Python/C API Reference Manual". + + Python 2.7 no longer uses CObjects itself; all objects which + were formerly CObjects are now capsules. Note that this change + does not by itself break binary compatibility with extensions + built for previous versions of Python--PyCObject_AsVoidPtr() + has been changed to also understand capsules. + +*/ + +/* original file header comment follows: */ + +/* C objects to be exported from one extension module to another. + + C objects are used for communication between extension modules. + They provide a way for an extension module to export a C interface + to other extension modules, so that extension modules can use the + Python import mechanism to link to one another. + +*/ + +#ifndef Py_COBJECT_H +#define Py_COBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +PyAPI_DATA(PyTypeObject) PyCObject_Type; + +#define PyCObject_Check(op) (Py_TYPE(op) == &PyCObject_Type) + +/* Create a PyCObject from a pointer to a C object and an optional + destructor function. If the second argument is non-null, then it + will be called with the first argument if and when the PyCObject is + destroyed. + +*/ +PyAPI_FUNC(PyObject *) PyCObject_FromVoidPtr( + void *cobj, void (*destruct)(void*)); + + +/* Create a PyCObject from a pointer to a C object, a description object, + and an optional destructor function. If the third argument is non-null, + then it will be called with the first and second arguments if and when + the PyCObject is destroyed. +*/ +PyAPI_FUNC(PyObject *) PyCObject_FromVoidPtrAndDesc( + void *cobj, void *desc, void (*destruct)(void*,void*)); + +/* Retrieve a pointer to a C object from a PyCObject. */ +PyAPI_FUNC(void *) PyCObject_AsVoidPtr(PyObject *); + +/* Retrieve a pointer to a description object from a PyCObject. */ +PyAPI_FUNC(void *) PyCObject_GetDesc(PyObject *); + +/* Import a pointer to a C object from a module using a PyCObject. */ +PyAPI_FUNC(void *) PyCObject_Import(char *module_name, char *cobject_name); + +/* Modify a C object. Fails (==0) if object has a destructor. */ +PyAPI_FUNC(int) PyCObject_SetVoidPtr(PyObject *self, void *cobj); + + +typedef struct { + PyObject_HEAD + void *cobject; + void *desc; + void (*destructor)(void *); +} PyCObject; + + +#ifdef __cplusplus +} +#endif +#endif /* !Py_COBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/code.h b/AppPkg/Applications/Python/Python-2.7.10/Include/code.h new file mode 100644 index 0000000000..40151595c6 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/code.h @@ -0,0 +1,107 @@ +/* Definitions for bytecode */ + +#ifndef Py_CODE_H +#define Py_CODE_H +#ifdef __cplusplus +extern "C" { +#endif + +/* Bytecode object */ +typedef struct { + PyObject_HEAD + int co_argcount; /* #arguments, except *args */ + int co_nlocals; /* #local variables */ + int co_stacksize; /* #entries needed for evaluation stack */ + int co_flags; /* CO_..., see below */ + PyObject *co_code; /* instruction opcodes */ + PyObject *co_consts; /* list (constants used) */ + PyObject *co_names; /* list of strings (names used) */ + PyObject *co_varnames; /* tuple of strings (local variable names) */ + PyObject *co_freevars; /* tuple of strings (free variable names) */ + PyObject *co_cellvars; /* tuple of strings (cell variable names) */ + /* The rest doesn't count for hash/cmp */ + PyObject *co_filename; /* string (where it was loaded from) */ + PyObject *co_name; /* string (name, for reference) */ + int co_firstlineno; /* first source line number */ + PyObject *co_lnotab; /* string (encoding addr<->lineno mapping) See + Objects/lnotab_notes.txt for details. */ + void *co_zombieframe; /* for optimization only (see frameobject.c) */ + PyObject *co_weakreflist; /* to support weakrefs to code objects */ +} PyCodeObject; + +/* Masks for co_flags above */ +#define CO_OPTIMIZED 0x0001 +#define CO_NEWLOCALS 0x0002 +#define CO_VARARGS 0x0004 +#define CO_VARKEYWORDS 0x0008 +#define CO_NESTED 0x0010 +#define CO_GENERATOR 0x0020 +/* The CO_NOFREE flag is set if there are no free or cell variables. + This information is redundant, but it allows a single flag test + to determine whether there is any extra work to be done when the + call frame it setup. +*/ +#define CO_NOFREE 0x0040 + +#if 0 +/* This is no longer used. Stopped defining in 2.5, do not re-use. */ +#define CO_GENERATOR_ALLOWED 0x1000 +#endif +#define CO_FUTURE_DIVISION 0x2000 +#define CO_FUTURE_ABSOLUTE_IMPORT 0x4000 /* do absolute imports by default */ +#define CO_FUTURE_WITH_STATEMENT 0x8000 +#define CO_FUTURE_PRINT_FUNCTION 0x10000 +#define CO_FUTURE_UNICODE_LITERALS 0x20000 + +/* This should be defined if a future statement modifies the syntax. + For example, when a keyword is added. +*/ +#if 1 +#define PY_PARSER_REQUIRES_FUTURE_KEYWORD +#endif + +#define CO_MAXBLOCKS 20 /* Max static block nesting within a function */ + +PyAPI_DATA(PyTypeObject) PyCode_Type; + +#define PyCode_Check(op) (Py_TYPE(op) == &PyCode_Type) +#define PyCode_GetNumFree(op) (PyTuple_GET_SIZE((op)->co_freevars)) + +/* Public interface */ +PyAPI_FUNC(PyCodeObject *) PyCode_New( + int, int, int, int, PyObject *, PyObject *, PyObject *, PyObject *, + PyObject *, PyObject *, PyObject *, PyObject *, int, PyObject *); + /* same as struct above */ + +/* Creates a new empty code object with the specified source location. */ +PyAPI_FUNC(PyCodeObject *) +PyCode_NewEmpty(const char *filename, const char *funcname, int firstlineno); + +/* Return the line number associated with the specified bytecode index + in this code object. If you just need the line number of a frame, + use PyFrame_GetLineNumber() instead. */ +PyAPI_FUNC(int) PyCode_Addr2Line(PyCodeObject *, int); + +/* for internal use only */ +#define _PyCode_GETCODEPTR(co, pp) \ + ((*Py_TYPE((co)->co_code)->tp_as_buffer->bf_getreadbuffer) \ + ((co)->co_code, 0, (void **)(pp))) + +typedef struct _addr_pair { + int ap_lower; + int ap_upper; +} PyAddrPair; + +/* Update *bounds to describe the first and one-past-the-last instructions in the + same line as lasti. Return the number of that line. +*/ +PyAPI_FUNC(int) _PyCode_CheckLineNumber(PyCodeObject* co, + int lasti, PyAddrPair *bounds); + +PyAPI_FUNC(PyObject*) PyCode_Optimize(PyObject *code, PyObject* consts, + PyObject *names, PyObject *lineno_obj); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_CODE_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/codecs.h b/AppPkg/Applications/Python/Python-2.7.10/Include/codecs.h new file mode 100644 index 0000000000..79c19a8453 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/codecs.h @@ -0,0 +1,167 @@ +#ifndef Py_CODECREGISTRY_H +#define Py_CODECREGISTRY_H +#ifdef __cplusplus +extern "C" { +#endif + +/* ------------------------------------------------------------------------ + + Python Codec Registry and support functions + + +Written by Marc-Andre Lemburg (mal@lemburg.com). + +Copyright (c) Corporation for National Research Initiatives. + + ------------------------------------------------------------------------ */ + +/* Register a new codec search function. + + As side effect, this tries to load the encodings package, if not + yet done, to make sure that it is always first in the list of + search functions. + + The search_function's refcount is incremented by this function. */ + +PyAPI_FUNC(int) PyCodec_Register( + PyObject *search_function + ); + +/* Codec register lookup API. + + Looks up the given encoding and returns a CodecInfo object with + function attributes which implement the different aspects of + processing the encoding. + + The encoding string is looked up converted to all lower-case + characters. This makes encodings looked up through this mechanism + effectively case-insensitive. + + If no codec is found, a KeyError is set and NULL returned. + + As side effect, this tries to load the encodings package, if not + yet done. This is part of the lazy load strategy for the encodings + package. + + */ + +PyAPI_FUNC(PyObject *) _PyCodec_Lookup( + const char *encoding + ); + +/* Generic codec based encoding API. + + object is passed through the encoder function found for the given + encoding using the error handling method defined by errors. errors + may be NULL to use the default method defined for the codec. + + Raises a LookupError in case no encoder can be found. + + */ + +PyAPI_FUNC(PyObject *) PyCodec_Encode( + PyObject *object, + const char *encoding, + const char *errors + ); + +/* Generic codec based decoding API. + + object is passed through the decoder function found for the given + encoding using the error handling method defined by errors. errors + may be NULL to use the default method defined for the codec. + + Raises a LookupError in case no encoder can be found. + + */ + +PyAPI_FUNC(PyObject *) PyCodec_Decode( + PyObject *object, + const char *encoding, + const char *errors + ); + +/* --- Codec Lookup APIs -------------------------------------------------- + + All APIs return a codec object with incremented refcount and are + based on _PyCodec_Lookup(). The same comments w/r to the encoding + name also apply to these APIs. + +*/ + +/* Get an encoder function for the given encoding. */ + +PyAPI_FUNC(PyObject *) PyCodec_Encoder( + const char *encoding + ); + +/* Get a decoder function for the given encoding. */ + +PyAPI_FUNC(PyObject *) PyCodec_Decoder( + const char *encoding + ); + +/* Get a IncrementalEncoder object for the given encoding. */ + +PyAPI_FUNC(PyObject *) PyCodec_IncrementalEncoder( + const char *encoding, + const char *errors + ); + +/* Get a IncrementalDecoder object function for the given encoding. */ + +PyAPI_FUNC(PyObject *) PyCodec_IncrementalDecoder( + const char *encoding, + const char *errors + ); + +/* Get a StreamReader factory function for the given encoding. */ + +PyAPI_FUNC(PyObject *) PyCodec_StreamReader( + const char *encoding, + PyObject *stream, + const char *errors + ); + +/* Get a StreamWriter factory function for the given encoding. */ + +PyAPI_FUNC(PyObject *) PyCodec_StreamWriter( + const char *encoding, + PyObject *stream, + const char *errors + ); + +/* Unicode encoding error handling callback registry API */ + +/* Register the error handling callback function error under the given + name. This function will be called by the codec when it encounters + unencodable characters/undecodable bytes and doesn't know the + callback name, when name is specified as the error parameter + in the call to the encode/decode function. + Return 0 on success, -1 on error */ +PyAPI_FUNC(int) PyCodec_RegisterError(const char *name, PyObject *error); + +/* Lookup the error handling callback function registered under the given + name. As a special case NULL can be passed, in which case + the error handling callback for "strict" will be returned. */ +PyAPI_FUNC(PyObject *) PyCodec_LookupError(const char *name); + +/* raise exc as an exception */ +PyAPI_FUNC(PyObject *) PyCodec_StrictErrors(PyObject *exc); + +/* ignore the unicode error, skipping the faulty input */ +PyAPI_FUNC(PyObject *) PyCodec_IgnoreErrors(PyObject *exc); + +/* replace the unicode encode error with ? or U+FFFD */ +PyAPI_FUNC(PyObject *) PyCodec_ReplaceErrors(PyObject *exc); + +/* replace the unicode encode error with XML character references */ +PyAPI_FUNC(PyObject *) PyCodec_XMLCharRefReplaceErrors(PyObject *exc); + +/* replace the unicode encode error with backslash escapes (\x, \u and \U) */ +PyAPI_FUNC(PyObject *) PyCodec_BackslashReplaceErrors(PyObject *exc); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_CODECREGISTRY_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/compile.h b/AppPkg/Applications/Python/Python-2.7.10/Include/compile.h new file mode 100644 index 0000000000..22cb75f073 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/compile.h @@ -0,0 +1,40 @@ + +#ifndef Py_COMPILE_H +#define Py_COMPILE_H + +#include "code.h" + +#ifdef __cplusplus +extern "C" { +#endif + +/* Public interface */ +struct _node; /* Declare the existence of this type */ +PyAPI_FUNC(PyCodeObject *) PyNode_Compile(struct _node *, const char *); + +/* Future feature support */ + +typedef struct { + int ff_features; /* flags set by future statements */ + int ff_lineno; /* line number of last future statement */ +} PyFutureFeatures; + +#define FUTURE_NESTED_SCOPES "nested_scopes" +#define FUTURE_GENERATORS "generators" +#define FUTURE_DIVISION "division" +#define FUTURE_ABSOLUTE_IMPORT "absolute_import" +#define FUTURE_WITH_STATEMENT "with_statement" +#define FUTURE_PRINT_FUNCTION "print_function" +#define FUTURE_UNICODE_LITERALS "unicode_literals" + + +struct _mod; /* Declare the existence of this type */ +PyAPI_FUNC(PyCodeObject *) PyAST_Compile(struct _mod *, const char *, + PyCompilerFlags *, PyArena *); +PyAPI_FUNC(PyFutureFeatures *) PyFuture_FromAST(struct _mod *, const char *); + + +#ifdef __cplusplus +} +#endif +#endif /* !Py_COMPILE_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/complexobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/complexobject.h new file mode 100644 index 0000000000..747048a9ac --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/complexobject.h @@ -0,0 +1,66 @@ +/* Complex number structure */ + +#ifndef Py_COMPLEXOBJECT_H +#define Py_COMPLEXOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +typedef struct { + double real; + double imag; +} Py_complex; + +/* Operations on complex numbers from complexmodule.c */ + +#define c_sum _Py_c_sum +#define c_diff _Py_c_diff +#define c_neg _Py_c_neg +#define c_prod _Py_c_prod +#define c_quot _Py_c_quot +#define c_pow _Py_c_pow +#define c_abs _Py_c_abs + +PyAPI_FUNC(Py_complex) c_sum(Py_complex, Py_complex); +PyAPI_FUNC(Py_complex) c_diff(Py_complex, Py_complex); +PyAPI_FUNC(Py_complex) c_neg(Py_complex); +PyAPI_FUNC(Py_complex) c_prod(Py_complex, Py_complex); +PyAPI_FUNC(Py_complex) c_quot(Py_complex, Py_complex); +PyAPI_FUNC(Py_complex) c_pow(Py_complex, Py_complex); +PyAPI_FUNC(double) c_abs(Py_complex); + + +/* Complex object interface */ + +/* +PyComplexObject represents a complex number with double-precision +real and imaginary parts. +*/ + +typedef struct { + PyObject_HEAD + Py_complex cval; +} PyComplexObject; + +PyAPI_DATA(PyTypeObject) PyComplex_Type; + +#define PyComplex_Check(op) PyObject_TypeCheck(op, &PyComplex_Type) +#define PyComplex_CheckExact(op) (Py_TYPE(op) == &PyComplex_Type) + +PyAPI_FUNC(PyObject *) PyComplex_FromCComplex(Py_complex); +PyAPI_FUNC(PyObject *) PyComplex_FromDoubles(double real, double imag); + +PyAPI_FUNC(double) PyComplex_RealAsDouble(PyObject *op); +PyAPI_FUNC(double) PyComplex_ImagAsDouble(PyObject *op); +PyAPI_FUNC(Py_complex) PyComplex_AsCComplex(PyObject *op); + +/* Format the object based on the format_spec, as defined in PEP 3101 + (Advanced String Formatting). */ +PyAPI_FUNC(PyObject *) _PyComplex_FormatAdvanced(PyObject *obj, + char *format_spec, + Py_ssize_t format_spec_len); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_COMPLEXOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/datetime.h b/AppPkg/Applications/Python/Python-2.7.10/Include/datetime.h new file mode 100644 index 0000000000..47d016270a --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/datetime.h @@ -0,0 +1,239 @@ +/* datetime.h + */ + +#ifndef DATETIME_H +#define DATETIME_H +#ifdef __cplusplus +extern "C" { +#endif + +/* Fields are packed into successive bytes, each viewed as unsigned and + * big-endian, unless otherwise noted: + * + * byte offset + * 0 year 2 bytes, 1-9999 + * 2 month 1 byte, 1-12 + * 3 day 1 byte, 1-31 + * 4 hour 1 byte, 0-23 + * 5 minute 1 byte, 0-59 + * 6 second 1 byte, 0-59 + * 7 usecond 3 bytes, 0-999999 + * 10 + */ + +/* # of bytes for year, month, and day. */ +#define _PyDateTime_DATE_DATASIZE 4 + +/* # of bytes for hour, minute, second, and usecond. */ +#define _PyDateTime_TIME_DATASIZE 6 + +/* # of bytes for year, month, day, hour, minute, second, and usecond. */ +#define _PyDateTime_DATETIME_DATASIZE 10 + + +typedef struct +{ + PyObject_HEAD + long hashcode; /* -1 when unknown */ + int days; /* -MAX_DELTA_DAYS <= days <= MAX_DELTA_DAYS */ + int seconds; /* 0 <= seconds < 24*3600 is invariant */ + int microseconds; /* 0 <= microseconds < 1000000 is invariant */ +} PyDateTime_Delta; + +typedef struct +{ + PyObject_HEAD /* a pure abstract base class */ +} PyDateTime_TZInfo; + + +/* The datetime and time types have hashcodes, and an optional tzinfo member, + * present if and only if hastzinfo is true. + */ +#define _PyTZINFO_HEAD \ + PyObject_HEAD \ + long hashcode; \ + char hastzinfo; /* boolean flag */ + +/* No _PyDateTime_BaseTZInfo is allocated; it's just to have something + * convenient to cast to, when getting at the hastzinfo member of objects + * starting with _PyTZINFO_HEAD. + */ +typedef struct +{ + _PyTZINFO_HEAD +} _PyDateTime_BaseTZInfo; + +/* All time objects are of PyDateTime_TimeType, but that can be allocated + * in two ways, with or without a tzinfo member. Without is the same as + * tzinfo == None, but consumes less memory. _PyDateTime_BaseTime is an + * internal struct used to allocate the right amount of space for the + * "without" case. + */ +#define _PyDateTime_TIMEHEAD \ + _PyTZINFO_HEAD \ + unsigned char data[_PyDateTime_TIME_DATASIZE]; + +typedef struct +{ + _PyDateTime_TIMEHEAD +} _PyDateTime_BaseTime; /* hastzinfo false */ + +typedef struct +{ + _PyDateTime_TIMEHEAD + PyObject *tzinfo; +} PyDateTime_Time; /* hastzinfo true */ + + +/* All datetime objects are of PyDateTime_DateTimeType, but that can be + * allocated in two ways too, just like for time objects above. In addition, + * the plain date type is a base class for datetime, so it must also have + * a hastzinfo member (although it's unused there). + */ +typedef struct +{ + _PyTZINFO_HEAD + unsigned char data[_PyDateTime_DATE_DATASIZE]; +} PyDateTime_Date; + +#define _PyDateTime_DATETIMEHEAD \ + _PyTZINFO_HEAD \ + unsigned char data[_PyDateTime_DATETIME_DATASIZE]; + +typedef struct +{ + _PyDateTime_DATETIMEHEAD +} _PyDateTime_BaseDateTime; /* hastzinfo false */ + +typedef struct +{ + _PyDateTime_DATETIMEHEAD + PyObject *tzinfo; +} PyDateTime_DateTime; /* hastzinfo true */ + + +/* Apply for date and datetime instances. */ +#define PyDateTime_GET_YEAR(o) ((((PyDateTime_Date*)o)->data[0] << 8) | \ + ((PyDateTime_Date*)o)->data[1]) +#define PyDateTime_GET_MONTH(o) (((PyDateTime_Date*)o)->data[2]) +#define PyDateTime_GET_DAY(o) (((PyDateTime_Date*)o)->data[3]) + +#define PyDateTime_DATE_GET_HOUR(o) (((PyDateTime_DateTime*)o)->data[4]) +#define PyDateTime_DATE_GET_MINUTE(o) (((PyDateTime_DateTime*)o)->data[5]) +#define PyDateTime_DATE_GET_SECOND(o) (((PyDateTime_DateTime*)o)->data[6]) +#define PyDateTime_DATE_GET_MICROSECOND(o) \ + ((((PyDateTime_DateTime*)o)->data[7] << 16) | \ + (((PyDateTime_DateTime*)o)->data[8] << 8) | \ + ((PyDateTime_DateTime*)o)->data[9]) + +/* Apply for time instances. */ +#define PyDateTime_TIME_GET_HOUR(o) (((PyDateTime_Time*)o)->data[0]) +#define PyDateTime_TIME_GET_MINUTE(o) (((PyDateTime_Time*)o)->data[1]) +#define PyDateTime_TIME_GET_SECOND(o) (((PyDateTime_Time*)o)->data[2]) +#define PyDateTime_TIME_GET_MICROSECOND(o) \ + ((((PyDateTime_Time*)o)->data[3] << 16) | \ + (((PyDateTime_Time*)o)->data[4] << 8) | \ + ((PyDateTime_Time*)o)->data[5]) + + +/* Define structure for C API. */ +typedef struct { + /* type objects */ + PyTypeObject *DateType; + PyTypeObject *DateTimeType; + PyTypeObject *TimeType; + PyTypeObject *DeltaType; + PyTypeObject *TZInfoType; + + /* constructors */ + PyObject *(*Date_FromDate)(int, int, int, PyTypeObject*); + PyObject *(*DateTime_FromDateAndTime)(int, int, int, int, int, int, int, + PyObject*, PyTypeObject*); + PyObject *(*Time_FromTime)(int, int, int, int, PyObject*, PyTypeObject*); + PyObject *(*Delta_FromDelta)(int, int, int, int, PyTypeObject*); + + /* constructors for the DB API */ + PyObject *(*DateTime_FromTimestamp)(PyObject*, PyObject*, PyObject*); + PyObject *(*Date_FromTimestamp)(PyObject*, PyObject*); + +} PyDateTime_CAPI; + +#define PyDateTime_CAPSULE_NAME "datetime.datetime_CAPI" + + +/* "magic" constant used to partially protect against developer mistakes. */ +#define DATETIME_API_MAGIC 0x414548d5 + +#ifdef Py_BUILD_CORE + +/* Macros for type checking when building the Python core. */ +#define PyDate_Check(op) PyObject_TypeCheck(op, &PyDateTime_DateType) +#define PyDate_CheckExact(op) (Py_TYPE(op) == &PyDateTime_DateType) + +#define PyDateTime_Check(op) PyObject_TypeCheck(op, &PyDateTime_DateTimeType) +#define PyDateTime_CheckExact(op) (Py_TYPE(op) == &PyDateTime_DateTimeType) + +#define PyTime_Check(op) PyObject_TypeCheck(op, &PyDateTime_TimeType) +#define PyTime_CheckExact(op) (Py_TYPE(op) == &PyDateTime_TimeType) + +#define PyDelta_Check(op) PyObject_TypeCheck(op, &PyDateTime_DeltaType) +#define PyDelta_CheckExact(op) (Py_TYPE(op) == &PyDateTime_DeltaType) + +#define PyTZInfo_Check(op) PyObject_TypeCheck(op, &PyDateTime_TZInfoType) +#define PyTZInfo_CheckExact(op) (Py_TYPE(op) == &PyDateTime_TZInfoType) + +#else + +/* Define global variable for the C API and a macro for setting it. */ +static PyDateTime_CAPI *PyDateTimeAPI = NULL; + +#define PyDateTime_IMPORT \ + PyDateTimeAPI = (PyDateTime_CAPI *)PyCapsule_Import(PyDateTime_CAPSULE_NAME, 0) + +/* Macros for type checking when not building the Python core. */ +#define PyDate_Check(op) PyObject_TypeCheck(op, PyDateTimeAPI->DateType) +#define PyDate_CheckExact(op) (Py_TYPE(op) == PyDateTimeAPI->DateType) + +#define PyDateTime_Check(op) PyObject_TypeCheck(op, PyDateTimeAPI->DateTimeType) +#define PyDateTime_CheckExact(op) (Py_TYPE(op) == PyDateTimeAPI->DateTimeType) + +#define PyTime_Check(op) PyObject_TypeCheck(op, PyDateTimeAPI->TimeType) +#define PyTime_CheckExact(op) (Py_TYPE(op) == PyDateTimeAPI->TimeType) + +#define PyDelta_Check(op) PyObject_TypeCheck(op, PyDateTimeAPI->DeltaType) +#define PyDelta_CheckExact(op) (Py_TYPE(op) == PyDateTimeAPI->DeltaType) + +#define PyTZInfo_Check(op) PyObject_TypeCheck(op, PyDateTimeAPI->TZInfoType) +#define PyTZInfo_CheckExact(op) (Py_TYPE(op) == PyDateTimeAPI->TZInfoType) + +/* Macros for accessing constructors in a simplified fashion. */ +#define PyDate_FromDate(year, month, day) \ + PyDateTimeAPI->Date_FromDate(year, month, day, PyDateTimeAPI->DateType) + +#define PyDateTime_FromDateAndTime(year, month, day, hour, min, sec, usec) \ + PyDateTimeAPI->DateTime_FromDateAndTime(year, month, day, hour, \ + min, sec, usec, Py_None, PyDateTimeAPI->DateTimeType) + +#define PyTime_FromTime(hour, minute, second, usecond) \ + PyDateTimeAPI->Time_FromTime(hour, minute, second, usecond, \ + Py_None, PyDateTimeAPI->TimeType) + +#define PyDelta_FromDSU(days, seconds, useconds) \ + PyDateTimeAPI->Delta_FromDelta(days, seconds, useconds, 1, \ + PyDateTimeAPI->DeltaType) + +/* Macros supporting the DB API. */ +#define PyDateTime_FromTimestamp(args) \ + PyDateTimeAPI->DateTime_FromTimestamp( \ + (PyObject*) (PyDateTimeAPI->DateTimeType), args, NULL) + +#define PyDate_FromTimestamp(args) \ + PyDateTimeAPI->Date_FromTimestamp( \ + (PyObject*) (PyDateTimeAPI->DateType), args) + +#endif /* Py_BUILD_CORE */ + +#ifdef __cplusplus +} +#endif +#endif diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/descrobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/descrobject.h new file mode 100644 index 0000000000..5a9c3e17e6 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/descrobject.h @@ -0,0 +1,94 @@ +/* Descriptors */ +#ifndef Py_DESCROBJECT_H +#define Py_DESCROBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +typedef PyObject *(*getter)(PyObject *, void *); +typedef int (*setter)(PyObject *, PyObject *, void *); + +typedef struct PyGetSetDef { + char *name; + getter get; + setter set; + char *doc; + void *closure; +} PyGetSetDef; + +typedef PyObject *(*wrapperfunc)(PyObject *self, PyObject *args, + void *wrapped); + +typedef PyObject *(*wrapperfunc_kwds)(PyObject *self, PyObject *args, + void *wrapped, PyObject *kwds); + +struct wrapperbase { + char *name; + int offset; + void *function; + wrapperfunc wrapper; + char *doc; + int flags; + PyObject *name_strobj; +}; + +/* Flags for above struct */ +#define PyWrapperFlag_KEYWORDS 1 /* wrapper function takes keyword args */ + +/* Various kinds of descriptor objects */ + +#define PyDescr_COMMON \ + PyObject_HEAD \ + PyTypeObject *d_type; \ + PyObject *d_name + +typedef struct { + PyDescr_COMMON; +} PyDescrObject; + +typedef struct { + PyDescr_COMMON; + PyMethodDef *d_method; +} PyMethodDescrObject; + +typedef struct { + PyDescr_COMMON; + struct PyMemberDef *d_member; +} PyMemberDescrObject; + +typedef struct { + PyDescr_COMMON; + PyGetSetDef *d_getset; +} PyGetSetDescrObject; + +typedef struct { + PyDescr_COMMON; + struct wrapperbase *d_base; + void *d_wrapped; /* This can be any function pointer */ +} PyWrapperDescrObject; + +PyAPI_DATA(PyTypeObject) PyWrapperDescr_Type; +PyAPI_DATA(PyTypeObject) PyDictProxy_Type; +PyAPI_DATA(PyTypeObject) PyGetSetDescr_Type; +PyAPI_DATA(PyTypeObject) PyMemberDescr_Type; + +PyAPI_FUNC(PyObject *) PyDescr_NewMethod(PyTypeObject *, PyMethodDef *); +PyAPI_FUNC(PyObject *) PyDescr_NewClassMethod(PyTypeObject *, PyMethodDef *); +PyAPI_FUNC(PyObject *) PyDescr_NewMember(PyTypeObject *, + struct PyMemberDef *); +PyAPI_FUNC(PyObject *) PyDescr_NewGetSet(PyTypeObject *, + struct PyGetSetDef *); +PyAPI_FUNC(PyObject *) PyDescr_NewWrapper(PyTypeObject *, + struct wrapperbase *, void *); +#define PyDescr_IsData(d) (Py_TYPE(d)->tp_descr_set != NULL) + +PyAPI_FUNC(PyObject *) PyDictProxy_New(PyObject *); +PyAPI_FUNC(PyObject *) PyWrapper_New(PyObject *, PyObject *); + + +PyAPI_DATA(PyTypeObject) PyProperty_Type; +#ifdef __cplusplus +} +#endif +#endif /* !Py_DESCROBJECT_H */ + diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/dictobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/dictobject.h new file mode 100644 index 0000000000..0f3ab17caa --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/dictobject.h @@ -0,0 +1,156 @@ +#ifndef Py_DICTOBJECT_H +#define Py_DICTOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + + +/* Dictionary object type -- mapping from hashable object to object */ + +/* The distribution includes a separate file, Objects/dictnotes.txt, + describing explorations into dictionary design and optimization. + It covers typical dictionary use patterns, the parameters for + tuning dictionaries, and several ideas for possible optimizations. +*/ + +/* +There are three kinds of slots in the table: + +1. Unused. me_key == me_value == NULL + Does not hold an active (key, value) pair now and never did. Unused can + transition to Active upon key insertion. This is the only case in which + me_key is NULL, and is each slot's initial state. + +2. Active. me_key != NULL and me_key != dummy and me_value != NULL + Holds an active (key, value) pair. Active can transition to Dummy upon + key deletion. This is the only case in which me_value != NULL. + +3. Dummy. me_key == dummy and me_value == NULL + Previously held an active (key, value) pair, but that was deleted and an + active pair has not yet overwritten the slot. Dummy can transition to + Active upon key insertion. Dummy slots cannot be made Unused again + (cannot have me_key set to NULL), else the probe sequence in case of + collision would have no way to know they were once active. + +Note: .popitem() abuses the me_hash field of an Unused or Dummy slot to +hold a search finger. The me_hash field of Unused or Dummy slots has no +meaning otherwise. +*/ + +/* PyDict_MINSIZE is the minimum size of a dictionary. This many slots are + * allocated directly in the dict object (in the ma_smalltable member). + * It must be a power of 2, and at least 4. 8 allows dicts with no more + * than 5 active entries to live in ma_smalltable (and so avoid an + * additional malloc); instrumentation suggested this suffices for the + * majority of dicts (consisting mostly of usually-small instance dicts and + * usually-small dicts created to pass keyword arguments). + */ +#define PyDict_MINSIZE 8 + +typedef struct { + /* Cached hash code of me_key. Note that hash codes are C longs. + * We have to use Py_ssize_t instead because dict_popitem() abuses + * me_hash to hold a search finger. + */ + Py_ssize_t me_hash; + PyObject *me_key; + PyObject *me_value; +} PyDictEntry; + +/* +To ensure the lookup algorithm terminates, there must be at least one Unused +slot (NULL key) in the table. +The value ma_fill is the number of non-NULL keys (sum of Active and Dummy); +ma_used is the number of non-NULL, non-dummy keys (== the number of non-NULL +values == the number of Active items). +To avoid slowing down lookups on a near-full table, we resize the table when +it's two-thirds full. +*/ +typedef struct _dictobject PyDictObject; +struct _dictobject { + PyObject_HEAD + Py_ssize_t ma_fill; /* # Active + # Dummy */ + Py_ssize_t ma_used; /* # Active */ + + /* The table contains ma_mask + 1 slots, and that's a power of 2. + * We store the mask instead of the size because the mask is more + * frequently needed. + */ + Py_ssize_t ma_mask; + + /* ma_table points to ma_smalltable for small tables, else to + * additional malloc'ed memory. ma_table is never NULL! This rule + * saves repeated runtime null-tests in the workhorse getitem and + * setitem calls. + */ + PyDictEntry *ma_table; + PyDictEntry *(*ma_lookup)(PyDictObject *mp, PyObject *key, long hash); + PyDictEntry ma_smalltable[PyDict_MINSIZE]; +}; + +PyAPI_DATA(PyTypeObject) PyDict_Type; +PyAPI_DATA(PyTypeObject) PyDictIterKey_Type; +PyAPI_DATA(PyTypeObject) PyDictIterValue_Type; +PyAPI_DATA(PyTypeObject) PyDictIterItem_Type; +PyAPI_DATA(PyTypeObject) PyDictKeys_Type; +PyAPI_DATA(PyTypeObject) PyDictItems_Type; +PyAPI_DATA(PyTypeObject) PyDictValues_Type; + +#define PyDict_Check(op) \ + PyType_FastSubclass(Py_TYPE(op), Py_TPFLAGS_DICT_SUBCLASS) +#define PyDict_CheckExact(op) (Py_TYPE(op) == &PyDict_Type) +#define PyDictKeys_Check(op) (Py_TYPE(op) == &PyDictKeys_Type) +#define PyDictItems_Check(op) (Py_TYPE(op) == &PyDictItems_Type) +#define PyDictValues_Check(op) (Py_TYPE(op) == &PyDictValues_Type) +/* This excludes Values, since they are not sets. */ +# define PyDictViewSet_Check(op) \ + (PyDictKeys_Check(op) || PyDictItems_Check(op)) + +PyAPI_FUNC(PyObject *) PyDict_New(void); +PyAPI_FUNC(PyObject *) PyDict_GetItem(PyObject *mp, PyObject *key); +PyAPI_FUNC(int) PyDict_SetItem(PyObject *mp, PyObject *key, PyObject *item); +PyAPI_FUNC(int) PyDict_DelItem(PyObject *mp, PyObject *key); +PyAPI_FUNC(void) PyDict_Clear(PyObject *mp); +PyAPI_FUNC(int) PyDict_Next( + PyObject *mp, Py_ssize_t *pos, PyObject **key, PyObject **value); +PyAPI_FUNC(int) _PyDict_Next( + PyObject *mp, Py_ssize_t *pos, PyObject **key, PyObject **value, long *hash); +PyAPI_FUNC(PyObject *) PyDict_Keys(PyObject *mp); +PyAPI_FUNC(PyObject *) PyDict_Values(PyObject *mp); +PyAPI_FUNC(PyObject *) PyDict_Items(PyObject *mp); +PyAPI_FUNC(Py_ssize_t) PyDict_Size(PyObject *mp); +PyAPI_FUNC(PyObject *) PyDict_Copy(PyObject *mp); +PyAPI_FUNC(int) PyDict_Contains(PyObject *mp, PyObject *key); +PyAPI_FUNC(int) _PyDict_Contains(PyObject *mp, PyObject *key, long hash); +PyAPI_FUNC(PyObject *) _PyDict_NewPresized(Py_ssize_t minused); +PyAPI_FUNC(void) _PyDict_MaybeUntrack(PyObject *mp); + +/* PyDict_Update(mp, other) is equivalent to PyDict_Merge(mp, other, 1). */ +PyAPI_FUNC(int) PyDict_Update(PyObject *mp, PyObject *other); + +/* PyDict_Merge updates/merges from a mapping object (an object that + supports PyMapping_Keys() and PyObject_GetItem()). If override is true, + the last occurrence of a key wins, else the first. The Python + dict.update(other) is equivalent to PyDict_Merge(dict, other, 1). +*/ +PyAPI_FUNC(int) PyDict_Merge(PyObject *mp, + PyObject *other, + int override); + +/* PyDict_MergeFromSeq2 updates/merges from an iterable object producing + iterable objects of length 2. If override is true, the last occurrence + of a key wins, else the first. The Python dict constructor dict(seq2) + is equivalent to dict={}; PyDict_MergeFromSeq(dict, seq2, 1). +*/ +PyAPI_FUNC(int) PyDict_MergeFromSeq2(PyObject *d, + PyObject *seq2, + int override); + +PyAPI_FUNC(PyObject *) PyDict_GetItemString(PyObject *dp, const char *key); +PyAPI_FUNC(int) PyDict_SetItemString(PyObject *dp, const char *key, PyObject *item); +PyAPI_FUNC(int) PyDict_DelItemString(PyObject *dp, const char *key); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_DICTOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/dtoa.h b/AppPkg/Applications/Python/Python-2.7.10/Include/dtoa.h new file mode 100644 index 0000000000..c7e80bcf8a --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/dtoa.h @@ -0,0 +1,15 @@ +#ifndef PY_NO_SHORT_FLOAT_REPR +#ifdef __cplusplus +extern "C" { +#endif + +PyAPI_FUNC(double) _Py_dg_strtod(const char *str, char **ptr); +PyAPI_FUNC(char *) _Py_dg_dtoa(double d, int mode, int ndigits, + int *decpt, int *sign, char **rve); +PyAPI_FUNC(void) _Py_dg_freedtoa(char *s); + + +#ifdef __cplusplus +} +#endif +#endif diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/enumobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/enumobject.h new file mode 100644 index 0000000000..42dc2d27de --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/enumobject.h @@ -0,0 +1,17 @@ +#ifndef Py_ENUMOBJECT_H +#define Py_ENUMOBJECT_H + +/* Enumerate Object */ + +#ifdef __cplusplus +extern "C" { +#endif + +PyAPI_DATA(PyTypeObject) PyEnum_Type; +PyAPI_DATA(PyTypeObject) PyReversed_Type; + +#ifdef __cplusplus +} +#endif + +#endif /* !Py_ENUMOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/errcode.h b/AppPkg/Applications/Python/Python-2.7.10/Include/errcode.h new file mode 100644 index 0000000000..295295cd60 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/errcode.h @@ -0,0 +1,36 @@ +#ifndef Py_ERRCODE_H +#define Py_ERRCODE_H +#ifdef __cplusplus +extern "C" { +#endif + + +/* Error codes passed around between file input, tokenizer, parser and + interpreter. This is necessary so we can turn them into Python + exceptions at a higher level. Note that some errors have a + slightly different meaning when passed from the tokenizer to the + parser than when passed from the parser to the interpreter; e.g. + the parser only returns E_EOF when it hits EOF immediately, and it + never returns E_OK. */ + +#define E_OK 10 /* No error */ +#define E_EOF 11 /* End Of File */ +#define E_INTR 12 /* Interrupted */ +#define E_TOKEN 13 /* Bad token */ +#define E_SYNTAX 14 /* Syntax error */ +#define E_NOMEM 15 /* Ran out of memory */ +#define E_DONE 16 /* Parsing complete */ +#define E_ERROR 17 /* Execution error */ +#define E_TABSPACE 18 /* Inconsistent mixing of tabs and spaces */ +#define E_OVERFLOW 19 /* Node had too many children */ +#define E_TOODEEP 20 /* Too many indentation levels */ +#define E_DEDENT 21 /* No matching outer block for dedent */ +#define E_DECODE 22 /* Error in decoding into Unicode */ +#define E_EOFS 23 /* EOF in triple-quoted string */ +#define E_EOLS 24 /* EOL in single-quoted string */ +#define E_LINECONT 25 /* Unexpected characters after a line continuation */ + +#ifdef __cplusplus +} +#endif +#endif /* !Py_ERRCODE_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/eval.h b/AppPkg/Applications/Python/Python-2.7.10/Include/eval.h new file mode 100644 index 0000000000..fe1d47aebb --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/eval.h @@ -0,0 +1,25 @@ + +/* Interface to execute compiled code */ + +#ifndef Py_EVAL_H +#define Py_EVAL_H +#ifdef __cplusplus +extern "C" { +#endif + +PyAPI_FUNC(PyObject *) PyEval_EvalCode(PyCodeObject *, PyObject *, PyObject *); + +PyAPI_FUNC(PyObject *) PyEval_EvalCodeEx(PyCodeObject *co, + PyObject *globals, + PyObject *locals, + PyObject **args, int argc, + PyObject **kwds, int kwdc, + PyObject **defs, int defc, + PyObject *closure); + +PyAPI_FUNC(PyObject *) _PyEval_CallTracing(PyObject *func, PyObject *args); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_EVAL_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/fileobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/fileobject.h new file mode 100644 index 0000000000..c16aed9fbb --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/fileobject.h @@ -0,0 +1,97 @@ + +/* File object interface */ + +#ifndef Py_FILEOBJECT_H +#define Py_FILEOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +typedef struct { + PyObject_HEAD + FILE *f_fp; + PyObject *f_name; + PyObject *f_mode; + int (*f_close)(FILE *); + int f_softspace; /* Flag used by 'print' command */ + int f_binary; /* Flag which indicates whether the file is + open in binary (1) or text (0) mode */ + char* f_buf; /* Allocated readahead buffer */ + char* f_bufend; /* Points after last occupied position */ + char* f_bufptr; /* Current buffer position */ + char *f_setbuf; /* Buffer for setbuf(3) and setvbuf(3) */ + int f_univ_newline; /* Handle any newline convention */ + int f_newlinetypes; /* Types of newlines seen */ + int f_skipnextlf; /* Skip next \n */ + PyObject *f_encoding; + PyObject *f_errors; + PyObject *weakreflist; /* List of weak references */ + int unlocked_count; /* Num. currently running sections of code + using f_fp with the GIL released. */ + int readable; + int writable; +} PyFileObject; + +PyAPI_DATA(PyTypeObject) PyFile_Type; + +#define PyFile_Check(op) PyObject_TypeCheck(op, &PyFile_Type) +#define PyFile_CheckExact(op) (Py_TYPE(op) == &PyFile_Type) + +PyAPI_FUNC(PyObject *) PyFile_FromString(char *, char *); +PyAPI_FUNC(void) PyFile_SetBufSize(PyObject *, int); +PyAPI_FUNC(int) PyFile_SetEncoding(PyObject *, const char *); +PyAPI_FUNC(int) PyFile_SetEncodingAndErrors(PyObject *, const char *, char *errors); +PyAPI_FUNC(PyObject *) PyFile_FromFile(FILE *, char *, char *, + int (*)(FILE *)); +PyAPI_FUNC(FILE *) PyFile_AsFile(PyObject *); +PyAPI_FUNC(void) PyFile_IncUseCount(PyFileObject *); +PyAPI_FUNC(void) PyFile_DecUseCount(PyFileObject *); +PyAPI_FUNC(PyObject *) PyFile_Name(PyObject *); +PyAPI_FUNC(PyObject *) PyFile_GetLine(PyObject *, int); +PyAPI_FUNC(int) PyFile_WriteObject(PyObject *, PyObject *, int); +PyAPI_FUNC(int) PyFile_SoftSpace(PyObject *, int); +PyAPI_FUNC(int) PyFile_WriteString(const char *, PyObject *); +PyAPI_FUNC(int) PyObject_AsFileDescriptor(PyObject *); + +/* The default encoding used by the platform file system APIs + If non-NULL, this is different than the default encoding for strings +*/ +PyAPI_DATA(const char *) Py_FileSystemDefaultEncoding; + +/* Routines to replace fread() and fgets() which accept any of \r, \n + or \r\n as line terminators. +*/ +#define PY_STDIOTEXTMODE "b" +char *Py_UniversalNewlineFgets(char *, int, FILE*, PyObject *); +size_t Py_UniversalNewlineFread(char *, size_t, FILE *, PyObject *); + +/* A routine to do sanity checking on the file mode string. returns + non-zero on if an exception occurred +*/ +int _PyFile_SanitizeMode(char *mode); + +#if defined _MSC_VER && _MSC_VER >= 1400 +/* A routine to check if a file descriptor is valid on Windows. Returns 0 + * and sets errno to EBADF if it isn't. This is to avoid Assertions + * from various functions in the Windows CRT beginning with + * Visual Studio 2005 + */ +int _PyVerify_fd(int fd); +#elif defined _MSC_VER && _MSC_VER >= 1200 +/* fdopen doesn't set errno EBADF and crashes for large fd on debug build */ +#define _PyVerify_fd(fd) (_get_osfhandle(fd) >= 0) +#else +#define _PyVerify_fd(A) (1) /* dummy */ +#endif + +/* A routine to check if a file descriptor can be select()-ed. */ +#ifdef HAVE_SELECT + #define _PyIsSelectable_fd(FD) (((FD) >= 0) && ((FD) < FD_SETSIZE)) +#else + #define _PyIsSelectable_fd(FD) (1) +#endif /* HAVE_SELECT */ + +#ifdef __cplusplus +} +#endif +#endif /* !Py_FILEOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/floatobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/floatobject.h new file mode 100644 index 0000000000..92c69fe88f --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/floatobject.h @@ -0,0 +1,140 @@ + +/* Float object interface */ + +/* +PyFloatObject represents a (double precision) floating point number. +*/ + +#ifndef Py_FLOATOBJECT_H +#define Py_FLOATOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +typedef struct { + PyObject_HEAD + double ob_fval; +} PyFloatObject; + +PyAPI_DATA(PyTypeObject) PyFloat_Type; + +#define PyFloat_Check(op) PyObject_TypeCheck(op, &PyFloat_Type) +#define PyFloat_CheckExact(op) (Py_TYPE(op) == &PyFloat_Type) + +/* The str() precision PyFloat_STR_PRECISION is chosen so that in most cases, + the rounding noise created by various operations is suppressed, while + giving plenty of precision for practical use. */ + +#define PyFloat_STR_PRECISION 12 + +#ifdef Py_NAN +#define Py_RETURN_NAN return PyFloat_FromDouble(Py_NAN) +#endif + +#define Py_RETURN_INF(sign) do \ + if (copysign(1., sign) == 1.) { \ + return PyFloat_FromDouble(Py_HUGE_VAL); \ + } else { \ + return PyFloat_FromDouble(-Py_HUGE_VAL); \ + } while(0) + +PyAPI_FUNC(double) PyFloat_GetMax(void); +PyAPI_FUNC(double) PyFloat_GetMin(void); +PyAPI_FUNC(PyObject *) PyFloat_GetInfo(void); + +/* Return Python float from string PyObject. Second argument ignored on + input, and, if non-NULL, NULL is stored into *junk (this tried to serve a + purpose once but can't be made to work as intended). */ +PyAPI_FUNC(PyObject *) PyFloat_FromString(PyObject*, char** junk); + +/* Return Python float from C double. */ +PyAPI_FUNC(PyObject *) PyFloat_FromDouble(double); + +/* Extract C double from Python float. The macro version trades safety for + speed. */ +PyAPI_FUNC(double) PyFloat_AsDouble(PyObject *); +#define PyFloat_AS_DOUBLE(op) (((PyFloatObject *)(op))->ob_fval) + +/* Write repr(v) into the char buffer argument, followed by null byte. The + buffer must be "big enough"; >= 100 is very safe. + PyFloat_AsReprString(buf, x) strives to print enough digits so that + PyFloat_FromString(buf) then reproduces x exactly. */ +PyAPI_FUNC(void) PyFloat_AsReprString(char*, PyFloatObject *v); + +/* Write str(v) into the char buffer argument, followed by null byte. The + buffer must be "big enough"; >= 100 is very safe. Note that it's + unusual to be able to get back the float you started with from + PyFloat_AsString's result -- use PyFloat_AsReprString() if you want to + preserve precision across conversions. */ +PyAPI_FUNC(void) PyFloat_AsString(char*, PyFloatObject *v); + +/* _PyFloat_{Pack,Unpack}{4,8} + * + * The struct and pickle (at least) modules need an efficient platform- + * independent way to store floating-point values as byte strings. + * The Pack routines produce a string from a C double, and the Unpack + * routines produce a C double from such a string. The suffix (4 or 8) + * specifies the number of bytes in the string. + * + * On platforms that appear to use (see _PyFloat_Init()) IEEE-754 formats + * these functions work by copying bits. On other platforms, the formats the + * 4- byte format is identical to the IEEE-754 single precision format, and + * the 8-byte format to the IEEE-754 double precision format, although the + * packing of INFs and NaNs (if such things exist on the platform) isn't + * handled correctly, and attempting to unpack a string containing an IEEE + * INF or NaN will raise an exception. + * + * On non-IEEE platforms with more precision, or larger dynamic range, than + * 754 supports, not all values can be packed; on non-IEEE platforms with less + * precision, or smaller dynamic range, not all values can be unpacked. What + * happens in such cases is partly accidental (alas). + */ + +/* The pack routines write 4 or 8 bytes, starting at p. le is a bool + * argument, true if you want the string in little-endian format (exponent + * last, at p+3 or p+7), false if you want big-endian format (exponent + * first, at p). + * Return value: 0 if all is OK, -1 if error (and an exception is + * set, most likely OverflowError). + * There are two problems on non-IEEE platforms: + * 1): What this does is undefined if x is a NaN or infinity. + * 2): -0.0 and +0.0 produce the same string. + */ +PyAPI_FUNC(int) _PyFloat_Pack4(double x, unsigned char *p, int le); +PyAPI_FUNC(int) _PyFloat_Pack8(double x, unsigned char *p, int le); + +/* Used to get the important decimal digits of a double */ +PyAPI_FUNC(int) _PyFloat_Digits(char *buf, double v, int *signum); +PyAPI_FUNC(void) _PyFloat_DigitsInit(void); + +/* The unpack routines read 4 or 8 bytes, starting at p. le is a bool + * argument, true if the string is in little-endian format (exponent + * last, at p+3 or p+7), false if big-endian (exponent first, at p). + * Return value: The unpacked double. On error, this is -1.0 and + * PyErr_Occurred() is true (and an exception is set, most likely + * OverflowError). Note that on a non-IEEE platform this will refuse + * to unpack a string that represents a NaN or infinity. + */ +PyAPI_FUNC(double) _PyFloat_Unpack4(const unsigned char *p, int le); +PyAPI_FUNC(double) _PyFloat_Unpack8(const unsigned char *p, int le); + +/* free list api */ +PyAPI_FUNC(int) PyFloat_ClearFreeList(void); + +/* Format the object based on the format_spec, as defined in PEP 3101 + (Advanced String Formatting). */ +PyAPI_FUNC(PyObject *) _PyFloat_FormatAdvanced(PyObject *obj, + char *format_spec, + Py_ssize_t format_spec_len); + +/* Round a C double x to the closest multiple of 10**-ndigits. Returns a + Python float on success, or NULL (with an appropriate exception set) on + failure. Used in builtin_round in bltinmodule.c. */ +PyAPI_FUNC(PyObject *) _Py_double_round(double x, int ndigits); + + + +#ifdef __cplusplus +} +#endif +#endif /* !Py_FLOATOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/frameobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/frameobject.h new file mode 100644 index 0000000000..2298ed315c --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/frameobject.h @@ -0,0 +1,89 @@ + +/* Frame object interface */ + +#ifndef Py_FRAMEOBJECT_H +#define Py_FRAMEOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +typedef struct { + int b_type; /* what kind of block this is */ + int b_handler; /* where to jump to find handler */ + int b_level; /* value stack level to pop to */ +} PyTryBlock; + +typedef struct _frame { + PyObject_VAR_HEAD + struct _frame *f_back; /* previous frame, or NULL */ + PyCodeObject *f_code; /* code segment */ + PyObject *f_builtins; /* builtin symbol table (PyDictObject) */ + PyObject *f_globals; /* global symbol table (PyDictObject) */ + PyObject *f_locals; /* local symbol table (any mapping) */ + PyObject **f_valuestack; /* points after the last local */ + /* Next free slot in f_valuestack. Frame creation sets to f_valuestack. + Frame evaluation usually NULLs it, but a frame that yields sets it + to the current stack top. */ + PyObject **f_stacktop; + PyObject *f_trace; /* Trace function */ + + /* If an exception is raised in this frame, the next three are used to + * record the exception info (if any) originally in the thread state. See + * comments before set_exc_info() -- it's not obvious. + * Invariant: if _type is NULL, then so are _value and _traceback. + * Desired invariant: all three are NULL, or all three are non-NULL. That + * one isn't currently true, but "should be". + */ + PyObject *f_exc_type, *f_exc_value, *f_exc_traceback; + + PyThreadState *f_tstate; + int f_lasti; /* Last instruction if called */ + /* Call PyFrame_GetLineNumber() instead of reading this field + directly. As of 2.3 f_lineno is only valid when tracing is + active (i.e. when f_trace is set). At other times we use + PyCode_Addr2Line to calculate the line from the current + bytecode index. */ + int f_lineno; /* Current line number */ + int f_iblock; /* index in f_blockstack */ + PyTryBlock f_blockstack[CO_MAXBLOCKS]; /* for try and loop blocks */ + PyObject *f_localsplus[1]; /* locals+stack, dynamically sized */ +} PyFrameObject; + + +/* Standard object interface */ + +PyAPI_DATA(PyTypeObject) PyFrame_Type; + +#define PyFrame_Check(op) ((op)->ob_type == &PyFrame_Type) +#define PyFrame_IsRestricted(f) \ + ((f)->f_builtins != (f)->f_tstate->interp->builtins) + +PyAPI_FUNC(PyFrameObject *) PyFrame_New(PyThreadState *, PyCodeObject *, + PyObject *, PyObject *); + + +/* The rest of the interface is specific for frame objects */ + +/* Block management functions */ + +PyAPI_FUNC(void) PyFrame_BlockSetup(PyFrameObject *, int, int, int); +PyAPI_FUNC(PyTryBlock *) PyFrame_BlockPop(PyFrameObject *); + +/* Extend the value stack */ + +PyAPI_FUNC(PyObject **) PyFrame_ExtendStack(PyFrameObject *, int, int); + +/* Conversions between "fast locals" and locals in dictionary */ + +PyAPI_FUNC(void) PyFrame_LocalsToFast(PyFrameObject *, int); +PyAPI_FUNC(void) PyFrame_FastToLocals(PyFrameObject *); + +PyAPI_FUNC(int) PyFrame_ClearFreeList(void); + +/* Return the line of code the frame is currently executing. */ +PyAPI_FUNC(int) PyFrame_GetLineNumber(PyFrameObject *); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_FRAMEOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/funcobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/funcobject.h new file mode 100644 index 0000000000..07c05ce3f8 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/funcobject.h @@ -0,0 +1,76 @@ + +/* Function object interface */ + +#ifndef Py_FUNCOBJECT_H +#define Py_FUNCOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +/* Function objects and code objects should not be confused with each other: + * + * Function objects are created by the execution of the 'def' statement. + * They reference a code object in their func_code attribute, which is a + * purely syntactic object, i.e. nothing more than a compiled version of some + * source code lines. There is one code object per source code "fragment", + * but each code object can be referenced by zero or many function objects + * depending only on how many times the 'def' statement in the source was + * executed so far. + */ + +typedef struct { + PyObject_HEAD + PyObject *func_code; /* A code object */ + PyObject *func_globals; /* A dictionary (other mappings won't do) */ + PyObject *func_defaults; /* NULL or a tuple */ + PyObject *func_closure; /* NULL or a tuple of cell objects */ + PyObject *func_doc; /* The __doc__ attribute, can be anything */ + PyObject *func_name; /* The __name__ attribute, a string object */ + PyObject *func_dict; /* The __dict__ attribute, a dict or NULL */ + PyObject *func_weakreflist; /* List of weak references */ + PyObject *func_module; /* The __module__ attribute, can be anything */ + + /* Invariant: + * func_closure contains the bindings for func_code->co_freevars, so + * PyTuple_Size(func_closure) == PyCode_GetNumFree(func_code) + * (func_closure may be NULL if PyCode_GetNumFree(func_code) == 0). + */ +} PyFunctionObject; + +PyAPI_DATA(PyTypeObject) PyFunction_Type; + +#define PyFunction_Check(op) (Py_TYPE(op) == &PyFunction_Type) + +PyAPI_FUNC(PyObject *) PyFunction_New(PyObject *, PyObject *); +PyAPI_FUNC(PyObject *) PyFunction_GetCode(PyObject *); +PyAPI_FUNC(PyObject *) PyFunction_GetGlobals(PyObject *); +PyAPI_FUNC(PyObject *) PyFunction_GetModule(PyObject *); +PyAPI_FUNC(PyObject *) PyFunction_GetDefaults(PyObject *); +PyAPI_FUNC(int) PyFunction_SetDefaults(PyObject *, PyObject *); +PyAPI_FUNC(PyObject *) PyFunction_GetClosure(PyObject *); +PyAPI_FUNC(int) PyFunction_SetClosure(PyObject *, PyObject *); + +/* Macros for direct access to these values. Type checks are *not* + done, so use with care. */ +#define PyFunction_GET_CODE(func) \ + (((PyFunctionObject *)func) -> func_code) +#define PyFunction_GET_GLOBALS(func) \ + (((PyFunctionObject *)func) -> func_globals) +#define PyFunction_GET_MODULE(func) \ + (((PyFunctionObject *)func) -> func_module) +#define PyFunction_GET_DEFAULTS(func) \ + (((PyFunctionObject *)func) -> func_defaults) +#define PyFunction_GET_CLOSURE(func) \ + (((PyFunctionObject *)func) -> func_closure) + +/* The classmethod and staticmethod types lives here, too */ +PyAPI_DATA(PyTypeObject) PyClassMethod_Type; +PyAPI_DATA(PyTypeObject) PyStaticMethod_Type; + +PyAPI_FUNC(PyObject *) PyClassMethod_New(PyObject *); +PyAPI_FUNC(PyObject *) PyStaticMethod_New(PyObject *); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_FUNCOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/genobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/genobject.h new file mode 100644 index 0000000000..ab9680da0f --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/genobject.h @@ -0,0 +1,40 @@ + +/* Generator object interface */ + +#ifndef Py_GENOBJECT_H +#define Py_GENOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +struct _frame; /* Avoid including frameobject.h */ + +typedef struct { + PyObject_HEAD + /* The gi_ prefix is intended to remind of generator-iterator. */ + + /* Note: gi_frame can be NULL if the generator is "finished" */ + struct _frame *gi_frame; + + /* True if generator is being executed. */ + int gi_running; + + /* The code object backing the generator */ + PyObject *gi_code; + + /* List of weak reference. */ + PyObject *gi_weakreflist; +} PyGenObject; + +PyAPI_DATA(PyTypeObject) PyGen_Type; + +#define PyGen_Check(op) PyObject_TypeCheck(op, &PyGen_Type) +#define PyGen_CheckExact(op) (Py_TYPE(op) == &PyGen_Type) + +PyAPI_FUNC(PyObject *) PyGen_New(struct _frame *); +PyAPI_FUNC(int) PyGen_NeedsFinalizing(PyGenObject *); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_GENOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/graminit.h b/AppPkg/Applications/Python/Python-2.7.10/Include/graminit.h new file mode 100644 index 0000000000..b083e9d1f5 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/graminit.h @@ -0,0 +1,87 @@ +/* Generated by Parser/pgen */ + +#define single_input 256 +#define file_input 257 +#define eval_input 258 +#define decorator 259 +#define decorators 260 +#define decorated 261 +#define funcdef 262 +#define parameters 263 +#define varargslist 264 +#define fpdef 265 +#define fplist 266 +#define stmt 267 +#define simple_stmt 268 +#define small_stmt 269 +#define expr_stmt 270 +#define augassign 271 +#define print_stmt 272 +#define del_stmt 273 +#define pass_stmt 274 +#define flow_stmt 275 +#define break_stmt 276 +#define continue_stmt 277 +#define return_stmt 278 +#define yield_stmt 279 +#define raise_stmt 280 +#define import_stmt 281 +#define import_name 282 +#define import_from 283 +#define import_as_name 284 +#define dotted_as_name 285 +#define import_as_names 286 +#define dotted_as_names 287 +#define dotted_name 288 +#define global_stmt 289 +#define exec_stmt 290 +#define assert_stmt 291 +#define compound_stmt 292 +#define if_stmt 293 +#define while_stmt 294 +#define for_stmt 295 +#define try_stmt 296 +#define with_stmt 297 +#define with_item 298 +#define except_clause 299 +#define suite 300 +#define testlist_safe 301 +#define old_test 302 +#define old_lambdef 303 +#define test 304 +#define or_test 305 +#define and_test 306 +#define not_test 307 +#define comparison 308 +#define comp_op 309 +#define expr 310 +#define xor_expr 311 +#define and_expr 312 +#define shift_expr 313 +#define arith_expr 314 +#define term 315 +#define factor 316 +#define power 317 +#define atom 318 +#define listmaker 319 +#define testlist_comp 320 +#define lambdef 321 +#define trailer 322 +#define subscriptlist 323 +#define subscript 324 +#define sliceop 325 +#define exprlist 326 +#define testlist 327 +#define dictorsetmaker 328 +#define classdef 329 +#define arglist 330 +#define argument 331 +#define list_iter 332 +#define list_for 333 +#define list_if 334 +#define comp_iter 335 +#define comp_for 336 +#define comp_if 337 +#define testlist1 338 +#define encoding_decl 339 +#define yield_expr 340 diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/grammar.h b/AppPkg/Applications/Python/Python-2.7.10/Include/grammar.h new file mode 100644 index 0000000000..f82ee9c1dc --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/grammar.h @@ -0,0 +1,93 @@ + +/* Grammar interface */ + +#ifndef Py_GRAMMAR_H +#define Py_GRAMMAR_H +#ifdef __cplusplus +extern "C" { +#endif + +#include "bitset.h" /* Sigh... */ + +/* A label of an arc */ + +typedef struct { + int lb_type; + char *lb_str; +} label; + +#define EMPTY 0 /* Label number 0 is by definition the empty label */ + +/* A list of labels */ + +typedef struct { + int ll_nlabels; + label *ll_label; +} labellist; + +/* An arc from one state to another */ + +typedef struct { + short a_lbl; /* Label of this arc */ + short a_arrow; /* State where this arc goes to */ +} arc; + +/* A state in a DFA */ + +typedef struct { + int s_narcs; + arc *s_arc; /* Array of arcs */ + + /* Optional accelerators */ + int s_lower; /* Lowest label index */ + int s_upper; /* Highest label index */ + int *s_accel; /* Accelerator */ + int s_accept; /* Nonzero for accepting state */ +} state; + +/* A DFA */ + +typedef struct { + int d_type; /* Non-terminal this represents */ + char *d_name; /* For printing */ + int d_initial; /* Initial state */ + int d_nstates; + state *d_state; /* Array of states */ + bitset d_first; +} dfa; + +/* A grammar */ + +typedef struct { + int g_ndfas; + dfa *g_dfa; /* Array of DFAs */ + labellist g_ll; + int g_start; /* Start symbol of the grammar */ + int g_accel; /* Set if accelerators present */ +} grammar; + +/* FUNCTIONS */ + +grammar *newgrammar(int start); +dfa *adddfa(grammar *g, int type, char *name); +int addstate(dfa *d); +void addarc(dfa *d, int from, int to, int lbl); +dfa *PyGrammar_FindDFA(grammar *g, int type); + +int addlabel(labellist *ll, int type, char *str); +int findlabel(labellist *ll, int type, char *str); +char *PyGrammar_LabelRepr(label *lb); +void translatelabels(grammar *g); + +void addfirstsets(grammar *g); + +void PyGrammar_AddAccelerators(grammar *g); +void PyGrammar_RemoveAccelerators(grammar *); + +void printgrammar(grammar *g, FILE *fp); +void printnonterminals(grammar *g, FILE *fp); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_GRAMMAR_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/import.h b/AppPkg/Applications/Python/Python-2.7.10/Include/import.h new file mode 100644 index 0000000000..a731f24905 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/import.h @@ -0,0 +1,71 @@ + +/* Module definition and import interface */ + +#ifndef Py_IMPORT_H +#define Py_IMPORT_H +#ifdef __cplusplus +extern "C" { +#endif + +PyAPI_FUNC(long) PyImport_GetMagicNumber(void); +PyAPI_FUNC(PyObject *) PyImport_ExecCodeModule(char *name, PyObject *co); +PyAPI_FUNC(PyObject *) PyImport_ExecCodeModuleEx( + char *name, PyObject *co, char *pathname); +PyAPI_FUNC(PyObject *) PyImport_GetModuleDict(void); +PyAPI_FUNC(PyObject *) PyImport_AddModule(const char *name); +PyAPI_FUNC(PyObject *) PyImport_ImportModule(const char *name); +PyAPI_FUNC(PyObject *) PyImport_ImportModuleNoBlock(const char *); +PyAPI_FUNC(PyObject *) PyImport_ImportModuleLevel(char *name, + PyObject *globals, PyObject *locals, PyObject *fromlist, int level); + +#define PyImport_ImportModuleEx(n, g, l, f) \ + PyImport_ImportModuleLevel(n, g, l, f, -1) + +PyAPI_FUNC(PyObject *) PyImport_GetImporter(PyObject *path); +PyAPI_FUNC(PyObject *) PyImport_Import(PyObject *name); +PyAPI_FUNC(PyObject *) PyImport_ReloadModule(PyObject *m); +PyAPI_FUNC(void) PyImport_Cleanup(void); +PyAPI_FUNC(int) PyImport_ImportFrozenModule(char *); + +#ifdef WITH_THREAD +PyAPI_FUNC(void) _PyImport_AcquireLock(void); +PyAPI_FUNC(int) _PyImport_ReleaseLock(void); +#else +#define _PyImport_AcquireLock() +#define _PyImport_ReleaseLock() 1 +#endif + +PyAPI_FUNC(struct filedescr *) _PyImport_FindModule( + const char *, PyObject *, char *, size_t, FILE **, PyObject **); +PyAPI_FUNC(int) _PyImport_IsScript(struct filedescr *); +PyAPI_FUNC(void) _PyImport_ReInitLock(void); + +PyAPI_FUNC(PyObject *) _PyImport_FindExtension(char *, char *); +PyAPI_FUNC(PyObject *) _PyImport_FixupExtension(char *, char *); + +struct _inittab { + char *name; + void (*initfunc)(void); +}; + +PyAPI_DATA(PyTypeObject) PyNullImporter_Type; +PyAPI_DATA(struct _inittab *) PyImport_Inittab; + +PyAPI_FUNC(int) PyImport_AppendInittab(const char *name, void (*initfunc)(void)); +PyAPI_FUNC(int) PyImport_ExtendInittab(struct _inittab *newtab); + +struct _frozen { + char *name; + unsigned char *code; + int size; +}; + +/* Embedding apps may change this pointer to point to their favorite + collection of frozen modules: */ + +PyAPI_DATA(struct _frozen *) PyImport_FrozenModules; + +#ifdef __cplusplus +} +#endif +#endif /* !Py_IMPORT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/intobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/intobject.h new file mode 100644 index 0000000000..b286ec6dbb --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/intobject.h @@ -0,0 +1,81 @@ + +/* Integer object interface */ + +/* +PyIntObject represents a (long) integer. This is an immutable object; +an integer cannot change its value after creation. + +There are functions to create new integer objects, to test an object +for integer-ness, and to get the integer value. The latter functions +returns -1 and sets errno to EBADF if the object is not an PyIntObject. +None of the functions should be applied to nil objects. + +The type PyIntObject is (unfortunately) exposed here so we can declare +_Py_TrueStruct and _Py_ZeroStruct in boolobject.h; don't use this. +*/ + +#ifndef Py_INTOBJECT_H +#define Py_INTOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +typedef struct { + PyObject_HEAD + long ob_ival; +} PyIntObject; + +PyAPI_DATA(PyTypeObject) PyInt_Type; + +#define PyInt_Check(op) \ + PyType_FastSubclass((op)->ob_type, Py_TPFLAGS_INT_SUBCLASS) +#define PyInt_CheckExact(op) ((op)->ob_type == &PyInt_Type) + +PyAPI_FUNC(PyObject *) PyInt_FromString(char*, char**, int); +#ifdef Py_USING_UNICODE +PyAPI_FUNC(PyObject *) PyInt_FromUnicode(Py_UNICODE*, Py_ssize_t, int); +#endif +PyAPI_FUNC(PyObject *) PyInt_FromLong(long); +PyAPI_FUNC(PyObject *) PyInt_FromSize_t(size_t); +PyAPI_FUNC(PyObject *) PyInt_FromSsize_t(Py_ssize_t); +PyAPI_FUNC(long) PyInt_AsLong(PyObject *); +PyAPI_FUNC(Py_ssize_t) PyInt_AsSsize_t(PyObject *); +PyAPI_FUNC(int) _PyInt_AsInt(PyObject *); +PyAPI_FUNC(unsigned long) PyInt_AsUnsignedLongMask(PyObject *); +#ifdef HAVE_LONG_LONG +PyAPI_FUNC(unsigned PY_LONG_LONG) PyInt_AsUnsignedLongLongMask(PyObject *); +#endif + +PyAPI_FUNC(long) PyInt_GetMax(void); + +/* Macro, trading safety for speed */ +#define PyInt_AS_LONG(op) (((PyIntObject *)(op))->ob_ival) + +/* These aren't really part of the Int object, but they're handy; the protos + * are necessary for systems that need the magic of PyAPI_FUNC and that want + * to have stropmodule as a dynamically loaded module instead of building it + * into the main Python shared library/DLL. Guido thinks I'm weird for + * building it this way. :-) [cjh] + */ +PyAPI_FUNC(unsigned long) PyOS_strtoul(char *, char **, int); +PyAPI_FUNC(long) PyOS_strtol(char *, char **, int); + +/* free list api */ +PyAPI_FUNC(int) PyInt_ClearFreeList(void); + +/* Convert an integer to the given base. Returns a string. + If base is 2, 8 or 16, add the proper prefix '0b', '0o' or '0x'. + If newstyle is zero, then use the pre-2.6 behavior of octal having + a leading "0" */ +PyAPI_FUNC(PyObject*) _PyInt_Format(PyIntObject* v, int base, int newstyle); + +/* Format the object based on the format_spec, as defined in PEP 3101 + (Advanced String Formatting). */ +PyAPI_FUNC(PyObject *) _PyInt_FormatAdvanced(PyObject *obj, + char *format_spec, + Py_ssize_t format_spec_len); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_INTOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/intrcheck.h b/AppPkg/Applications/Python/Python-2.7.10/Include/intrcheck.h new file mode 100644 index 0000000000..11d759e42a --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/intrcheck.h @@ -0,0 +1,15 @@ + +#ifndef Py_INTRCHECK_H +#define Py_INTRCHECK_H +#ifdef __cplusplus +extern "C" { +#endif + +PyAPI_FUNC(int) PyOS_InterruptOccurred(void); +PyAPI_FUNC(void) PyOS_InitInterrupts(void); +PyAPI_FUNC(void) PyOS_AfterFork(void); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_INTRCHECK_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/iterobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/iterobject.h new file mode 100644 index 0000000000..ac49cb6fbf --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/iterobject.h @@ -0,0 +1,23 @@ +#ifndef Py_ITEROBJECT_H +#define Py_ITEROBJECT_H +/* Iterators (the basic kind, over a sequence) */ +#ifdef __cplusplus +extern "C" { +#endif + +PyAPI_DATA(PyTypeObject) PySeqIter_Type; + +#define PySeqIter_Check(op) (Py_TYPE(op) == &PySeqIter_Type) + +PyAPI_FUNC(PyObject *) PySeqIter_New(PyObject *); + +PyAPI_DATA(PyTypeObject) PyCallIter_Type; + +#define PyCallIter_Check(op) (Py_TYPE(op) == &PyCallIter_Type) + +PyAPI_FUNC(PyObject *) PyCallIter_New(PyObject *, PyObject *); +#ifdef __cplusplus +} +#endif +#endif /* !Py_ITEROBJECT_H */ + diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/listobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/listobject.h new file mode 100644 index 0000000000..1b55d62ce8 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/listobject.h @@ -0,0 +1,68 @@ + +/* List object interface */ + +/* +Another generally useful object type is an list of object pointers. +This is a mutable type: the list items can be changed, and items can be +added or removed. Out-of-range indices or non-list objects are ignored. + +*** WARNING *** PyList_SetItem does not increment the new item's reference +count, but does decrement the reference count of the item it replaces, +if not nil. It does *decrement* the reference count if it is *not* +inserted in the list. Similarly, PyList_GetItem does not increment the +returned item's reference count. +*/ + +#ifndef Py_LISTOBJECT_H +#define Py_LISTOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +typedef struct { + PyObject_VAR_HEAD + /* Vector of pointers to list elements. list[0] is ob_item[0], etc. */ + PyObject **ob_item; + + /* ob_item contains space for 'allocated' elements. The number + * currently in use is ob_size. + * Invariants: + * 0 <= ob_size <= allocated + * len(list) == ob_size + * ob_item == NULL implies ob_size == allocated == 0 + * list.sort() temporarily sets allocated to -1 to detect mutations. + * + * Items must normally not be NULL, except during construction when + * the list is not yet visible outside the function that builds it. + */ + Py_ssize_t allocated; +} PyListObject; + +PyAPI_DATA(PyTypeObject) PyList_Type; + +#define PyList_Check(op) \ + PyType_FastSubclass(Py_TYPE(op), Py_TPFLAGS_LIST_SUBCLASS) +#define PyList_CheckExact(op) (Py_TYPE(op) == &PyList_Type) + +PyAPI_FUNC(PyObject *) PyList_New(Py_ssize_t size); +PyAPI_FUNC(Py_ssize_t) PyList_Size(PyObject *); +PyAPI_FUNC(PyObject *) PyList_GetItem(PyObject *, Py_ssize_t); +PyAPI_FUNC(int) PyList_SetItem(PyObject *, Py_ssize_t, PyObject *); +PyAPI_FUNC(int) PyList_Insert(PyObject *, Py_ssize_t, PyObject *); +PyAPI_FUNC(int) PyList_Append(PyObject *, PyObject *); +PyAPI_FUNC(PyObject *) PyList_GetSlice(PyObject *, Py_ssize_t, Py_ssize_t); +PyAPI_FUNC(int) PyList_SetSlice(PyObject *, Py_ssize_t, Py_ssize_t, PyObject *); +PyAPI_FUNC(int) PyList_Sort(PyObject *); +PyAPI_FUNC(int) PyList_Reverse(PyObject *); +PyAPI_FUNC(PyObject *) PyList_AsTuple(PyObject *); +PyAPI_FUNC(PyObject *) _PyList_Extend(PyListObject *, PyObject *); + +/* Macro, trading safety for speed */ +#define PyList_GET_ITEM(op, i) (((PyListObject *)(op))->ob_item[i]) +#define PyList_SET_ITEM(op, i, v) (((PyListObject *)(op))->ob_item[i] = (v)) +#define PyList_GET_SIZE(op) Py_SIZE(op) + +#ifdef __cplusplus +} +#endif +#endif /* !Py_LISTOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/longintrepr.h b/AppPkg/Applications/Python/Python-2.7.10/Include/longintrepr.h new file mode 100644 index 0000000000..3d1cd25b89 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/longintrepr.h @@ -0,0 +1,103 @@ +#ifndef Py_LONGINTREPR_H +#define Py_LONGINTREPR_H +#ifdef __cplusplus +extern "C" { +#endif + + +/* This is published for the benefit of "friend" marshal.c only. */ + +/* Parameters of the long integer representation. There are two different + sets of parameters: one set for 30-bit digits, stored in an unsigned 32-bit + integer type, and one set for 15-bit digits with each digit stored in an + unsigned short. The value of PYLONG_BITS_IN_DIGIT, defined either at + configure time or in pyport.h, is used to decide which digit size to use. + + Type 'digit' should be able to hold 2*PyLong_BASE-1, and type 'twodigits' + should be an unsigned integer type able to hold all integers up to + PyLong_BASE*PyLong_BASE-1. x_sub assumes that 'digit' is an unsigned type, + and that overflow is handled by taking the result modulo 2**N for some N > + PyLong_SHIFT. The majority of the code doesn't care about the precise + value of PyLong_SHIFT, but there are some notable exceptions: + + - long_pow() requires that PyLong_SHIFT be divisible by 5 + + - PyLong_{As,From}ByteArray require that PyLong_SHIFT be at least 8 + + - long_hash() requires that PyLong_SHIFT is *strictly* less than the number + of bits in an unsigned long, as do the PyLong <-> long (or unsigned long) + conversion functions + + - the long <-> size_t/Py_ssize_t conversion functions expect that + PyLong_SHIFT is strictly less than the number of bits in a size_t + + - the marshal code currently expects that PyLong_SHIFT is a multiple of 15 + + The values 15 and 30 should fit all of the above requirements, on any + platform. +*/ + +#if PYLONG_BITS_IN_DIGIT == 30 +#if !(defined HAVE_UINT64_T && defined HAVE_UINT32_T && \ + defined HAVE_INT64_T && defined HAVE_INT32_T) +#error "30-bit long digits requested, but the necessary types are not available on this platform" +#endif +typedef PY_UINT32_T digit; +typedef PY_INT32_T sdigit; /* signed variant of digit */ +typedef PY_UINT64_T twodigits; +typedef PY_INT64_T stwodigits; /* signed variant of twodigits */ +#define PyLong_SHIFT 30 +#define _PyLong_DECIMAL_SHIFT 9 /* max(e such that 10**e fits in a digit) */ +#define _PyLong_DECIMAL_BASE ((digit)1000000000) /* 10 ** DECIMAL_SHIFT */ +#elif PYLONG_BITS_IN_DIGIT == 15 +typedef unsigned short digit; +typedef short sdigit; /* signed variant of digit */ +typedef unsigned long twodigits; +typedef long stwodigits; /* signed variant of twodigits */ +#define PyLong_SHIFT 15 +#define _PyLong_DECIMAL_SHIFT 4 /* max(e such that 10**e fits in a digit) */ +#define _PyLong_DECIMAL_BASE ((digit)10000) /* 10 ** DECIMAL_SHIFT */ +#else +#error "PYLONG_BITS_IN_DIGIT should be 15 or 30" +#endif +#define PyLong_BASE ((digit)1 << PyLong_SHIFT) +#define PyLong_MASK ((digit)(PyLong_BASE - 1)) + +/* b/w compatibility with Python 2.5 */ +#define SHIFT PyLong_SHIFT +#define BASE PyLong_BASE +#define MASK PyLong_MASK + +#if PyLong_SHIFT % 5 != 0 +#error "longobject.c requires that PyLong_SHIFT be divisible by 5" +#endif + +/* Long integer representation. + The absolute value of a number is equal to + SUM(for i=0 through abs(ob_size)-1) ob_digit[i] * 2**(SHIFT*i) + Negative numbers are represented with ob_size < 0; + zero is represented by ob_size == 0. + In a normalized number, ob_digit[abs(ob_size)-1] (the most significant + digit) is never zero. Also, in all cases, for all valid i, + 0 <= ob_digit[i] <= MASK. + The allocation function takes care of allocating extra memory + so that ob_digit[0] ... ob_digit[abs(ob_size)-1] are actually available. + + CAUTION: Generic code manipulating subtypes of PyVarObject has to + aware that longs abuse ob_size's sign bit. +*/ + +struct _longobject { + PyObject_VAR_HEAD + digit ob_digit[1]; +}; + +PyAPI_FUNC(PyLongObject *) _PyLong_New(Py_ssize_t); + +/* Return a copy of src. */ +PyAPI_FUNC(PyObject *) _PyLong_Copy(PyLongObject *src); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_LONGINTREPR_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/longobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/longobject.h new file mode 100644 index 0000000000..71453b4d37 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/longobject.h @@ -0,0 +1,135 @@ +#ifndef Py_LONGOBJECT_H +#define Py_LONGOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + + +/* Long (arbitrary precision) integer object interface */ + +typedef struct _longobject PyLongObject; /* Revealed in longintrepr.h */ + +PyAPI_DATA(PyTypeObject) PyLong_Type; + +#define PyLong_Check(op) \ + PyType_FastSubclass(Py_TYPE(op), Py_TPFLAGS_LONG_SUBCLASS) +#define PyLong_CheckExact(op) (Py_TYPE(op) == &PyLong_Type) + +PyAPI_FUNC(PyObject *) PyLong_FromLong(long); +PyAPI_FUNC(PyObject *) PyLong_FromUnsignedLong(unsigned long); +PyAPI_FUNC(PyObject *) PyLong_FromDouble(double); +PyAPI_FUNC(PyObject *) PyLong_FromSize_t(size_t); +PyAPI_FUNC(PyObject *) PyLong_FromSsize_t(Py_ssize_t); +PyAPI_FUNC(long) PyLong_AsLong(PyObject *); +PyAPI_FUNC(long) PyLong_AsLongAndOverflow(PyObject *, int *); +PyAPI_FUNC(unsigned long) PyLong_AsUnsignedLong(PyObject *); +PyAPI_FUNC(unsigned long) PyLong_AsUnsignedLongMask(PyObject *); +PyAPI_FUNC(Py_ssize_t) PyLong_AsSsize_t(PyObject *); +PyAPI_FUNC(int) _PyLong_AsInt(PyObject *); +PyAPI_FUNC(PyObject *) PyLong_GetInfo(void); + +/* For use by intobject.c only */ +#define _PyLong_AsSsize_t PyLong_AsSsize_t +#define _PyLong_FromSize_t PyLong_FromSize_t +#define _PyLong_FromSsize_t PyLong_FromSsize_t +PyAPI_DATA(int) _PyLong_DigitValue[256]; + +/* _PyLong_Frexp returns a double x and an exponent e such that the + true value is approximately equal to x * 2**e. e is >= 0. x is + 0.0 if and only if the input is 0 (in which case, e and x are both + zeroes); otherwise, 0.5 <= abs(x) < 1.0. On overflow, which is + possible if the number of bits doesn't fit into a Py_ssize_t, sets + OverflowError and returns -1.0 for x, 0 for e. */ +PyAPI_FUNC(double) _PyLong_Frexp(PyLongObject *a, Py_ssize_t *e); + +PyAPI_FUNC(double) PyLong_AsDouble(PyObject *); +PyAPI_FUNC(PyObject *) PyLong_FromVoidPtr(void *); +PyAPI_FUNC(void *) PyLong_AsVoidPtr(PyObject *); + +#ifdef HAVE_LONG_LONG +PyAPI_FUNC(PyObject *) PyLong_FromLongLong(PY_LONG_LONG); +PyAPI_FUNC(PyObject *) PyLong_FromUnsignedLongLong(unsigned PY_LONG_LONG); +PyAPI_FUNC(PY_LONG_LONG) PyLong_AsLongLong(PyObject *); +PyAPI_FUNC(unsigned PY_LONG_LONG) PyLong_AsUnsignedLongLong(PyObject *); +PyAPI_FUNC(unsigned PY_LONG_LONG) PyLong_AsUnsignedLongLongMask(PyObject *); +PyAPI_FUNC(PY_LONG_LONG) PyLong_AsLongLongAndOverflow(PyObject *, int *); +#endif /* HAVE_LONG_LONG */ + +PyAPI_FUNC(PyObject *) PyLong_FromString(char *, char **, int); +#ifdef Py_USING_UNICODE +PyAPI_FUNC(PyObject *) PyLong_FromUnicode(Py_UNICODE*, Py_ssize_t, int); +#endif + +/* _PyLong_Sign. Return 0 if v is 0, -1 if v < 0, +1 if v > 0. + v must not be NULL, and must be a normalized long. + There are no error cases. +*/ +PyAPI_FUNC(int) _PyLong_Sign(PyObject *v); + + +/* _PyLong_NumBits. Return the number of bits needed to represent the + absolute value of a long. For example, this returns 1 for 1 and -1, 2 + for 2 and -2, and 2 for 3 and -3. It returns 0 for 0. + v must not be NULL, and must be a normalized long. + (size_t)-1 is returned and OverflowError set if the true result doesn't + fit in a size_t. +*/ +PyAPI_FUNC(size_t) _PyLong_NumBits(PyObject *v); + +/* _PyLong_FromByteArray: View the n unsigned bytes as a binary integer in + base 256, and return a Python long with the same numeric value. + If n is 0, the integer is 0. Else: + If little_endian is 1/true, bytes[n-1] is the MSB and bytes[0] the LSB; + else (little_endian is 0/false) bytes[0] is the MSB and bytes[n-1] the + LSB. + If is_signed is 0/false, view the bytes as a non-negative integer. + If is_signed is 1/true, view the bytes as a 2's-complement integer, + non-negative if bit 0x80 of the MSB is clear, negative if set. + Error returns: + + Return NULL with the appropriate exception set if there's not + enough memory to create the Python long. +*/ +PyAPI_FUNC(PyObject *) _PyLong_FromByteArray( + const unsigned char* bytes, size_t n, + int little_endian, int is_signed); + +/* _PyLong_AsByteArray: Convert the least-significant 8*n bits of long + v to a base-256 integer, stored in array bytes. Normally return 0, + return -1 on error. + If little_endian is 1/true, store the MSB at bytes[n-1] and the LSB at + bytes[0]; else (little_endian is 0/false) store the MSB at bytes[0] and + the LSB at bytes[n-1]. + If is_signed is 0/false, it's an error if v < 0; else (v >= 0) n bytes + are filled and there's nothing special about bit 0x80 of the MSB. + If is_signed is 1/true, bytes is filled with the 2's-complement + representation of v's value. Bit 0x80 of the MSB is the sign bit. + Error returns (-1): + + is_signed is 0 and v < 0. TypeError is set in this case, and bytes + isn't altered. + + n isn't big enough to hold the full mathematical value of v. For + example, if is_signed is 0 and there are more digits in the v than + fit in n; or if is_signed is 1, v < 0, and n is just 1 bit shy of + being large enough to hold a sign bit. OverflowError is set in this + case, but bytes holds the least-signficant n bytes of the true value. +*/ +PyAPI_FUNC(int) _PyLong_AsByteArray(PyLongObject* v, + unsigned char* bytes, size_t n, + int little_endian, int is_signed); + +/* _PyLong_Format: Convert the long to a string object with given base, + appending a base prefix of 0[box] if base is 2, 8 or 16. + Add a trailing "L" if addL is non-zero. + If newstyle is zero, then use the pre-2.6 behavior of octal having + a leading "0", instead of the prefix "0o" */ +PyAPI_FUNC(PyObject *) _PyLong_Format(PyObject *aa, int base, int addL, int newstyle); + +/* Format the object based on the format_spec, as defined in PEP 3101 + (Advanced String Formatting). */ +PyAPI_FUNC(PyObject *) _PyLong_FormatAdvanced(PyObject *obj, + char *format_spec, + Py_ssize_t format_spec_len); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_LONGOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/marshal.h b/AppPkg/Applications/Python/Python-2.7.10/Include/marshal.h new file mode 100644 index 0000000000..43ac5385a7 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/marshal.h @@ -0,0 +1,25 @@ + +/* Interface for marshal.c */ + +#ifndef Py_MARSHAL_H +#define Py_MARSHAL_H +#ifdef __cplusplus +extern "C" { +#endif + +#define Py_MARSHAL_VERSION 2 + +PyAPI_FUNC(void) PyMarshal_WriteLongToFile(long, FILE *, int); +PyAPI_FUNC(void) PyMarshal_WriteObjectToFile(PyObject *, FILE *, int); +PyAPI_FUNC(PyObject *) PyMarshal_WriteObjectToString(PyObject *, int); + +PyAPI_FUNC(long) PyMarshal_ReadLongFromFile(FILE *); +PyAPI_FUNC(int) PyMarshal_ReadShortFromFile(FILE *); +PyAPI_FUNC(PyObject *) PyMarshal_ReadObjectFromFile(FILE *); +PyAPI_FUNC(PyObject *) PyMarshal_ReadLastObjectFromFile(FILE *); +PyAPI_FUNC(PyObject *) PyMarshal_ReadObjectFromString(char *, Py_ssize_t); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_MARSHAL_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/memoryobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/memoryobject.h new file mode 100644 index 0000000000..ca5064e985 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/memoryobject.h @@ -0,0 +1,74 @@ +/* Memory view object. In Python this is available as "memoryview". */ + +#ifndef Py_MEMORYOBJECT_H +#define Py_MEMORYOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +PyAPI_DATA(PyTypeObject) PyMemoryView_Type; + +#define PyMemoryView_Check(op) (Py_TYPE(op) == &PyMemoryView_Type) + +/* Get a pointer to the underlying Py_buffer of a memoryview object. */ +#define PyMemoryView_GET_BUFFER(op) (&((PyMemoryViewObject *)(op))->view) +/* Get a pointer to the PyObject from which originates a memoryview object. */ +#define PyMemoryView_GET_BASE(op) (((PyMemoryViewObject *)(op))->view.obj) + + +PyAPI_FUNC(PyObject *) PyMemoryView_GetContiguous(PyObject *base, + int buffertype, + char fort); + + /* Return a contiguous chunk of memory representing the buffer + from an object in a memory view object. If a copy is made then the + base object for the memory view will be a *new* bytes object. + + Otherwise, the base-object will be the object itself and no + data-copying will be done. + + The buffertype argument can be PyBUF_READ, PyBUF_WRITE, + PyBUF_SHADOW to determine whether the returned buffer + should be READONLY, WRITABLE, or set to update the + original buffer if a copy must be made. If buffertype is + PyBUF_WRITE and the buffer is not contiguous an error will + be raised. In this circumstance, the user can use + PyBUF_SHADOW to ensure that a a writable temporary + contiguous buffer is returned. The contents of this + contiguous buffer will be copied back into the original + object after the memoryview object is deleted as long as + the original object is writable and allows setting an + exclusive write lock. If this is not allowed by the + original object, then a BufferError is raised. + + If the object is multi-dimensional and if fortran is 'F', + the first dimension of the underlying array will vary the + fastest in the buffer. If fortran is 'C', then the last + dimension will vary the fastest (C-style contiguous). If + fortran is 'A', then it does not matter and you will get + whatever the object decides is more efficient. + + A new reference is returned that must be DECREF'd when finished. + */ + +PyAPI_FUNC(PyObject *) PyMemoryView_FromObject(PyObject *base); + +PyAPI_FUNC(PyObject *) PyMemoryView_FromBuffer(Py_buffer *info); + /* create new if bufptr is NULL + will be a new bytesobject in base */ + + +/* The struct is declared here so that macros can work, but it shouldn't + be considered public. Don't access those fields directly, use the macros + and functions instead! */ +typedef struct { + PyObject_HEAD + PyObject *base; + Py_buffer view; +} PyMemoryViewObject; + + +#ifdef __cplusplus +} +#endif +#endif /* !Py_MEMORYOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/metagrammar.h b/AppPkg/Applications/Python/Python-2.7.10/Include/metagrammar.h new file mode 100644 index 0000000000..1fb471a0f9 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/metagrammar.h @@ -0,0 +1,18 @@ +#ifndef Py_METAGRAMMAR_H +#define Py_METAGRAMMAR_H +#ifdef __cplusplus +extern "C" { +#endif + + +#define MSTART 256 +#define RULE 257 +#define RHS 258 +#define ALT 259 +#define ITEM 260 +#define ATOM 261 + +#ifdef __cplusplus +} +#endif +#endif /* !Py_METAGRAMMAR_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/methodobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/methodobject.h new file mode 100644 index 0000000000..8b2828853f --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/methodobject.h @@ -0,0 +1,93 @@ + +/* Method object interface */ + +#ifndef Py_METHODOBJECT_H +#define Py_METHODOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +/* This is about the type 'builtin_function_or_method', + not Python methods in user-defined classes. See classobject.h + for the latter. */ + +PyAPI_DATA(PyTypeObject) PyCFunction_Type; + +#define PyCFunction_Check(op) (Py_TYPE(op) == &PyCFunction_Type) + +typedef PyObject *(*PyCFunction)(PyObject *, PyObject *); +typedef PyObject *(*PyCFunctionWithKeywords)(PyObject *, PyObject *, + PyObject *); +typedef PyObject *(*PyNoArgsFunction)(PyObject *); + +PyAPI_FUNC(PyCFunction) PyCFunction_GetFunction(PyObject *); +PyAPI_FUNC(PyObject *) PyCFunction_GetSelf(PyObject *); +PyAPI_FUNC(int) PyCFunction_GetFlags(PyObject *); + +/* Macros for direct access to these values. Type checks are *not* + done, so use with care. */ +#define PyCFunction_GET_FUNCTION(func) \ + (((PyCFunctionObject *)func) -> m_ml -> ml_meth) +#define PyCFunction_GET_SELF(func) \ + (((PyCFunctionObject *)func) -> m_self) +#define PyCFunction_GET_FLAGS(func) \ + (((PyCFunctionObject *)func) -> m_ml -> ml_flags) +PyAPI_FUNC(PyObject *) PyCFunction_Call(PyObject *, PyObject *, PyObject *); + +struct PyMethodDef { + const char *ml_name; /* The name of the built-in function/method */ + PyCFunction ml_meth; /* The C function that implements it */ + int ml_flags; /* Combination of METH_xxx flags, which mostly + describe the args expected by the C func */ + const char *ml_doc; /* The __doc__ attribute, or NULL */ +}; +typedef struct PyMethodDef PyMethodDef; + +PyAPI_FUNC(PyObject *) Py_FindMethod(PyMethodDef[], PyObject *, const char *); + +#define PyCFunction_New(ML, SELF) PyCFunction_NewEx((ML), (SELF), NULL) +PyAPI_FUNC(PyObject *) PyCFunction_NewEx(PyMethodDef *, PyObject *, + PyObject *); + +/* Flag passed to newmethodobject */ +#define METH_OLDARGS 0x0000 +#define METH_VARARGS 0x0001 +#define METH_KEYWORDS 0x0002 +/* METH_NOARGS and METH_O must not be combined with the flags above. */ +#define METH_NOARGS 0x0004 +#define METH_O 0x0008 + +/* METH_CLASS and METH_STATIC are a little different; these control + the construction of methods for a class. These cannot be used for + functions in modules. */ +#define METH_CLASS 0x0010 +#define METH_STATIC 0x0020 + +/* METH_COEXIST allows a method to be entered eventhough a slot has + already filled the entry. When defined, the flag allows a separate + method, "__contains__" for example, to coexist with a defined + slot like sq_contains. */ + +#define METH_COEXIST 0x0040 + +typedef struct PyMethodChain { + PyMethodDef *methods; /* Methods of this type */ + struct PyMethodChain *link; /* NULL or base type */ +} PyMethodChain; + +PyAPI_FUNC(PyObject *) Py_FindMethodInChain(PyMethodChain *, PyObject *, + const char *); + +typedef struct { + PyObject_HEAD + PyMethodDef *m_ml; /* Description of the C function to call */ + PyObject *m_self; /* Passed as 'self' arg to the C func, can be NULL */ + PyObject *m_module; /* The __module__ attribute, can be anything */ +} PyCFunctionObject; + +PyAPI_FUNC(int) PyCFunction_ClearFreeList(void); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_METHODOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/modsupport.h b/AppPkg/Applications/Python/Python-2.7.10/Include/modsupport.h new file mode 100644 index 0000000000..8a8cf8d710 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/modsupport.h @@ -0,0 +1,134 @@ + +#ifndef Py_MODSUPPORT_H +#define Py_MODSUPPORT_H +#ifdef __cplusplus +extern "C" { +#endif + +/* Module support interface */ + +#include + +/* If PY_SSIZE_T_CLEAN is defined, each functions treats #-specifier + to mean Py_ssize_t */ +#ifdef PY_SSIZE_T_CLEAN +#define PyArg_Parse _PyArg_Parse_SizeT +#define PyArg_ParseTuple _PyArg_ParseTuple_SizeT +#define PyArg_ParseTupleAndKeywords _PyArg_ParseTupleAndKeywords_SizeT +#define PyArg_VaParse _PyArg_VaParse_SizeT +#define PyArg_VaParseTupleAndKeywords _PyArg_VaParseTupleAndKeywords_SizeT +#define Py_BuildValue _Py_BuildValue_SizeT +#define Py_VaBuildValue _Py_VaBuildValue_SizeT +#else +PyAPI_FUNC(PyObject *) _Py_VaBuildValue_SizeT(const char *, va_list); +#endif + +PyAPI_FUNC(int) PyArg_Parse(PyObject *, const char *, ...); +PyAPI_FUNC(int) PyArg_ParseTuple(PyObject *, const char *, ...) Py_FORMAT_PARSETUPLE(PyArg_ParseTuple, 2, 3); +PyAPI_FUNC(int) PyArg_ParseTupleAndKeywords(PyObject *, PyObject *, + const char *, char **, ...); +PyAPI_FUNC(int) PyArg_UnpackTuple(PyObject *, const char *, Py_ssize_t, Py_ssize_t, ...); +PyAPI_FUNC(PyObject *) Py_BuildValue(const char *, ...); +PyAPI_FUNC(PyObject *) _Py_BuildValue_SizeT(const char *, ...); +PyAPI_FUNC(int) _PyArg_NoKeywords(const char *funcname, PyObject *kw); + +PyAPI_FUNC(int) PyArg_VaParse(PyObject *, const char *, va_list); +PyAPI_FUNC(int) PyArg_VaParseTupleAndKeywords(PyObject *, PyObject *, + const char *, char **, va_list); +PyAPI_FUNC(PyObject *) Py_VaBuildValue(const char *, va_list); + +PyAPI_FUNC(int) PyModule_AddObject(PyObject *, const char *, PyObject *); +PyAPI_FUNC(int) PyModule_AddIntConstant(PyObject *, const char *, long); +PyAPI_FUNC(int) PyModule_AddStringConstant(PyObject *, const char *, const char *); +#define PyModule_AddIntMacro(m, c) PyModule_AddIntConstant(m, #c, c) +#define PyModule_AddStringMacro(m, c) PyModule_AddStringConstant(m, #c, c) + +#define PYTHON_API_VERSION 1013 +#define PYTHON_API_STRING "1013" +/* The API version is maintained (independently from the Python version) + so we can detect mismatches between the interpreter and dynamically + loaded modules. These are diagnosed by an error message but + the module is still loaded (because the mismatch can only be tested + after loading the module). The error message is intended to + explain the core dump a few seconds later. + + The symbol PYTHON_API_STRING defines the same value as a string + literal. *** PLEASE MAKE SURE THE DEFINITIONS MATCH. *** + + Please add a line or two to the top of this log for each API + version change: + + 22-Feb-2006 MvL 1013 PEP 353 - long indices for sequence lengths + + 19-Aug-2002 GvR 1012 Changes to string object struct for + interning changes, saving 3 bytes. + + 17-Jul-2001 GvR 1011 Descr-branch, just to be on the safe side + + 25-Jan-2001 FLD 1010 Parameters added to PyCode_New() and + PyFrame_New(); Python 2.1a2 + + 14-Mar-2000 GvR 1009 Unicode API added + + 3-Jan-1999 GvR 1007 Decided to change back! (Don't reuse 1008!) + + 3-Dec-1998 GvR 1008 Python 1.5.2b1 + + 18-Jan-1997 GvR 1007 string interning and other speedups + + 11-Oct-1996 GvR renamed Py_Ellipses to Py_Ellipsis :-( + + 30-Jul-1996 GvR Slice and ellipses syntax added + + 23-Jul-1996 GvR For 1.4 -- better safe than sorry this time :-) + + 7-Nov-1995 GvR Keyword arguments (should've been done at 1.3 :-( ) + + 10-Jan-1995 GvR Renamed globals to new naming scheme + + 9-Jan-1995 GvR Initial version (incompatible with older API) +*/ + +#ifdef MS_WINDOWS +/* Special defines for Windows versions used to live here. Things + have changed, and the "Version" is now in a global string variable. + Reason for this is that this for easier branding of a "custom DLL" + without actually needing a recompile. */ +#endif /* MS_WINDOWS */ + +#if SIZEOF_SIZE_T != SIZEOF_INT +/* On a 64-bit system, rename the Py_InitModule4 so that 2.4 + modules cannot get loaded into a 2.5 interpreter */ +#define Py_InitModule4 Py_InitModule4_64 +#endif + +#ifdef Py_TRACE_REFS + /* When we are tracing reference counts, rename Py_InitModule4 so + modules compiled with incompatible settings will generate a + link-time error. */ + #if SIZEOF_SIZE_T != SIZEOF_INT + #undef Py_InitModule4 + #define Py_InitModule4 Py_InitModule4TraceRefs_64 + #else + #define Py_InitModule4 Py_InitModule4TraceRefs + #endif +#endif + +PyAPI_FUNC(PyObject *) Py_InitModule4(const char *name, PyMethodDef *methods, + const char *doc, PyObject *self, + int apiver); + +#define Py_InitModule(name, methods) \ + Py_InitModule4(name, methods, (char *)NULL, (PyObject *)NULL, \ + PYTHON_API_VERSION) + +#define Py_InitModule3(name, methods, doc) \ + Py_InitModule4(name, methods, doc, (PyObject *)NULL, \ + PYTHON_API_VERSION) + +PyAPI_DATA(char *) _Py_PackageContext; + +#ifdef __cplusplus +} +#endif +#endif /* !Py_MODSUPPORT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/moduleobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/moduleobject.h new file mode 100644 index 0000000000..ff16ad288a --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/moduleobject.h @@ -0,0 +1,24 @@ + +/* Module object interface */ + +#ifndef Py_MODULEOBJECT_H +#define Py_MODULEOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +PyAPI_DATA(PyTypeObject) PyModule_Type; + +#define PyModule_Check(op) PyObject_TypeCheck(op, &PyModule_Type) +#define PyModule_CheckExact(op) (Py_TYPE(op) == &PyModule_Type) + +PyAPI_FUNC(PyObject *) PyModule_New(const char *); +PyAPI_FUNC(PyObject *) PyModule_GetDict(PyObject *); +PyAPI_FUNC(char *) PyModule_GetName(PyObject *); +PyAPI_FUNC(char *) PyModule_GetFilename(PyObject *); +PyAPI_FUNC(void) _PyModule_Clear(PyObject *); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_MODULEOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/node.h b/AppPkg/Applications/Python/Python-2.7.10/Include/node.h new file mode 100644 index 0000000000..9baa89a444 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/node.h @@ -0,0 +1,41 @@ + +/* Parse tree node interface */ + +#ifndef Py_NODE_H +#define Py_NODE_H +#ifdef __cplusplus +extern "C" { +#endif + +typedef struct _node { + short n_type; + char *n_str; + int n_lineno; + int n_col_offset; + int n_nchildren; + struct _node *n_child; +} node; + +PyAPI_FUNC(node *) PyNode_New(int type); +PyAPI_FUNC(int) PyNode_AddChild(node *n, int type, + char *str, int lineno, int col_offset); +PyAPI_FUNC(void) PyNode_Free(node *n); +PyAPI_FUNC(Py_ssize_t) _PyNode_SizeOf(node *n); + +/* Node access functions */ +#define NCH(n) ((n)->n_nchildren) + +#define CHILD(n, i) (&(n)->n_child[i]) +#define RCHILD(n, i) (CHILD(n, NCH(n) + i)) +#define TYPE(n) ((n)->n_type) +#define STR(n) ((n)->n_str) + +/* Assert that the type of a node is what we expect */ +#define REQ(n, type) assert(TYPE(n) == (type)) + +PyAPI_FUNC(void) PyNode_ListTree(node *); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_NODE_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/object.h b/AppPkg/Applications/Python/Python-2.7.10/Include/object.h new file mode 100644 index 0000000000..bb5fa3cac9 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/object.h @@ -0,0 +1,1013 @@ +#ifndef Py_OBJECT_H +#define Py_OBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + + +/* Object and type object interface */ + +/* +Objects are structures allocated on the heap. Special rules apply to +the use of objects to ensure they are properly garbage-collected. +Objects are never allocated statically or on the stack; they must be +accessed through special macros and functions only. (Type objects are +exceptions to the first rule; the standard types are represented by +statically initialized type objects, although work on type/class unification +for Python 2.2 made it possible to have heap-allocated type objects too). + +An object has a 'reference count' that is increased or decreased when a +pointer to the object is copied or deleted; when the reference count +reaches zero there are no references to the object left and it can be +removed from the heap. + +An object has a 'type' that determines what it represents and what kind +of data it contains. An object's type is fixed when it is created. +Types themselves are represented as objects; an object contains a +pointer to the corresponding type object. The type itself has a type +pointer pointing to the object representing the type 'type', which +contains a pointer to itself!). + +Objects do not float around in memory; once allocated an object keeps +the same size and address. Objects that must hold variable-size data +can contain pointers to variable-size parts of the object. Not all +objects of the same type have the same size; but the size cannot change +after allocation. (These restrictions are made so a reference to an +object can be simply a pointer -- moving an object would require +updating all the pointers, and changing an object's size would require +moving it if there was another object right next to it.) + +Objects are always accessed through pointers of the type 'PyObject *'. +The type 'PyObject' is a structure that only contains the reference count +and the type pointer. The actual memory allocated for an object +contains other data that can only be accessed after casting the pointer +to a pointer to a longer structure type. This longer type must start +with the reference count and type fields; the macro PyObject_HEAD should be +used for this (to accommodate for future changes). The implementation +of a particular object type can cast the object pointer to the proper +type and back. + +A standard interface exists for objects that contain an array of items +whose size is determined when the object is allocated. +*/ + +/* Py_DEBUG implies Py_TRACE_REFS. */ +#if defined(Py_DEBUG) && !defined(Py_TRACE_REFS) +#define Py_TRACE_REFS +#endif + +/* Py_TRACE_REFS implies Py_REF_DEBUG. */ +#if defined(Py_TRACE_REFS) && !defined(Py_REF_DEBUG) +#define Py_REF_DEBUG +#endif + +#ifdef Py_TRACE_REFS +/* Define pointers to support a doubly-linked list of all live heap objects. */ +#define _PyObject_HEAD_EXTRA \ + struct _object *_ob_next; \ + struct _object *_ob_prev; + +#define _PyObject_EXTRA_INIT 0, 0, + +#else +#define _PyObject_HEAD_EXTRA +#define _PyObject_EXTRA_INIT +#endif + +/* PyObject_HEAD defines the initial segment of every PyObject. */ +#define PyObject_HEAD \ + _PyObject_HEAD_EXTRA \ + Py_ssize_t ob_refcnt; \ + struct _typeobject *ob_type; + +#define PyObject_HEAD_INIT(type) \ + _PyObject_EXTRA_INIT \ + 1, type, + +#define PyVarObject_HEAD_INIT(type, size) \ + PyObject_HEAD_INIT(type) size, + +/* PyObject_VAR_HEAD defines the initial segment of all variable-size + * container objects. These end with a declaration of an array with 1 + * element, but enough space is malloc'ed so that the array actually + * has room for ob_size elements. Note that ob_size is an element count, + * not necessarily a byte count. + */ +#define PyObject_VAR_HEAD \ + PyObject_HEAD \ + Py_ssize_t ob_size; /* Number of items in variable part */ +#define Py_INVALID_SIZE (Py_ssize_t)-1 + +/* Nothing is actually declared to be a PyObject, but every pointer to + * a Python object can be cast to a PyObject*. This is inheritance built + * by hand. Similarly every pointer to a variable-size Python object can, + * in addition, be cast to PyVarObject*. + */ +typedef struct _object { + PyObject_HEAD +} PyObject; + +typedef struct { + PyObject_VAR_HEAD +} PyVarObject; + +#define Py_REFCNT(ob) (((PyObject*)(ob))->ob_refcnt) +#define Py_TYPE(ob) (((PyObject*)(ob))->ob_type) +#define Py_SIZE(ob) (((PyVarObject*)(ob))->ob_size) + +/* +Type objects contain a string containing the type name (to help somewhat +in debugging), the allocation parameters (see PyObject_New() and +PyObject_NewVar()), +and methods for accessing objects of the type. Methods are optional, a +nil pointer meaning that particular kind of access is not available for +this type. The Py_DECREF() macro uses the tp_dealloc method without +checking for a nil pointer; it should always be implemented except if +the implementation can guarantee that the reference count will never +reach zero (e.g., for statically allocated type objects). + +NB: the methods for certain type groups are now contained in separate +method blocks. +*/ + +typedef PyObject * (*unaryfunc)(PyObject *); +typedef PyObject * (*binaryfunc)(PyObject *, PyObject *); +typedef PyObject * (*ternaryfunc)(PyObject *, PyObject *, PyObject *); +typedef int (*inquiry)(PyObject *); +typedef Py_ssize_t (*lenfunc)(PyObject *); +typedef int (*coercion)(PyObject **, PyObject **); +typedef PyObject *(*intargfunc)(PyObject *, int) Py_DEPRECATED(2.5); +typedef PyObject *(*intintargfunc)(PyObject *, int, int) Py_DEPRECATED(2.5); +typedef PyObject *(*ssizeargfunc)(PyObject *, Py_ssize_t); +typedef PyObject *(*ssizessizeargfunc)(PyObject *, Py_ssize_t, Py_ssize_t); +typedef int(*intobjargproc)(PyObject *, int, PyObject *); +typedef int(*intintobjargproc)(PyObject *, int, int, PyObject *); +typedef int(*ssizeobjargproc)(PyObject *, Py_ssize_t, PyObject *); +typedef int(*ssizessizeobjargproc)(PyObject *, Py_ssize_t, Py_ssize_t, PyObject *); +typedef int(*objobjargproc)(PyObject *, PyObject *, PyObject *); + + + +/* int-based buffer interface */ +typedef int (*getreadbufferproc)(PyObject *, int, void **); +typedef int (*getwritebufferproc)(PyObject *, int, void **); +typedef int (*getsegcountproc)(PyObject *, int *); +typedef int (*getcharbufferproc)(PyObject *, int, char **); +/* ssize_t-based buffer interface */ +typedef Py_ssize_t (*readbufferproc)(PyObject *, Py_ssize_t, void **); +typedef Py_ssize_t (*writebufferproc)(PyObject *, Py_ssize_t, void **); +typedef Py_ssize_t (*segcountproc)(PyObject *, Py_ssize_t *); +typedef Py_ssize_t (*charbufferproc)(PyObject *, Py_ssize_t, char **); + + +/* Py3k buffer interface */ +typedef struct bufferinfo { + void *buf; + PyObject *obj; /* owned reference */ + Py_ssize_t len; + Py_ssize_t itemsize; /* This is Py_ssize_t so it can be + pointed to by strides in simple case.*/ + int readonly; + int ndim; + char *format; + Py_ssize_t *shape; + Py_ssize_t *strides; + Py_ssize_t *suboffsets; + Py_ssize_t smalltable[2]; /* static store for shape and strides of + mono-dimensional buffers. */ + void *internal; +} Py_buffer; + +typedef int (*getbufferproc)(PyObject *, Py_buffer *, int); +typedef void (*releasebufferproc)(PyObject *, Py_buffer *); + + /* Flags for getting buffers */ +#define PyBUF_SIMPLE 0 +#define PyBUF_WRITABLE 0x0001 +/* we used to include an E, backwards compatible alias */ +#define PyBUF_WRITEABLE PyBUF_WRITABLE +#define PyBUF_FORMAT 0x0004 +#define PyBUF_ND 0x0008 +#define PyBUF_STRIDES (0x0010 | PyBUF_ND) +#define PyBUF_C_CONTIGUOUS (0x0020 | PyBUF_STRIDES) +#define PyBUF_F_CONTIGUOUS (0x0040 | PyBUF_STRIDES) +#define PyBUF_ANY_CONTIGUOUS (0x0080 | PyBUF_STRIDES) +#define PyBUF_INDIRECT (0x0100 | PyBUF_STRIDES) + +#define PyBUF_CONTIG (PyBUF_ND | PyBUF_WRITABLE) +#define PyBUF_CONTIG_RO (PyBUF_ND) + +#define PyBUF_STRIDED (PyBUF_STRIDES | PyBUF_WRITABLE) +#define PyBUF_STRIDED_RO (PyBUF_STRIDES) + +#define PyBUF_RECORDS (PyBUF_STRIDES | PyBUF_WRITABLE | PyBUF_FORMAT) +#define PyBUF_RECORDS_RO (PyBUF_STRIDES | PyBUF_FORMAT) + +#define PyBUF_FULL (PyBUF_INDIRECT | PyBUF_WRITABLE | PyBUF_FORMAT) +#define PyBUF_FULL_RO (PyBUF_INDIRECT | PyBUF_FORMAT) + + +#define PyBUF_READ 0x100 +#define PyBUF_WRITE 0x200 +#define PyBUF_SHADOW 0x400 +/* end Py3k buffer interface */ + +typedef int (*objobjproc)(PyObject *, PyObject *); +typedef int (*visitproc)(PyObject *, void *); +typedef int (*traverseproc)(PyObject *, visitproc, void *); + +typedef struct { + /* For numbers without flag bit Py_TPFLAGS_CHECKTYPES set, all + arguments are guaranteed to be of the object's type (modulo + coercion hacks -- i.e. if the type's coercion function + returns other types, then these are allowed as well). Numbers that + have the Py_TPFLAGS_CHECKTYPES flag bit set should check *both* + arguments for proper type and implement the necessary conversions + in the slot functions themselves. */ + + binaryfunc nb_add; + binaryfunc nb_subtract; + binaryfunc nb_multiply; + binaryfunc nb_divide; + binaryfunc nb_remainder; + binaryfunc nb_divmod; + ternaryfunc nb_power; + unaryfunc nb_negative; + unaryfunc nb_positive; + unaryfunc nb_absolute; + inquiry nb_nonzero; + unaryfunc nb_invert; + binaryfunc nb_lshift; + binaryfunc nb_rshift; + binaryfunc nb_and; + binaryfunc nb_xor; + binaryfunc nb_or; + coercion nb_coerce; + unaryfunc nb_int; + unaryfunc nb_long; + unaryfunc nb_float; + unaryfunc nb_oct; + unaryfunc nb_hex; + /* Added in release 2.0 */ + binaryfunc nb_inplace_add; + binaryfunc nb_inplace_subtract; + binaryfunc nb_inplace_multiply; + binaryfunc nb_inplace_divide; + binaryfunc nb_inplace_remainder; + ternaryfunc nb_inplace_power; + binaryfunc nb_inplace_lshift; + binaryfunc nb_inplace_rshift; + binaryfunc nb_inplace_and; + binaryfunc nb_inplace_xor; + binaryfunc nb_inplace_or; + + /* Added in release 2.2 */ + /* The following require the Py_TPFLAGS_HAVE_CLASS flag */ + binaryfunc nb_floor_divide; + binaryfunc nb_true_divide; + binaryfunc nb_inplace_floor_divide; + binaryfunc nb_inplace_true_divide; + + /* Added in release 2.5 */ + unaryfunc nb_index; +} PyNumberMethods; + +typedef struct { + lenfunc sq_length; + binaryfunc sq_concat; + ssizeargfunc sq_repeat; + ssizeargfunc sq_item; + ssizessizeargfunc sq_slice; + ssizeobjargproc sq_ass_item; + ssizessizeobjargproc sq_ass_slice; + objobjproc sq_contains; + /* Added in release 2.0 */ + binaryfunc sq_inplace_concat; + ssizeargfunc sq_inplace_repeat; +} PySequenceMethods; + +typedef struct { + lenfunc mp_length; + binaryfunc mp_subscript; + objobjargproc mp_ass_subscript; +} PyMappingMethods; + +typedef struct { + readbufferproc bf_getreadbuffer; + writebufferproc bf_getwritebuffer; + segcountproc bf_getsegcount; + charbufferproc bf_getcharbuffer; + getbufferproc bf_getbuffer; + releasebufferproc bf_releasebuffer; +} PyBufferProcs; + + +typedef void (*freefunc)(void *); +typedef void (*destructor)(PyObject *); +typedef int (*printfunc)(PyObject *, FILE *, int); +typedef PyObject *(*getattrfunc)(PyObject *, char *); +typedef PyObject *(*getattrofunc)(PyObject *, PyObject *); +typedef int (*setattrfunc)(PyObject *, char *, PyObject *); +typedef int (*setattrofunc)(PyObject *, PyObject *, PyObject *); +typedef int (*cmpfunc)(PyObject *, PyObject *); +typedef PyObject *(*reprfunc)(PyObject *); +typedef long (*hashfunc)(PyObject *); +typedef PyObject *(*richcmpfunc) (PyObject *, PyObject *, int); +typedef PyObject *(*getiterfunc) (PyObject *); +typedef PyObject *(*iternextfunc) (PyObject *); +typedef PyObject *(*descrgetfunc) (PyObject *, PyObject *, PyObject *); +typedef int (*descrsetfunc) (PyObject *, PyObject *, PyObject *); +typedef int (*initproc)(PyObject *, PyObject *, PyObject *); +typedef PyObject *(*newfunc)(struct _typeobject *, PyObject *, PyObject *); +typedef PyObject *(*allocfunc)(struct _typeobject *, Py_ssize_t); + +typedef struct _typeobject { + PyObject_VAR_HEAD + const char *tp_name; /* For printing, in format "." */ + Py_ssize_t tp_basicsize, tp_itemsize; /* For allocation */ + + /* Methods to implement standard operations */ + + destructor tp_dealloc; + printfunc tp_print; + getattrfunc tp_getattr; + setattrfunc tp_setattr; + cmpfunc tp_compare; + reprfunc tp_repr; + + /* Method suites for standard classes */ + + PyNumberMethods *tp_as_number; + PySequenceMethods *tp_as_sequence; + PyMappingMethods *tp_as_mapping; + + /* More standard operations (here for binary compatibility) */ + + hashfunc tp_hash; + ternaryfunc tp_call; + reprfunc tp_str; + getattrofunc tp_getattro; + setattrofunc tp_setattro; + + /* Functions to access object as input/output buffer */ + PyBufferProcs *tp_as_buffer; + + /* Flags to define presence of optional/expanded features */ + long tp_flags; + + const char *tp_doc; /* Documentation string */ + + /* Assigned meaning in release 2.0 */ + /* call function for all accessible objects */ + traverseproc tp_traverse; + + /* delete references to contained objects */ + inquiry tp_clear; + + /* Assigned meaning in release 2.1 */ + /* rich comparisons */ + richcmpfunc tp_richcompare; + + /* weak reference enabler */ + Py_ssize_t tp_weaklistoffset; + + /* Added in release 2.2 */ + /* Iterators */ + getiterfunc tp_iter; + iternextfunc tp_iternext; + + /* Attribute descriptor and subclassing stuff */ + struct PyMethodDef *tp_methods; + struct PyMemberDef *tp_members; + struct PyGetSetDef *tp_getset; + struct _typeobject *tp_base; + PyObject *tp_dict; + descrgetfunc tp_descr_get; + descrsetfunc tp_descr_set; + Py_ssize_t tp_dictoffset; + initproc tp_init; + allocfunc tp_alloc; + newfunc tp_new; + freefunc tp_free; /* Low-level free-memory routine */ + inquiry tp_is_gc; /* For PyObject_IS_GC */ + PyObject *tp_bases; + PyObject *tp_mro; /* method resolution order */ + PyObject *tp_cache; + PyObject *tp_subclasses; + PyObject *tp_weaklist; + destructor tp_del; + + /* Type attribute cache version tag. Added in version 2.6 */ + unsigned int tp_version_tag; + +#ifdef COUNT_ALLOCS + /* these must be last and never explicitly initialized */ + Py_ssize_t tp_allocs; + Py_ssize_t tp_frees; + Py_ssize_t tp_maxalloc; + struct _typeobject *tp_prev; + struct _typeobject *tp_next; +#endif +} PyTypeObject; + + +/* The *real* layout of a type object when allocated on the heap */ +typedef struct _heaptypeobject { + /* Note: there's a dependency on the order of these members + in slotptr() in typeobject.c . */ + PyTypeObject ht_type; + PyNumberMethods as_number; + PyMappingMethods as_mapping; + PySequenceMethods as_sequence; /* as_sequence comes after as_mapping, + so that the mapping wins when both + the mapping and the sequence define + a given operator (e.g. __getitem__). + see add_operators() in typeobject.c . */ + PyBufferProcs as_buffer; + PyObject *ht_name, *ht_slots; + /* here are optional user slots, followed by the members. */ +} PyHeapTypeObject; + +/* access macro to the members which are floating "behind" the object */ +#define PyHeapType_GET_MEMBERS(etype) \ + ((PyMemberDef *)(((char *)etype) + Py_TYPE(etype)->tp_basicsize)) + + +/* Generic type check */ +PyAPI_FUNC(int) PyType_IsSubtype(PyTypeObject *, PyTypeObject *); +#define PyObject_TypeCheck(ob, tp) \ + (Py_TYPE(ob) == (tp) || PyType_IsSubtype(Py_TYPE(ob), (tp))) + +PyAPI_DATA(PyTypeObject) PyType_Type; /* built-in 'type' */ +PyAPI_DATA(PyTypeObject) PyBaseObject_Type; /* built-in 'object' */ +PyAPI_DATA(PyTypeObject) PySuper_Type; /* built-in 'super' */ + +#define PyType_Check(op) \ + PyType_FastSubclass(Py_TYPE(op), Py_TPFLAGS_TYPE_SUBCLASS) +#define PyType_CheckExact(op) (Py_TYPE(op) == &PyType_Type) + +PyAPI_FUNC(int) PyType_Ready(PyTypeObject *); +PyAPI_FUNC(PyObject *) PyType_GenericAlloc(PyTypeObject *, Py_ssize_t); +PyAPI_FUNC(PyObject *) PyType_GenericNew(PyTypeObject *, + PyObject *, PyObject *); +PyAPI_FUNC(PyObject *) _PyType_Lookup(PyTypeObject *, PyObject *); +PyAPI_FUNC(PyObject *) _PyObject_LookupSpecial(PyObject *, char *, PyObject **); +PyAPI_FUNC(unsigned int) PyType_ClearCache(void); +PyAPI_FUNC(void) PyType_Modified(PyTypeObject *); + +/* Generic operations on objects */ +PyAPI_FUNC(int) PyObject_Print(PyObject *, FILE *, int); +PyAPI_FUNC(void) _PyObject_Dump(PyObject *); +PyAPI_FUNC(PyObject *) PyObject_Repr(PyObject *); +PyAPI_FUNC(PyObject *) _PyObject_Str(PyObject *); +PyAPI_FUNC(PyObject *) PyObject_Str(PyObject *); +#define PyObject_Bytes PyObject_Str +#ifdef Py_USING_UNICODE +PyAPI_FUNC(PyObject *) PyObject_Unicode(PyObject *); +#endif +PyAPI_FUNC(int) PyObject_Compare(PyObject *, PyObject *); +PyAPI_FUNC(PyObject *) PyObject_RichCompare(PyObject *, PyObject *, int); +PyAPI_FUNC(int) PyObject_RichCompareBool(PyObject *, PyObject *, int); +PyAPI_FUNC(PyObject *) PyObject_GetAttrString(PyObject *, const char *); +PyAPI_FUNC(int) PyObject_SetAttrString(PyObject *, const char *, PyObject *); +PyAPI_FUNC(int) PyObject_HasAttrString(PyObject *, const char *); +PyAPI_FUNC(PyObject *) PyObject_GetAttr(PyObject *, PyObject *); +PyAPI_FUNC(int) PyObject_SetAttr(PyObject *, PyObject *, PyObject *); +PyAPI_FUNC(int) PyObject_HasAttr(PyObject *, PyObject *); +PyAPI_FUNC(PyObject **) _PyObject_GetDictPtr(PyObject *); +PyAPI_FUNC(PyObject *) PyObject_SelfIter(PyObject *); +PyAPI_FUNC(PyObject *) _PyObject_NextNotImplemented(PyObject *); +PyAPI_FUNC(PyObject *) PyObject_GenericGetAttr(PyObject *, PyObject *); +PyAPI_FUNC(int) PyObject_GenericSetAttr(PyObject *, + PyObject *, PyObject *); +PyAPI_FUNC(long) PyObject_Hash(PyObject *); +PyAPI_FUNC(long) PyObject_HashNotImplemented(PyObject *); +PyAPI_FUNC(int) PyObject_IsTrue(PyObject *); +PyAPI_FUNC(int) PyObject_Not(PyObject *); +PyAPI_FUNC(int) PyCallable_Check(PyObject *); +PyAPI_FUNC(int) PyNumber_Coerce(PyObject **, PyObject **); +PyAPI_FUNC(int) PyNumber_CoerceEx(PyObject **, PyObject **); + +PyAPI_FUNC(void) PyObject_ClearWeakRefs(PyObject *); + +/* A slot function whose address we need to compare */ +extern int _PyObject_SlotCompare(PyObject *, PyObject *); +/* Same as PyObject_Generic{Get,Set}Attr, but passing the attributes + dict as the last parameter. */ +PyAPI_FUNC(PyObject *) +_PyObject_GenericGetAttrWithDict(PyObject *, PyObject *, PyObject *); +PyAPI_FUNC(int) +_PyObject_GenericSetAttrWithDict(PyObject *, PyObject *, + PyObject *, PyObject *); + + +/* PyObject_Dir(obj) acts like Python __builtin__.dir(obj), returning a + list of strings. PyObject_Dir(NULL) is like __builtin__.dir(), + returning the names of the current locals. In this case, if there are + no current locals, NULL is returned, and PyErr_Occurred() is false. +*/ +PyAPI_FUNC(PyObject *) PyObject_Dir(PyObject *); + + +/* Helpers for printing recursive container types */ +PyAPI_FUNC(int) Py_ReprEnter(PyObject *); +PyAPI_FUNC(void) Py_ReprLeave(PyObject *); + +/* Helpers for hash functions */ +PyAPI_FUNC(long) _Py_HashDouble(double); +PyAPI_FUNC(long) _Py_HashPointer(void*); + +typedef struct { + long prefix; + long suffix; +} _Py_HashSecret_t; +PyAPI_DATA(_Py_HashSecret_t) _Py_HashSecret; + +#ifdef Py_DEBUG +PyAPI_DATA(int) _Py_HashSecret_Initialized; +#endif + +/* Helper for passing objects to printf and the like. + Leaks refcounts. Don't use it! +*/ +#define PyObject_REPR(obj) PyString_AS_STRING(PyObject_Repr(obj)) + +/* Flag bits for printing: */ +#define Py_PRINT_RAW 1 /* No string quotes etc. */ + +/* +`Type flags (tp_flags) + +These flags are used to extend the type structure in a backwards-compatible +fashion. Extensions can use the flags to indicate (and test) when a given +type structure contains a new feature. The Python core will use these when +introducing new functionality between major revisions (to avoid mid-version +changes in the PYTHON_API_VERSION). + +Arbitration of the flag bit positions will need to be coordinated among +all extension writers who publically release their extensions (this will +be fewer than you might expect!).. + +Python 1.5.2 introduced the bf_getcharbuffer slot into PyBufferProcs. + +Type definitions should use Py_TPFLAGS_DEFAULT for their tp_flags value. + +Code can use PyType_HasFeature(type_ob, flag_value) to test whether the +given type object has a specified feature. + +NOTE: when building the core, Py_TPFLAGS_DEFAULT includes +Py_TPFLAGS_HAVE_VERSION_TAG; outside the core, it doesn't. This is so +that extensions that modify tp_dict of their own types directly don't +break, since this was allowed in 2.5. In 3.0 they will have to +manually remove this flag though! +*/ + +/* PyBufferProcs contains bf_getcharbuffer */ +#define Py_TPFLAGS_HAVE_GETCHARBUFFER (1L<<0) + +/* PySequenceMethods contains sq_contains */ +#define Py_TPFLAGS_HAVE_SEQUENCE_IN (1L<<1) + +/* This is here for backwards compatibility. Extensions that use the old GC + * API will still compile but the objects will not be tracked by the GC. */ +#define Py_TPFLAGS_GC 0 /* used to be (1L<<2) */ + +/* PySequenceMethods and PyNumberMethods contain in-place operators */ +#define Py_TPFLAGS_HAVE_INPLACEOPS (1L<<3) + +/* PyNumberMethods do their own coercion */ +#define Py_TPFLAGS_CHECKTYPES (1L<<4) + +/* tp_richcompare is defined */ +#define Py_TPFLAGS_HAVE_RICHCOMPARE (1L<<5) + +/* Objects which are weakly referencable if their tp_weaklistoffset is >0 */ +#define Py_TPFLAGS_HAVE_WEAKREFS (1L<<6) + +/* tp_iter is defined */ +#define Py_TPFLAGS_HAVE_ITER (1L<<7) + +/* New members introduced by Python 2.2 exist */ +#define Py_TPFLAGS_HAVE_CLASS (1L<<8) + +/* Set if the type object is dynamically allocated */ +#define Py_TPFLAGS_HEAPTYPE (1L<<9) + +/* Set if the type allows subclassing */ +#define Py_TPFLAGS_BASETYPE (1L<<10) + +/* Set if the type is 'ready' -- fully initialized */ +#define Py_TPFLAGS_READY (1L<<12) + +/* Set while the type is being 'readied', to prevent recursive ready calls */ +#define Py_TPFLAGS_READYING (1L<<13) + +/* Objects support garbage collection (see objimp.h) */ +#define Py_TPFLAGS_HAVE_GC (1L<<14) + +/* These two bits are preserved for Stackless Python, next after this is 17 */ +#ifdef STACKLESS +#define Py_TPFLAGS_HAVE_STACKLESS_EXTENSION (3L<<15) +#else +#define Py_TPFLAGS_HAVE_STACKLESS_EXTENSION 0 +#endif + +/* Objects support nb_index in PyNumberMethods */ +#define Py_TPFLAGS_HAVE_INDEX (1L<<17) + +/* Objects support type attribute cache */ +#define Py_TPFLAGS_HAVE_VERSION_TAG (1L<<18) +#define Py_TPFLAGS_VALID_VERSION_TAG (1L<<19) + +/* Type is abstract and cannot be instantiated */ +#define Py_TPFLAGS_IS_ABSTRACT (1L<<20) + +/* Has the new buffer protocol */ +#define Py_TPFLAGS_HAVE_NEWBUFFER (1L<<21) + +/* These flags are used to determine if a type is a subclass. */ +#define Py_TPFLAGS_INT_SUBCLASS (1L<<23) +#define Py_TPFLAGS_LONG_SUBCLASS (1L<<24) +#define Py_TPFLAGS_LIST_SUBCLASS (1L<<25) +#define Py_TPFLAGS_TUPLE_SUBCLASS (1L<<26) +#define Py_TPFLAGS_STRING_SUBCLASS (1L<<27) +#define Py_TPFLAGS_UNICODE_SUBCLASS (1L<<28) +#define Py_TPFLAGS_DICT_SUBCLASS (1L<<29) +#define Py_TPFLAGS_BASE_EXC_SUBCLASS (1L<<30) +#define Py_TPFLAGS_TYPE_SUBCLASS (1L<<31) + +#define Py_TPFLAGS_DEFAULT_EXTERNAL ( \ + Py_TPFLAGS_HAVE_GETCHARBUFFER | \ + Py_TPFLAGS_HAVE_SEQUENCE_IN | \ + Py_TPFLAGS_HAVE_INPLACEOPS | \ + Py_TPFLAGS_HAVE_RICHCOMPARE | \ + Py_TPFLAGS_HAVE_WEAKREFS | \ + Py_TPFLAGS_HAVE_ITER | \ + Py_TPFLAGS_HAVE_CLASS | \ + Py_TPFLAGS_HAVE_STACKLESS_EXTENSION | \ + Py_TPFLAGS_HAVE_INDEX | \ + 0) +#define Py_TPFLAGS_DEFAULT_CORE (Py_TPFLAGS_DEFAULT_EXTERNAL | \ + Py_TPFLAGS_HAVE_VERSION_TAG) + +#ifdef Py_BUILD_CORE +#define Py_TPFLAGS_DEFAULT Py_TPFLAGS_DEFAULT_CORE +#else +#define Py_TPFLAGS_DEFAULT Py_TPFLAGS_DEFAULT_EXTERNAL +#endif + +#define PyType_HasFeature(t,f) (((t)->tp_flags & (f)) != 0) +#define PyType_FastSubclass(t,f) PyType_HasFeature(t,f) + + +/* +The macros Py_INCREF(op) and Py_DECREF(op) are used to increment or decrement +reference counts. Py_DECREF calls the object's deallocator function when +the refcount falls to 0; for +objects that don't contain references to other objects or heap memory +this can be the standard function free(). Both macros can be used +wherever a void expression is allowed. The argument must not be a +NULL pointer. If it may be NULL, use Py_XINCREF/Py_XDECREF instead. +The macro _Py_NewReference(op) initialize reference counts to 1, and +in special builds (Py_REF_DEBUG, Py_TRACE_REFS) performs additional +bookkeeping appropriate to the special build. + +We assume that the reference count field can never overflow; this can +be proven when the size of the field is the same as the pointer size, so +we ignore the possibility. Provided a C int is at least 32 bits (which +is implicitly assumed in many parts of this code), that's enough for +about 2**31 references to an object. + +XXX The following became out of date in Python 2.2, but I'm not sure +XXX what the full truth is now. Certainly, heap-allocated type objects +XXX can and should be deallocated. +Type objects should never be deallocated; the type pointer in an object +is not considered to be a reference to the type object, to save +complications in the deallocation function. (This is actually a +decision that's up to the implementer of each new type so if you want, +you can count such references to the type object.) + +*** WARNING*** The Py_DECREF macro must have a side-effect-free argument +since it may evaluate its argument multiple times. (The alternative +would be to mace it a proper function or assign it to a global temporary +variable first, both of which are slower; and in a multi-threaded +environment the global variable trick is not safe.) +*/ + +/* First define a pile of simple helper macros, one set per special + * build symbol. These either expand to the obvious things, or to + * nothing at all when the special mode isn't in effect. The main + * macros can later be defined just once then, yet expand to different + * things depending on which special build options are and aren't in effect. + * Trust me : while painful, this is 20x easier to understand than, + * e.g, defining _Py_NewReference five different times in a maze of nested + * #ifdefs (we used to do that -- it was impenetrable). + */ +#ifdef Py_REF_DEBUG +PyAPI_DATA(Py_ssize_t) _Py_RefTotal; +PyAPI_FUNC(void) _Py_NegativeRefcount(const char *fname, + int lineno, PyObject *op); +PyAPI_FUNC(PyObject *) _PyDict_Dummy(void); +PyAPI_FUNC(PyObject *) _PySet_Dummy(void); +PyAPI_FUNC(Py_ssize_t) _Py_GetRefTotal(void); +#define _Py_INC_REFTOTAL _Py_RefTotal++ +#define _Py_DEC_REFTOTAL _Py_RefTotal-- +#define _Py_REF_DEBUG_COMMA , +#define _Py_CHECK_REFCNT(OP) \ +{ if (((PyObject*)OP)->ob_refcnt < 0) \ + _Py_NegativeRefcount(__FILE__, __LINE__, \ + (PyObject *)(OP)); \ +} +#else +#define _Py_INC_REFTOTAL +#define _Py_DEC_REFTOTAL +#define _Py_REF_DEBUG_COMMA +#define _Py_CHECK_REFCNT(OP) /* a semicolon */; +#endif /* Py_REF_DEBUG */ + +#ifdef COUNT_ALLOCS +PyAPI_FUNC(void) inc_count(PyTypeObject *); +PyAPI_FUNC(void) dec_count(PyTypeObject *); +#define _Py_INC_TPALLOCS(OP) inc_count(Py_TYPE(OP)) +#define _Py_INC_TPFREES(OP) dec_count(Py_TYPE(OP)) +#define _Py_DEC_TPFREES(OP) Py_TYPE(OP)->tp_frees-- +#define _Py_COUNT_ALLOCS_COMMA , +#else +#define _Py_INC_TPALLOCS(OP) +#define _Py_INC_TPFREES(OP) +#define _Py_DEC_TPFREES(OP) +#define _Py_COUNT_ALLOCS_COMMA +#endif /* COUNT_ALLOCS */ + +#ifdef Py_TRACE_REFS +/* Py_TRACE_REFS is such major surgery that we call external routines. */ +PyAPI_FUNC(void) _Py_NewReference(PyObject *); +PyAPI_FUNC(void) _Py_ForgetReference(PyObject *); +PyAPI_FUNC(void) _Py_Dealloc(PyObject *); +PyAPI_FUNC(void) _Py_PrintReferences(FILE *); +PyAPI_FUNC(void) _Py_PrintReferenceAddresses(FILE *); +PyAPI_FUNC(void) _Py_AddToAllObjects(PyObject *, int force); + +#else +/* Without Py_TRACE_REFS, there's little enough to do that we expand code + * inline. + */ +#define _Py_NewReference(op) ( \ + _Py_INC_TPALLOCS(op) _Py_COUNT_ALLOCS_COMMA \ + _Py_INC_REFTOTAL _Py_REF_DEBUG_COMMA \ + Py_REFCNT(op) = 1) + +#define _Py_ForgetReference(op) _Py_INC_TPFREES(op) + +#define _Py_Dealloc(op) ( \ + _Py_INC_TPFREES(op) _Py_COUNT_ALLOCS_COMMA \ + (*Py_TYPE(op)->tp_dealloc)((PyObject *)(op))) +#endif /* !Py_TRACE_REFS */ + +#define Py_INCREF(op) ( \ + _Py_INC_REFTOTAL _Py_REF_DEBUG_COMMA \ + ((PyObject*)(op))->ob_refcnt++) + +#define Py_DECREF(op) \ + do { \ + if (_Py_DEC_REFTOTAL _Py_REF_DEBUG_COMMA \ + --((PyObject*)(op))->ob_refcnt != 0) \ + _Py_CHECK_REFCNT(op) \ + else \ + _Py_Dealloc((PyObject *)(op)); \ + } while (0) + +/* Safely decref `op` and set `op` to NULL, especially useful in tp_clear + * and tp_dealloc implementatons. + * + * Note that "the obvious" code can be deadly: + * + * Py_XDECREF(op); + * op = NULL; + * + * Typically, `op` is something like self->containee, and `self` is done + * using its `containee` member. In the code sequence above, suppose + * `containee` is non-NULL with a refcount of 1. Its refcount falls to + * 0 on the first line, which can trigger an arbitrary amount of code, + * possibly including finalizers (like __del__ methods or weakref callbacks) + * coded in Python, which in turn can release the GIL and allow other threads + * to run, etc. Such code may even invoke methods of `self` again, or cause + * cyclic gc to trigger, but-- oops! --self->containee still points to the + * object being torn down, and it may be in an insane state while being torn + * down. This has in fact been a rich historic source of miserable (rare & + * hard-to-diagnose) segfaulting (and other) bugs. + * + * The safe way is: + * + * Py_CLEAR(op); + * + * That arranges to set `op` to NULL _before_ decref'ing, so that any code + * triggered as a side-effect of `op` getting torn down no longer believes + * `op` points to a valid object. + * + * There are cases where it's safe to use the naive code, but they're brittle. + * For example, if `op` points to a Python integer, you know that destroying + * one of those can't cause problems -- but in part that relies on that + * Python integers aren't currently weakly referencable. Best practice is + * to use Py_CLEAR() even if you can't think of a reason for why you need to. + */ +#define Py_CLEAR(op) \ + do { \ + if (op) { \ + PyObject *_py_tmp = (PyObject *)(op); \ + (op) = NULL; \ + Py_DECREF(_py_tmp); \ + } \ + } while (0) + +/* Macros to use in case the object pointer may be NULL: */ +#define Py_XINCREF(op) do { if ((op) == NULL) ; else Py_INCREF(op); } while (0) +#define Py_XDECREF(op) do { if ((op) == NULL) ; else Py_DECREF(op); } while (0) + +/* +These are provided as conveniences to Python runtime embedders, so that +they can have object code that is not dependent on Python compilation flags. +*/ +PyAPI_FUNC(void) Py_IncRef(PyObject *); +PyAPI_FUNC(void) Py_DecRef(PyObject *); + +/* +_Py_NoneStruct is an object of undefined type which can be used in contexts +where NULL (nil) is not suitable (since NULL often means 'error'). + +Don't forget to apply Py_INCREF() when returning this value!!! +*/ +PyAPI_DATA(PyObject) _Py_NoneStruct; /* Don't use this directly */ +#define Py_None (&_Py_NoneStruct) + +/* Macro for returning Py_None from a function */ +#define Py_RETURN_NONE return Py_INCREF(Py_None), Py_None + +/* +Py_NotImplemented is a singleton used to signal that an operation is +not implemented for a given type combination. +*/ +PyAPI_DATA(PyObject) _Py_NotImplementedStruct; /* Don't use this directly */ +#define Py_NotImplemented (&_Py_NotImplementedStruct) + +/* Rich comparison opcodes */ +#define Py_LT 0 +#define Py_LE 1 +#define Py_EQ 2 +#define Py_NE 3 +#define Py_GT 4 +#define Py_GE 5 + +/* Maps Py_LT to Py_GT, ..., Py_GE to Py_LE. + * Defined in object.c. + */ +PyAPI_DATA(int) _Py_SwappedOp[]; + +/* +Define staticforward and statichere for source compatibility with old +C extensions. + +The staticforward define was needed to support certain broken C +compilers (notably SCO ODT 3.0, perhaps early AIX as well) botched the +static keyword when it was used with a forward declaration of a static +initialized structure. Standard C allows the forward declaration with +static, and we've decided to stop catering to broken C compilers. +(In fact, we expect that the compilers are all fixed eight years later.) +*/ + +#define staticforward static +#define statichere static + + +/* +More conventions +================ + +Argument Checking +----------------- + +Functions that take objects as arguments normally don't check for nil +arguments, but they do check the type of the argument, and return an +error if the function doesn't apply to the type. + +Failure Modes +------------- + +Functions may fail for a variety of reasons, including running out of +memory. This is communicated to the caller in two ways: an error string +is set (see errors.h), and the function result differs: functions that +normally return a pointer return NULL for failure, functions returning +an integer return -1 (which could be a legal return value too!), and +other functions return 0 for success and -1 for failure. +Callers should always check for errors before using the result. If +an error was set, the caller must either explicitly clear it, or pass +the error on to its caller. + +Reference Counts +---------------- + +It takes a while to get used to the proper usage of reference counts. + +Functions that create an object set the reference count to 1; such new +objects must be stored somewhere or destroyed again with Py_DECREF(). +Some functions that 'store' objects, such as PyTuple_SetItem() and +PyList_SetItem(), +don't increment the reference count of the object, since the most +frequent use is to store a fresh object. Functions that 'retrieve' +objects, such as PyTuple_GetItem() and PyDict_GetItemString(), also +don't increment +the reference count, since most frequently the object is only looked at +quickly. Thus, to retrieve an object and store it again, the caller +must call Py_INCREF() explicitly. + +NOTE: functions that 'consume' a reference count, like +PyList_SetItem(), consume the reference even if the object wasn't +successfully stored, to simplify error handling. + +It seems attractive to make other functions that take an object as +argument consume a reference count; however, this may quickly get +confusing (even the current practice is already confusing). Consider +it carefully, it may save lots of calls to Py_INCREF() and Py_DECREF() at +times. +*/ + + +/* Trashcan mechanism, thanks to Christian Tismer. + +When deallocating a container object, it's possible to trigger an unbounded +chain of deallocations, as each Py_DECREF in turn drops the refcount on "the +next" object in the chain to 0. This can easily lead to stack faults, and +especially in threads (which typically have less stack space to work with). + +A container object that participates in cyclic gc can avoid this by +bracketing the body of its tp_dealloc function with a pair of macros: + +static void +mytype_dealloc(mytype *p) +{ + ... declarations go here ... + + PyObject_GC_UnTrack(p); // must untrack first + Py_TRASHCAN_SAFE_BEGIN(p) + ... The body of the deallocator goes here, including all calls ... + ... to Py_DECREF on contained objects. ... + Py_TRASHCAN_SAFE_END(p) +} + +CAUTION: Never return from the middle of the body! If the body needs to +"get out early", put a label immediately before the Py_TRASHCAN_SAFE_END +call, and goto it. Else the call-depth counter (see below) will stay +above 0 forever, and the trashcan will never get emptied. + +How it works: The BEGIN macro increments a call-depth counter. So long +as this counter is small, the body of the deallocator is run directly without +further ado. But if the counter gets large, it instead adds p to a list of +objects to be deallocated later, skips the body of the deallocator, and +resumes execution after the END macro. The tp_dealloc routine then returns +without deallocating anything (and so unbounded call-stack depth is avoided). + +When the call stack finishes unwinding again, code generated by the END macro +notices this, and calls another routine to deallocate all the objects that +may have been added to the list of deferred deallocations. In effect, a +chain of N deallocations is broken into N / PyTrash_UNWIND_LEVEL pieces, +with the call stack never exceeding a depth of PyTrash_UNWIND_LEVEL. +*/ + +/* This is the old private API, invoked by the macros before 2.7.4. + Kept for binary compatibility of extensions. */ +PyAPI_FUNC(void) _PyTrash_deposit_object(PyObject*); +PyAPI_FUNC(void) _PyTrash_destroy_chain(void); +PyAPI_DATA(int) _PyTrash_delete_nesting; +PyAPI_DATA(PyObject *) _PyTrash_delete_later; + +/* The new thread-safe private API, invoked by the macros below. */ +PyAPI_FUNC(void) _PyTrash_thread_deposit_object(PyObject*); +PyAPI_FUNC(void) _PyTrash_thread_destroy_chain(void); + +#define PyTrash_UNWIND_LEVEL 50 + +/* Note the workaround for when the thread state is NULL (issue #17703) */ +#define Py_TRASHCAN_SAFE_BEGIN(op) \ + do { \ + PyThreadState *_tstate = PyThreadState_GET(); \ + if (!_tstate || \ + _tstate->trash_delete_nesting < PyTrash_UNWIND_LEVEL) { \ + if (_tstate) \ + ++_tstate->trash_delete_nesting; + /* The body of the deallocator is here. */ +#define Py_TRASHCAN_SAFE_END(op) \ + if (_tstate) { \ + --_tstate->trash_delete_nesting; \ + if (_tstate->trash_delete_later \ + && _tstate->trash_delete_nesting <= 0) \ + _PyTrash_thread_destroy_chain(); \ + } \ + } \ + else \ + _PyTrash_thread_deposit_object((PyObject*)op); \ + } while (0); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_OBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/objimpl.h b/AppPkg/Applications/Python/Python-2.7.10/Include/objimpl.h new file mode 100644 index 0000000000..79d7e2de60 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/objimpl.h @@ -0,0 +1,354 @@ +/* The PyObject_ memory family: high-level object memory interfaces. + See pymem.h for the low-level PyMem_ family. +*/ + +#ifndef Py_OBJIMPL_H +#define Py_OBJIMPL_H + +#include "pymem.h" + +#ifdef __cplusplus +extern "C" { +#endif + +/* BEWARE: + + Each interface exports both functions and macros. Extension modules should + use the functions, to ensure binary compatibility across Python versions. + Because the Python implementation is free to change internal details, and + the macros may (or may not) expose details for speed, if you do use the + macros you must recompile your extensions with each Python release. + + Never mix calls to PyObject_ memory functions with calls to the platform + malloc/realloc/ calloc/free, or with calls to PyMem_. +*/ + +/* +Functions and macros for modules that implement new object types. + + - PyObject_New(type, typeobj) allocates memory for a new object of the given + type, and initializes part of it. 'type' must be the C structure type used + to represent the object, and 'typeobj' the address of the corresponding + type object. Reference count and type pointer are filled in; the rest of + the bytes of the object are *undefined*! The resulting expression type is + 'type *'. The size of the object is determined by the tp_basicsize field + of the type object. + + - PyObject_NewVar(type, typeobj, n) is similar but allocates a variable-size + object with room for n items. In addition to the refcount and type pointer + fields, this also fills in the ob_size field. + + - PyObject_Del(op) releases the memory allocated for an object. It does not + run a destructor -- it only frees the memory. PyObject_Free is identical. + + - PyObject_Init(op, typeobj) and PyObject_InitVar(op, typeobj, n) don't + allocate memory. Instead of a 'type' parameter, they take a pointer to a + new object (allocated by an arbitrary allocator), and initialize its object + header fields. + +Note that objects created with PyObject_{New, NewVar} are allocated using the +specialized Python allocator (implemented in obmalloc.c), if WITH_PYMALLOC is +enabled. In addition, a special debugging allocator is used if PYMALLOC_DEBUG +is also #defined. + +In case a specific form of memory management is needed (for example, if you +must use the platform malloc heap(s), or shared memory, or C++ local storage or +operator new), you must first allocate the object with your custom allocator, +then pass its pointer to PyObject_{Init, InitVar} for filling in its Python- +specific fields: reference count, type pointer, possibly others. You should +be aware that Python no control over these objects because they don't +cooperate with the Python memory manager. Such objects may not be eligible +for automatic garbage collection and you have to make sure that they are +released accordingly whenever their destructor gets called (cf. the specific +form of memory management you're using). + +Unless you have specific memory management requirements, use +PyObject_{New, NewVar, Del}. +*/ + +/* + * Raw object memory interface + * =========================== + */ + +/* Functions to call the same malloc/realloc/free as used by Python's + object allocator. If WITH_PYMALLOC is enabled, these may differ from + the platform malloc/realloc/free. The Python object allocator is + designed for fast, cache-conscious allocation of many "small" objects, + and with low hidden memory overhead. + + PyObject_Malloc(0) returns a unique non-NULL pointer if possible. + + PyObject_Realloc(NULL, n) acts like PyObject_Malloc(n). + PyObject_Realloc(p != NULL, 0) does not return NULL, or free the memory + at p. + + Returned pointers must be checked for NULL explicitly; no action is + performed on failure other than to return NULL (no warning it printed, no + exception is set, etc). + + For allocating objects, use PyObject_{New, NewVar} instead whenever + possible. The PyObject_{Malloc, Realloc, Free} family is exposed + so that you can exploit Python's small-block allocator for non-object + uses. If you must use these routines to allocate object memory, make sure + the object gets initialized via PyObject_{Init, InitVar} after obtaining + the raw memory. +*/ +PyAPI_FUNC(void *) PyObject_Malloc(size_t); +PyAPI_FUNC(void *) PyObject_Realloc(void *, size_t); +PyAPI_FUNC(void) PyObject_Free(void *); + + +/* Macros */ +#ifdef WITH_PYMALLOC +#ifdef PYMALLOC_DEBUG /* WITH_PYMALLOC && PYMALLOC_DEBUG */ +PyAPI_FUNC(void *) _PyObject_DebugMalloc(size_t nbytes); +PyAPI_FUNC(void *) _PyObject_DebugRealloc(void *p, size_t nbytes); +PyAPI_FUNC(void) _PyObject_DebugFree(void *p); +PyAPI_FUNC(void) _PyObject_DebugDumpAddress(const void *p); +PyAPI_FUNC(void) _PyObject_DebugCheckAddress(const void *p); +PyAPI_FUNC(void) _PyObject_DebugMallocStats(void); +PyAPI_FUNC(void *) _PyObject_DebugMallocApi(char api, size_t nbytes); +PyAPI_FUNC(void *) _PyObject_DebugReallocApi(char api, void *p, size_t nbytes); +PyAPI_FUNC(void) _PyObject_DebugFreeApi(char api, void *p); +PyAPI_FUNC(void) _PyObject_DebugCheckAddressApi(char api, const void *p); +PyAPI_FUNC(void *) _PyMem_DebugMalloc(size_t nbytes); +PyAPI_FUNC(void *) _PyMem_DebugRealloc(void *p, size_t nbytes); +PyAPI_FUNC(void) _PyMem_DebugFree(void *p); +#define PyObject_MALLOC _PyObject_DebugMalloc +#define PyObject_Malloc _PyObject_DebugMalloc +#define PyObject_REALLOC _PyObject_DebugRealloc +#define PyObject_Realloc _PyObject_DebugRealloc +#define PyObject_FREE _PyObject_DebugFree +#define PyObject_Free _PyObject_DebugFree + +#else /* WITH_PYMALLOC && ! PYMALLOC_DEBUG */ +#define PyObject_MALLOC PyObject_Malloc +#define PyObject_REALLOC PyObject_Realloc +#define PyObject_FREE PyObject_Free +#endif + +#else /* ! WITH_PYMALLOC */ +#define PyObject_MALLOC PyMem_MALLOC +#define PyObject_REALLOC PyMem_REALLOC +#define PyObject_FREE PyMem_FREE + +#endif /* WITH_PYMALLOC */ + +#define PyObject_Del PyObject_Free +#define PyObject_DEL PyObject_FREE + +/* for source compatibility with 2.2 */ +#define _PyObject_Del PyObject_Free + +/* + * Generic object allocator interface + * ================================== + */ + +/* Functions */ +PyAPI_FUNC(PyObject *) PyObject_Init(PyObject *, PyTypeObject *); +PyAPI_FUNC(PyVarObject *) PyObject_InitVar(PyVarObject *, + PyTypeObject *, Py_ssize_t); +PyAPI_FUNC(PyObject *) _PyObject_New(PyTypeObject *); +PyAPI_FUNC(PyVarObject *) _PyObject_NewVar(PyTypeObject *, Py_ssize_t); + +#define PyObject_New(type, typeobj) \ + ( (type *) _PyObject_New(typeobj) ) +#define PyObject_NewVar(type, typeobj, n) \ + ( (type *) _PyObject_NewVar((typeobj), (n)) ) + +/* Macros trading binary compatibility for speed. See also pymem.h. + Note that these macros expect non-NULL object pointers.*/ +#define PyObject_INIT(op, typeobj) \ + ( Py_TYPE(op) = (typeobj), _Py_NewReference((PyObject *)(op)), (op) ) +#define PyObject_INIT_VAR(op, typeobj, size) \ + ( Py_SIZE(op) = (size), PyObject_INIT((op), (typeobj)) ) + +#define _PyObject_SIZE(typeobj) ( (typeobj)->tp_basicsize ) + +/* _PyObject_VAR_SIZE returns the number of bytes (as size_t) allocated for a + vrbl-size object with nitems items, exclusive of gc overhead (if any). The + value is rounded up to the closest multiple of sizeof(void *), in order to + ensure that pointer fields at the end of the object are correctly aligned + for the platform (this is of special importance for subclasses of, e.g., + str or long, so that pointers can be stored after the embedded data). + + Note that there's no memory wastage in doing this, as malloc has to + return (at worst) pointer-aligned memory anyway. +*/ +#if ((SIZEOF_VOID_P - 1) & SIZEOF_VOID_P) != 0 +# error "_PyObject_VAR_SIZE requires SIZEOF_VOID_P be a power of 2" +#endif + +#define _PyObject_VAR_SIZE(typeobj, nitems) \ + (size_t) \ + ( ( (typeobj)->tp_basicsize + \ + (nitems)*(typeobj)->tp_itemsize + \ + (SIZEOF_VOID_P - 1) \ + ) & ~(SIZEOF_VOID_P - 1) \ + ) + +#define PyObject_NEW(type, typeobj) \ +( (type *) PyObject_Init( \ + (PyObject *) PyObject_MALLOC( _PyObject_SIZE(typeobj) ), (typeobj)) ) + +#define PyObject_NEW_VAR(type, typeobj, n) \ +( (type *) PyObject_InitVar( \ + (PyVarObject *) PyObject_MALLOC(_PyObject_VAR_SIZE((typeobj),(n)) ),\ + (typeobj), (n)) ) + +/* This example code implements an object constructor with a custom + allocator, where PyObject_New is inlined, and shows the important + distinction between two steps (at least): + 1) the actual allocation of the object storage; + 2) the initialization of the Python specific fields + in this storage with PyObject_{Init, InitVar}. + + PyObject * + YourObject_New(...) + { + PyObject *op; + + op = (PyObject *) Your_Allocator(_PyObject_SIZE(YourTypeStruct)); + if (op == NULL) + return PyErr_NoMemory(); + + PyObject_Init(op, &YourTypeStruct); + + op->ob_field = value; + ... + return op; + } + + Note that in C++, the use of the new operator usually implies that + the 1st step is performed automatically for you, so in a C++ class + constructor you would start directly with PyObject_Init/InitVar +*/ + +/* + * Garbage Collection Support + * ========================== + */ + +/* C equivalent of gc.collect(). */ +PyAPI_FUNC(Py_ssize_t) PyGC_Collect(void); + +/* Test if a type has a GC head */ +#define PyType_IS_GC(t) PyType_HasFeature((t), Py_TPFLAGS_HAVE_GC) + +/* Test if an object has a GC head */ +#define PyObject_IS_GC(o) (PyType_IS_GC(Py_TYPE(o)) && \ + (Py_TYPE(o)->tp_is_gc == NULL || Py_TYPE(o)->tp_is_gc(o))) + +PyAPI_FUNC(PyVarObject *) _PyObject_GC_Resize(PyVarObject *, Py_ssize_t); +#define PyObject_GC_Resize(type, op, n) \ + ( (type *) _PyObject_GC_Resize((PyVarObject *)(op), (n)) ) + +/* for source compatibility with 2.2 */ +#define _PyObject_GC_Del PyObject_GC_Del + +/* GC information is stored BEFORE the object structure. */ +typedef union _gc_head { + struct { + union _gc_head *gc_next; + union _gc_head *gc_prev; + Py_ssize_t gc_refs; + } gc; + long double dummy; /* force worst-case alignment */ +} PyGC_Head; + +extern PyGC_Head *_PyGC_generation0; + +#define _Py_AS_GC(o) ((PyGC_Head *)(o)-1) + +#define _PyGC_REFS_UNTRACKED (-2) +#define _PyGC_REFS_REACHABLE (-3) +#define _PyGC_REFS_TENTATIVELY_UNREACHABLE (-4) + +/* Tell the GC to track this object. NB: While the object is tracked the + * collector it must be safe to call the ob_traverse method. */ +#define _PyObject_GC_TRACK(o) do { \ + PyGC_Head *g = _Py_AS_GC(o); \ + if (g->gc.gc_refs != _PyGC_REFS_UNTRACKED) \ + Py_FatalError("GC object already tracked"); \ + g->gc.gc_refs = _PyGC_REFS_REACHABLE; \ + g->gc.gc_next = _PyGC_generation0; \ + g->gc.gc_prev = _PyGC_generation0->gc.gc_prev; \ + g->gc.gc_prev->gc.gc_next = g; \ + _PyGC_generation0->gc.gc_prev = g; \ + } while (0); + +/* Tell the GC to stop tracking this object. + * gc_next doesn't need to be set to NULL, but doing so is a good + * way to provoke memory errors if calling code is confused. + */ +#define _PyObject_GC_UNTRACK(o) do { \ + PyGC_Head *g = _Py_AS_GC(o); \ + assert(g->gc.gc_refs != _PyGC_REFS_UNTRACKED); \ + g->gc.gc_refs = _PyGC_REFS_UNTRACKED; \ + g->gc.gc_prev->gc.gc_next = g->gc.gc_next; \ + g->gc.gc_next->gc.gc_prev = g->gc.gc_prev; \ + g->gc.gc_next = NULL; \ + } while (0); + +/* True if the object is currently tracked by the GC. */ +#define _PyObject_GC_IS_TRACKED(o) \ + ((_Py_AS_GC(o))->gc.gc_refs != _PyGC_REFS_UNTRACKED) + +/* True if the object may be tracked by the GC in the future, or already is. + This can be useful to implement some optimizations. */ +#define _PyObject_GC_MAY_BE_TRACKED(obj) \ + (PyObject_IS_GC(obj) && \ + (!PyTuple_CheckExact(obj) || _PyObject_GC_IS_TRACKED(obj))) + + +PyAPI_FUNC(PyObject *) _PyObject_GC_Malloc(size_t); +PyAPI_FUNC(PyObject *) _PyObject_GC_New(PyTypeObject *); +PyAPI_FUNC(PyVarObject *) _PyObject_GC_NewVar(PyTypeObject *, Py_ssize_t); +PyAPI_FUNC(void) PyObject_GC_Track(void *); +PyAPI_FUNC(void) PyObject_GC_UnTrack(void *); +PyAPI_FUNC(void) PyObject_GC_Del(void *); + +#define PyObject_GC_New(type, typeobj) \ + ( (type *) _PyObject_GC_New(typeobj) ) +#define PyObject_GC_NewVar(type, typeobj, n) \ + ( (type *) _PyObject_GC_NewVar((typeobj), (n)) ) + + +/* Utility macro to help write tp_traverse functions. + * To use this macro, the tp_traverse function must name its arguments + * "visit" and "arg". This is intended to keep tp_traverse functions + * looking as much alike as possible. + */ +#define Py_VISIT(op) \ + do { \ + if (op) { \ + int vret = visit((PyObject *)(op), arg); \ + if (vret) \ + return vret; \ + } \ + } while (0) + +/* This is here for the sake of backwards compatibility. Extensions that + * use the old GC API will still compile but the objects will not be + * tracked by the GC. */ +#define PyGC_HEAD_SIZE 0 +#define PyObject_GC_Init(op) +#define PyObject_GC_Fini(op) +#define PyObject_AS_GC(op) (op) +#define PyObject_FROM_GC(op) (op) + + +/* Test if a type supports weak references */ +#define PyType_SUPPORTS_WEAKREFS(t) \ + (PyType_HasFeature((t), Py_TPFLAGS_HAVE_WEAKREFS) \ + && ((t)->tp_weaklistoffset > 0)) + +#define PyObject_GET_WEAKREFS_LISTPTR(o) \ + ((PyObject **) (((char *) (o)) + Py_TYPE(o)->tp_weaklistoffset)) + +#ifdef __cplusplus +} +#endif +#endif /* !Py_OBJIMPL_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/opcode.h b/AppPkg/Applications/Python/Python-2.7.10/Include/opcode.h new file mode 100644 index 0000000000..fe2a690305 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/opcode.h @@ -0,0 +1,162 @@ +#ifndef Py_OPCODE_H +#define Py_OPCODE_H +#ifdef __cplusplus +extern "C" { +#endif + + +/* Instruction opcodes for compiled code */ + +#define STOP_CODE 0 +#define POP_TOP 1 +#define ROT_TWO 2 +#define ROT_THREE 3 +#define DUP_TOP 4 +#define ROT_FOUR 5 +#define NOP 9 + +#define UNARY_POSITIVE 10 +#define UNARY_NEGATIVE 11 +#define UNARY_NOT 12 +#define UNARY_CONVERT 13 + +#define UNARY_INVERT 15 + +#define BINARY_POWER 19 + +#define BINARY_MULTIPLY 20 +#define BINARY_DIVIDE 21 +#define BINARY_MODULO 22 +#define BINARY_ADD 23 +#define BINARY_SUBTRACT 24 +#define BINARY_SUBSCR 25 +#define BINARY_FLOOR_DIVIDE 26 +#define BINARY_TRUE_DIVIDE 27 +#define INPLACE_FLOOR_DIVIDE 28 +#define INPLACE_TRUE_DIVIDE 29 + +#define SLICE 30 +/* Also uses 31-33 */ + +#define STORE_SLICE 40 +/* Also uses 41-43 */ + +#define DELETE_SLICE 50 +/* Also uses 51-53 */ + +#define STORE_MAP 54 +#define INPLACE_ADD 55 +#define INPLACE_SUBTRACT 56 +#define INPLACE_MULTIPLY 57 +#define INPLACE_DIVIDE 58 +#define INPLACE_MODULO 59 +#define STORE_SUBSCR 60 +#define DELETE_SUBSCR 61 + +#define BINARY_LSHIFT 62 +#define BINARY_RSHIFT 63 +#define BINARY_AND 64 +#define BINARY_XOR 65 +#define BINARY_OR 66 +#define INPLACE_POWER 67 +#define GET_ITER 68 + +#define PRINT_EXPR 70 +#define PRINT_ITEM 71 +#define PRINT_NEWLINE 72 +#define PRINT_ITEM_TO 73 +#define PRINT_NEWLINE_TO 74 +#define INPLACE_LSHIFT 75 +#define INPLACE_RSHIFT 76 +#define INPLACE_AND 77 +#define INPLACE_XOR 78 +#define INPLACE_OR 79 +#define BREAK_LOOP 80 +#define WITH_CLEANUP 81 +#define LOAD_LOCALS 82 +#define RETURN_VALUE 83 +#define IMPORT_STAR 84 +#define EXEC_STMT 85 +#define YIELD_VALUE 86 +#define POP_BLOCK 87 +#define END_FINALLY 88 +#define BUILD_CLASS 89 + +#define HAVE_ARGUMENT 90 /* Opcodes from here have an argument: */ + +#define STORE_NAME 90 /* Index in name list */ +#define DELETE_NAME 91 /* "" */ +#define UNPACK_SEQUENCE 92 /* Number of sequence items */ +#define FOR_ITER 93 +#define LIST_APPEND 94 + +#define STORE_ATTR 95 /* Index in name list */ +#define DELETE_ATTR 96 /* "" */ +#define STORE_GLOBAL 97 /* "" */ +#define DELETE_GLOBAL 98 /* "" */ +#define DUP_TOPX 99 /* number of items to duplicate */ +#define LOAD_CONST 100 /* Index in const list */ +#define LOAD_NAME 101 /* Index in name list */ +#define BUILD_TUPLE 102 /* Number of tuple items */ +#define BUILD_LIST 103 /* Number of list items */ +#define BUILD_SET 104 /* Number of set items */ +#define BUILD_MAP 105 /* Always zero for now */ +#define LOAD_ATTR 106 /* Index in name list */ +#define COMPARE_OP 107 /* Comparison operator */ +#define IMPORT_NAME 108 /* Index in name list */ +#define IMPORT_FROM 109 /* Index in name list */ +#define JUMP_FORWARD 110 /* Number of bytes to skip */ + +#define JUMP_IF_FALSE_OR_POP 111 /* Target byte offset from beginning + of code */ +#define JUMP_IF_TRUE_OR_POP 112 /* "" */ +#define JUMP_ABSOLUTE 113 /* "" */ +#define POP_JUMP_IF_FALSE 114 /* "" */ +#define POP_JUMP_IF_TRUE 115 /* "" */ + +#define LOAD_GLOBAL 116 /* Index in name list */ + +#define CONTINUE_LOOP 119 /* Start of loop (absolute) */ +#define SETUP_LOOP 120 /* Target address (relative) */ +#define SETUP_EXCEPT 121 /* "" */ +#define SETUP_FINALLY 122 /* "" */ + +#define LOAD_FAST 124 /* Local variable number */ +#define STORE_FAST 125 /* Local variable number */ +#define DELETE_FAST 126 /* Local variable number */ + +#define RAISE_VARARGS 130 /* Number of raise arguments (1, 2 or 3) */ +/* CALL_FUNCTION_XXX opcodes defined below depend on this definition */ +#define CALL_FUNCTION 131 /* #args + (#kwargs<<8) */ +#define MAKE_FUNCTION 132 /* #defaults */ +#define BUILD_SLICE 133 /* Number of items */ + +#define MAKE_CLOSURE 134 /* #free vars */ +#define LOAD_CLOSURE 135 /* Load free variable from closure */ +#define LOAD_DEREF 136 /* Load and dereference from closure cell */ +#define STORE_DEREF 137 /* Store into cell */ + +/* The next 3 opcodes must be contiguous and satisfy + (CALL_FUNCTION_VAR - CALL_FUNCTION) & 3 == 1 */ +#define CALL_FUNCTION_VAR 140 /* #args + (#kwargs<<8) */ +#define CALL_FUNCTION_KW 141 /* #args + (#kwargs<<8) */ +#define CALL_FUNCTION_VAR_KW 142 /* #args + (#kwargs<<8) */ + +#define SETUP_WITH 143 + +/* Support for opargs more than 16 bits long */ +#define EXTENDED_ARG 145 + +#define SET_ADD 146 +#define MAP_ADD 147 + + +enum cmp_op {PyCmp_LT=Py_LT, PyCmp_LE=Py_LE, PyCmp_EQ=Py_EQ, PyCmp_NE=Py_NE, PyCmp_GT=Py_GT, PyCmp_GE=Py_GE, + PyCmp_IN, PyCmp_NOT_IN, PyCmp_IS, PyCmp_IS_NOT, PyCmp_EXC_MATCH, PyCmp_BAD}; + +#define HAS_ARG(op) ((op) >= HAVE_ARGUMENT) + +#ifdef __cplusplus +} +#endif +#endif /* !Py_OPCODE_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/osdefs.h b/AppPkg/Applications/Python/Python-2.7.10/Include/osdefs.h new file mode 100644 index 0000000000..d41ea14b32 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/osdefs.h @@ -0,0 +1,63 @@ +#ifndef Py_OSDEFS_H +#define Py_OSDEFS_H +#ifdef __cplusplus +extern "C" { +#endif + + +/* Operating system dependencies */ + +/* Mod by chrish: QNX has WATCOM, but isn't DOS */ +#if !defined(__QNX__) +#if defined(MS_WINDOWS) || defined(__BORLANDC__) || defined(__WATCOMC__) || defined(__DJGPP__) || defined(PYOS_OS2) +#if defined(PYOS_OS2) && defined(PYCC_GCC) +#define MAXPATHLEN 260 +#define SEP '/' +#define ALTSEP '\\' +#else +#define SEP '\\' +#define ALTSEP '/' +#define MAXPATHLEN 256 +#endif +#define DELIM ';' +#endif +#endif + +#ifdef RISCOS +#define SEP '.' +#define MAXPATHLEN 256 +#define DELIM ',' +#endif + + +/* Filename separator */ +#ifndef SEP +#define SEP '/' +#endif + +/* Max pathname length */ +#ifdef __hpux +#include +#include +#ifndef PATH_MAX +#define PATH_MAX MAXPATHLEN +#endif +#endif + +#ifndef MAXPATHLEN +#if defined(PATH_MAX) && PATH_MAX > 1024 +#define MAXPATHLEN PATH_MAX +#else +#define MAXPATHLEN 1024 +#endif +#endif + +/* Search path entry delimiter */ +#ifndef DELIM +#define DELIM ':' +#endif + +#ifdef __cplusplus +} +#endif +#endif /* !Py_OSDEFS_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/parsetok.h b/AppPkg/Applications/Python/Python-2.7.10/Include/parsetok.h new file mode 100644 index 0000000000..915bdba234 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/parsetok.h @@ -0,0 +1,64 @@ + +/* Parser-tokenizer link interface */ + +#ifndef Py_PARSETOK_H +#define Py_PARSETOK_H +#ifdef __cplusplus +extern "C" { +#endif + +typedef struct { + int error; + const char *filename; + int lineno; + int offset; + char *text; + int token; + int expected; +} perrdetail; + +#if 0 +#define PyPARSE_YIELD_IS_KEYWORD 0x0001 +#endif + +#define PyPARSE_DONT_IMPLY_DEDENT 0x0002 + +#if 0 +#define PyPARSE_WITH_IS_KEYWORD 0x0003 +#endif + +#define PyPARSE_PRINT_IS_FUNCTION 0x0004 +#define PyPARSE_UNICODE_LITERALS 0x0008 + + + +PyAPI_FUNC(node *) PyParser_ParseString(const char *, grammar *, int, + perrdetail *); +PyAPI_FUNC(node *) PyParser_ParseFile (FILE *, const char *, grammar *, int, + char *, char *, perrdetail *); + +PyAPI_FUNC(node *) PyParser_ParseStringFlags(const char *, grammar *, int, + perrdetail *, int); +PyAPI_FUNC(node *) PyParser_ParseFileFlags(FILE *, const char *, grammar *, + int, char *, char *, + perrdetail *, int); +PyAPI_FUNC(node *) PyParser_ParseFileFlagsEx(FILE *, const char *, grammar *, + int, char *, char *, + perrdetail *, int *); + +PyAPI_FUNC(node *) PyParser_ParseStringFlagsFilename(const char *, + const char *, + grammar *, int, + perrdetail *, int); +PyAPI_FUNC(node *) PyParser_ParseStringFlagsFilenameEx(const char *, + const char *, + grammar *, int, + perrdetail *, int *); + +/* Note that he following function is defined in pythonrun.c not parsetok.c. */ +PyAPI_FUNC(void) PyParser_SetError(perrdetail *); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_PARSETOK_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/patchlevel.h b/AppPkg/Applications/Python/Python-2.7.10/Include/patchlevel.h new file mode 100644 index 0000000000..6b17d28858 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/patchlevel.h @@ -0,0 +1,43 @@ + +/* Newfangled version identification scheme. + + This scheme was added in Python 1.5.2b2; before that time, only PATCHLEVEL + was available. To test for presence of the scheme, test for + defined(PY_MAJOR_VERSION). + + When the major or minor version changes, the VERSION variable in + configure.ac must also be changed. + + There is also (independent) API version information in modsupport.h. +*/ + +/* Values for PY_RELEASE_LEVEL */ +#define PY_RELEASE_LEVEL_ALPHA 0xA +#define PY_RELEASE_LEVEL_BETA 0xB +#define PY_RELEASE_LEVEL_GAMMA 0xC /* For release candidates */ +#define PY_RELEASE_LEVEL_FINAL 0xF /* Serial should be 0 here */ + /* Higher for patch releases */ + +/* Version parsed out into numeric values */ +/*--start constants--*/ +#define PY_MAJOR_VERSION 2 +#define PY_MINOR_VERSION 7 +#define PY_MICRO_VERSION 10 +#define PY_RELEASE_LEVEL PY_RELEASE_LEVEL_FINAL +#define PY_RELEASE_SERIAL 0 + +/* Version as a string */ +#define PY_VERSION "2.7.10" +/*--end constants--*/ + +/* Subversion Revision number of this file (not of the repository). Empty + since Mercurial migration. */ +#define PY_PATCHLEVEL_REVISION "" + +/* Version as a single 4-byte hex number, e.g. 0x010502B2 == 1.5.2b2. + Use this for numeric comparisons, e.g. #if PY_VERSION_HEX >= ... */ +#define PY_VERSION_HEX ((PY_MAJOR_VERSION << 24) | \ + (PY_MINOR_VERSION << 16) | \ + (PY_MICRO_VERSION << 8) | \ + (PY_RELEASE_LEVEL << 4) | \ + (PY_RELEASE_SERIAL << 0)) diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/pgen.h b/AppPkg/Applications/Python/Python-2.7.10/Include/pgen.h new file mode 100644 index 0000000000..af84852b39 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/pgen.h @@ -0,0 +1,18 @@ +#ifndef Py_PGEN_H +#define Py_PGEN_H +#ifdef __cplusplus +extern "C" { +#endif + + +/* Parser generator interface */ + +extern grammar *meta_grammar(void); + +struct _node; +extern grammar *pgen(struct _node *); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_PGEN_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/pgenheaders.h b/AppPkg/Applications/Python/Python-2.7.10/Include/pgenheaders.h new file mode 100644 index 0000000000..7aac4e2b6a --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/pgenheaders.h @@ -0,0 +1,42 @@ +#ifndef Py_PGENHEADERS_H +#define Py_PGENHEADERS_H +#ifdef __cplusplus +extern "C" { +#endif + + +/* Include files and extern declarations used by most of the parser. */ + +#include "Python.h" + +PyAPI_FUNC(void) PySys_WriteStdout(const char *format, ...) + Py_GCC_ATTRIBUTE((format(printf, 1, 2))); +PyAPI_FUNC(void) PySys_WriteStderr(const char *format, ...) + Py_GCC_ATTRIBUTE((format(printf, 1, 2))); + +#define addarc _Py_addarc +#define addbit _Py_addbit +#define adddfa _Py_adddfa +#define addfirstsets _Py_addfirstsets +#define addlabel _Py_addlabel +#define addstate _Py_addstate +#define delbitset _Py_delbitset +#define dumptree _Py_dumptree +#define findlabel _Py_findlabel +#define mergebitset _Py_mergebitset +#define meta_grammar _Py_meta_grammar +#define newbitset _Py_newbitset +#define newgrammar _Py_newgrammar +#define pgen _Py_pgen +#define printgrammar _Py_printgrammar +#define printnonterminals _Py_printnonterminals +#define printtree _Py_printtree +#define samebitset _Py_samebitset +#define showtree _Py_showtree +#define tok_dump _Py_tok_dump +#define translatelabels _Py_translatelabels + +#ifdef __cplusplus +} +#endif +#endif /* !Py_PGENHEADERS_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/py_curses.h b/AppPkg/Applications/Python/Python-2.7.10/Include/py_curses.h new file mode 100644 index 0000000000..212060735b --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/py_curses.h @@ -0,0 +1,176 @@ + +#ifndef Py_CURSES_H +#define Py_CURSES_H + +#ifdef __APPLE__ +/* +** On Mac OS X 10.2 [n]curses.h and stdlib.h use different guards +** against multiple definition of wchar_t. +*/ +#ifdef _BSD_WCHAR_T_DEFINED_ +#define _WCHAR_T +#endif + +/* the following define is necessary for OS X 10.6; without it, the + Apple-supplied ncurses.h sets NCURSES_OPAQUE to 1, and then Python + can't get at the WINDOW flags field. */ +#define NCURSES_OPAQUE 0 +#endif /* __APPLE__ */ + +#ifdef __FreeBSD__ +/* +** On FreeBSD, [n]curses.h and stdlib.h/wchar.h use different guards +** against multiple definition of wchar_t and wint_t. +*/ +#ifdef _XOPEN_SOURCE_EXTENDED +#ifndef __FreeBSD_version +#include +#endif +#if __FreeBSD_version >= 500000 +#ifndef __wchar_t +#define __wchar_t +#endif +#ifndef __wint_t +#define __wint_t +#endif +#else +#ifndef _WCHAR_T +#define _WCHAR_T +#endif +#ifndef _WINT_T +#define _WINT_T +#endif +#endif +#endif +#endif + +#ifdef HAVE_NCURSES_H +#include +#else +#include +#ifdef HAVE_TERM_H +/* for tigetstr, which is not declared in SysV curses */ +#include +#endif +#endif + +#ifdef HAVE_NCURSES_H +/* configure was checking , but we will + use , which has all these features. */ +#ifndef WINDOW_HAS_FLAGS +#define WINDOW_HAS_FLAGS 1 +#endif +#ifndef MVWDELCH_IS_EXPRESSION +#define MVWDELCH_IS_EXPRESSION 1 +#endif +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +#define PyCurses_API_pointers 4 + +/* Type declarations */ + +typedef struct { + PyObject_HEAD + WINDOW *win; +} PyCursesWindowObject; + +#define PyCursesWindow_Check(v) (Py_TYPE(v) == &PyCursesWindow_Type) + +#define PyCurses_CAPSULE_NAME "_curses._C_API" + + +#ifdef CURSES_MODULE +/* This section is used when compiling _cursesmodule.c */ + +#else +/* This section is used in modules that use the _cursesmodule API */ + +static void **PyCurses_API; + +#define PyCursesWindow_Type (*(PyTypeObject *) PyCurses_API[0]) +#define PyCursesSetupTermCalled {if (! ((int (*)(void))PyCurses_API[1]) () ) return NULL;} +#define PyCursesInitialised {if (! ((int (*)(void))PyCurses_API[2]) () ) return NULL;} +#define PyCursesInitialisedColor {if (! ((int (*)(void))PyCurses_API[3]) () ) return NULL;} + +#define import_curses() \ + PyCurses_API = (void **)PyCapsule_Import(PyCurses_CAPSULE_NAME, 1); + +#endif + +/* general error messages */ +static char *catchall_ERR = "curses function returned ERR"; +static char *catchall_NULL = "curses function returned NULL"; + +/* Function Prototype Macros - They are ugly but very, very useful. ;-) + + X - function name + TYPE - parameter Type + ERGSTR - format string for construction of the return value + PARSESTR - format string for argument parsing + */ + +#define NoArgNoReturnFunction(X) \ +static PyObject *PyCurses_ ## X (PyObject *self) \ +{ \ + PyCursesInitialised \ + return PyCursesCheckERR(X(), # X); } + +#define NoArgOrFlagNoReturnFunction(X) \ +static PyObject *PyCurses_ ## X (PyObject *self, PyObject *args) \ +{ \ + int flag = 0; \ + PyCursesInitialised \ + switch(PyTuple_Size(args)) { \ + case 0: \ + return PyCursesCheckERR(X(), # X); \ + case 1: \ + if (!PyArg_ParseTuple(args, "i;True(1) or False(0)", &flag)) return NULL; \ + if (flag) return PyCursesCheckERR(X(), # X); \ + else return PyCursesCheckERR(no ## X (), # X); \ + default: \ + PyErr_SetString(PyExc_TypeError, # X " requires 0 or 1 arguments"); \ + return NULL; } } + +#define NoArgReturnIntFunction(X) \ +static PyObject *PyCurses_ ## X (PyObject *self) \ +{ \ + PyCursesInitialised \ + return PyInt_FromLong((long) X()); } + + +#define NoArgReturnStringFunction(X) \ +static PyObject *PyCurses_ ## X (PyObject *self) \ +{ \ + PyCursesInitialised \ + return PyString_FromString(X()); } + +#define NoArgTrueFalseFunction(X) \ +static PyObject *PyCurses_ ## X (PyObject *self) \ +{ \ + PyCursesInitialised \ + if (X () == FALSE) { \ + Py_INCREF(Py_False); \ + return Py_False; \ + } \ + Py_INCREF(Py_True); \ + return Py_True; } + +#define NoArgNoReturnVoidFunction(X) \ +static PyObject *PyCurses_ ## X (PyObject *self) \ +{ \ + PyCursesInitialised \ + X(); \ + Py_INCREF(Py_None); \ + return Py_None; } + +#ifdef __cplusplus +} +#endif + +#endif /* !defined(Py_CURSES_H) */ + + diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/pyarena.h b/AppPkg/Applications/Python/Python-2.7.10/Include/pyarena.h new file mode 100644 index 0000000000..fec1afa820 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/pyarena.h @@ -0,0 +1,62 @@ +/* An arena-like memory interface for the compiler. + */ + +#ifndef Py_PYARENA_H +#define Py_PYARENA_H + +#ifdef __cplusplus +extern "C" { +#endif + + typedef struct _arena PyArena; + + /* PyArena_New() and PyArena_Free() create a new arena and free it, + respectively. Once an arena has been created, it can be used + to allocate memory via PyArena_Malloc(). Pointers to PyObject can + also be registered with the arena via PyArena_AddPyObject(), and the + arena will ensure that the PyObjects stay alive at least until + PyArena_Free() is called. When an arena is freed, all the memory it + allocated is freed, the arena releases internal references to registered + PyObject*, and none of its pointers are valid. + XXX (tim) What does "none of its pointers are valid" mean? Does it + XXX mean that pointers previously obtained via PyArena_Malloc() are + XXX no longer valid? (That's clearly true, but not sure that's what + XXX the text is trying to say.) + + PyArena_New() returns an arena pointer. On error, it + returns a negative number and sets an exception. + XXX (tim): Not true. On error, PyArena_New() actually returns NULL, + XXX and looks like it may or may not set an exception (e.g., if the + XXX internal PyList_New(0) returns NULL, PyArena_New() passes that on + XXX and an exception is set; OTOH, if the internal + XXX block_new(DEFAULT_BLOCK_SIZE) returns NULL, that's passed on but + XXX an exception is not set in that case). + */ + PyAPI_FUNC(PyArena *) PyArena_New(void); + PyAPI_FUNC(void) PyArena_Free(PyArena *); + + /* Mostly like malloc(), return the address of a block of memory spanning + * `size` bytes, or return NULL (without setting an exception) if enough + * new memory can't be obtained. Unlike malloc(0), PyArena_Malloc() with + * size=0 does not guarantee to return a unique pointer (the pointer + * returned may equal one or more other pointers obtained from + * PyArena_Malloc()). + * Note that pointers obtained via PyArena_Malloc() must never be passed to + * the system free() or realloc(), or to any of Python's similar memory- + * management functions. PyArena_Malloc()-obtained pointers remain valid + * until PyArena_Free(ar) is called, at which point all pointers obtained + * from the arena `ar` become invalid simultaneously. + */ + PyAPI_FUNC(void *) PyArena_Malloc(PyArena *, size_t size); + + /* This routine isn't a proper arena allocation routine. It takes + * a PyObject* and records it so that it can be DECREFed when the + * arena is freed. + */ + PyAPI_FUNC(int) PyArena_AddPyObject(PyArena *, PyObject *); + +#ifdef __cplusplus +} +#endif + +#endif /* !Py_PYARENA_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/pycapsule.h b/AppPkg/Applications/Python/Python-2.7.10/Include/pycapsule.h new file mode 100644 index 0000000000..d4144350b3 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/pycapsule.h @@ -0,0 +1,56 @@ + +/* Capsule objects let you wrap a C "void *" pointer in a Python + object. They're a way of passing data through the Python interpreter + without creating your own custom type. + + Capsules are used for communication between extension modules. + They provide a way for an extension module to export a C interface + to other extension modules, so that extension modules can use the + Python import mechanism to link to one another. + + For more information, please see "c-api/capsule.html" in the + documentation. +*/ + +#ifndef Py_CAPSULE_H +#define Py_CAPSULE_H +#ifdef __cplusplus +extern "C" { +#endif + +PyAPI_DATA(PyTypeObject) PyCapsule_Type; + +typedef void (*PyCapsule_Destructor)(PyObject *); + +#define PyCapsule_CheckExact(op) (Py_TYPE(op) == &PyCapsule_Type) + + +PyAPI_FUNC(PyObject *) PyCapsule_New( + void *pointer, + const char *name, + PyCapsule_Destructor destructor); + +PyAPI_FUNC(void *) PyCapsule_GetPointer(PyObject *capsule, const char *name); + +PyAPI_FUNC(PyCapsule_Destructor) PyCapsule_GetDestructor(PyObject *capsule); + +PyAPI_FUNC(const char *) PyCapsule_GetName(PyObject *capsule); + +PyAPI_FUNC(void *) PyCapsule_GetContext(PyObject *capsule); + +PyAPI_FUNC(int) PyCapsule_IsValid(PyObject *capsule, const char *name); + +PyAPI_FUNC(int) PyCapsule_SetPointer(PyObject *capsule, void *pointer); + +PyAPI_FUNC(int) PyCapsule_SetDestructor(PyObject *capsule, PyCapsule_Destructor destructor); + +PyAPI_FUNC(int) PyCapsule_SetName(PyObject *capsule, const char *name); + +PyAPI_FUNC(int) PyCapsule_SetContext(PyObject *capsule, void *context); + +PyAPI_FUNC(void *) PyCapsule_Import(const char *name, int no_block); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_CAPSULE_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/pyctype.h b/AppPkg/Applications/Python/Python-2.7.10/Include/pyctype.h new file mode 100644 index 0000000000..e28542ac4a --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/pyctype.h @@ -0,0 +1,31 @@ +#ifndef PYCTYPE_H +#define PYCTYPE_H + +#define PY_CTF_LOWER 0x01 +#define PY_CTF_UPPER 0x02 +#define PY_CTF_ALPHA (PY_CTF_LOWER|PY_CTF_UPPER) +#define PY_CTF_DIGIT 0x04 +#define PY_CTF_ALNUM (PY_CTF_ALPHA|PY_CTF_DIGIT) +#define PY_CTF_SPACE 0x08 +#define PY_CTF_XDIGIT 0x10 + +PyAPI_DATA(const unsigned int) _Py_ctype_table[256]; + +/* Unlike their C counterparts, the following macros are not meant to + * handle an int with any of the values [EOF, 0-UCHAR_MAX]. The argument + * must be a signed/unsigned char. */ +#define Py_ISLOWER(c) (_Py_ctype_table[Py_CHARMASK(c)] & PY_CTF_LOWER) +#define Py_ISUPPER(c) (_Py_ctype_table[Py_CHARMASK(c)] & PY_CTF_UPPER) +#define Py_ISALPHA(c) (_Py_ctype_table[Py_CHARMASK(c)] & PY_CTF_ALPHA) +#define Py_ISDIGIT(c) (_Py_ctype_table[Py_CHARMASK(c)] & PY_CTF_DIGIT) +#define Py_ISXDIGIT(c) (_Py_ctype_table[Py_CHARMASK(c)] & PY_CTF_XDIGIT) +#define Py_ISALNUM(c) (_Py_ctype_table[Py_CHARMASK(c)] & PY_CTF_ALNUM) +#define Py_ISSPACE(c) (_Py_ctype_table[Py_CHARMASK(c)] & PY_CTF_SPACE) + +PyAPI_DATA(const unsigned char) _Py_ctype_tolower[256]; +PyAPI_DATA(const unsigned char) _Py_ctype_toupper[256]; + +#define Py_TOLOWER(c) (_Py_ctype_tolower[Py_CHARMASK(c)]) +#define Py_TOUPPER(c) (_Py_ctype_toupper[Py_CHARMASK(c)]) + +#endif /* !PYCTYPE_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/pydebug.h b/AppPkg/Applications/Python/Python-2.7.10/Include/pydebug.h new file mode 100644 index 0000000000..9f719e1d35 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/pydebug.h @@ -0,0 +1,41 @@ + +#ifndef Py_PYDEBUG_H +#define Py_PYDEBUG_H +#ifdef __cplusplus +extern "C" { +#endif + +PyAPI_DATA(int) Py_DebugFlag; +PyAPI_DATA(int) Py_VerboseFlag; +PyAPI_DATA(int) Py_InteractiveFlag; +PyAPI_DATA(int) Py_InspectFlag; +PyAPI_DATA(int) Py_OptimizeFlag; +PyAPI_DATA(int) Py_NoSiteFlag; +PyAPI_DATA(int) Py_BytesWarningFlag; +PyAPI_DATA(int) Py_UseClassExceptionsFlag; +PyAPI_DATA(int) Py_FrozenFlag; +PyAPI_DATA(int) Py_TabcheckFlag; +PyAPI_DATA(int) Py_UnicodeFlag; +PyAPI_DATA(int) Py_IgnoreEnvironmentFlag; +PyAPI_DATA(int) Py_DivisionWarningFlag; +PyAPI_DATA(int) Py_DontWriteBytecodeFlag; +PyAPI_DATA(int) Py_NoUserSiteDirectory; +/* _XXX Py_QnewFlag should go away in 3.0. It's true iff -Qnew is passed, + on the command line, and is used in 2.2 by ceval.c to make all "/" divisions + true divisions (which they will be in 3.0). */ +PyAPI_DATA(int) _Py_QnewFlag; +/* Warn about 3.x issues */ +PyAPI_DATA(int) Py_Py3kWarningFlag; +PyAPI_DATA(int) Py_HashRandomizationFlag; + +/* this is a wrapper around getenv() that pays attention to + Py_IgnoreEnvironmentFlag. It should be used for getting variables like + PYTHONPATH and PYTHONHOME from the environment */ +#define Py_GETENV(s) (Py_IgnoreEnvironmentFlag ? NULL : getenv(s)) + +PyAPI_FUNC(void) Py_FatalError(const char *message); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_PYDEBUG_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/pyerrors.h b/AppPkg/Applications/Python/Python-2.7.10/Include/pyerrors.h new file mode 100644 index 0000000000..a703345144 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/pyerrors.h @@ -0,0 +1,329 @@ +#ifndef Py_ERRORS_H +#define Py_ERRORS_H +#ifdef __cplusplus +extern "C" { +#endif + +/* Error objects */ + +typedef struct { + PyObject_HEAD + PyObject *dict; + PyObject *args; + PyObject *message; +} PyBaseExceptionObject; + +typedef struct { + PyObject_HEAD + PyObject *dict; + PyObject *args; + PyObject *message; + PyObject *msg; + PyObject *filename; + PyObject *lineno; + PyObject *offset; + PyObject *text; + PyObject *print_file_and_line; +} PySyntaxErrorObject; + +#ifdef Py_USING_UNICODE +typedef struct { + PyObject_HEAD + PyObject *dict; + PyObject *args; + PyObject *message; + PyObject *encoding; + PyObject *object; + Py_ssize_t start; + Py_ssize_t end; + PyObject *reason; +} PyUnicodeErrorObject; +#endif + +typedef struct { + PyObject_HEAD + PyObject *dict; + PyObject *args; + PyObject *message; + PyObject *code; +} PySystemExitObject; + +typedef struct { + PyObject_HEAD + PyObject *dict; + PyObject *args; + PyObject *message; + PyObject *myerrno; + PyObject *strerror; + PyObject *filename; +} PyEnvironmentErrorObject; + +#ifdef MS_WINDOWS +typedef struct { + PyObject_HEAD + PyObject *dict; + PyObject *args; + PyObject *message; + PyObject *myerrno; + PyObject *strerror; + PyObject *filename; + PyObject *winerror; +} PyWindowsErrorObject; +#endif + +/* Error handling definitions */ + +PyAPI_FUNC(void) PyErr_SetNone(PyObject *); +PyAPI_FUNC(void) PyErr_SetObject(PyObject *, PyObject *); +PyAPI_FUNC(void) PyErr_SetString(PyObject *, const char *); +PyAPI_FUNC(PyObject *) PyErr_Occurred(void); +PyAPI_FUNC(void) PyErr_Clear(void); +PyAPI_FUNC(void) PyErr_Fetch(PyObject **, PyObject **, PyObject **); +PyAPI_FUNC(void) PyErr_Restore(PyObject *, PyObject *, PyObject *); + +#ifdef Py_DEBUG +#define _PyErr_OCCURRED() PyErr_Occurred() +#else +#define _PyErr_OCCURRED() (_PyThreadState_Current->curexc_type) +#endif + +/* Error testing and normalization */ +PyAPI_FUNC(int) PyErr_GivenExceptionMatches(PyObject *, PyObject *); +PyAPI_FUNC(int) PyErr_ExceptionMatches(PyObject *); +PyAPI_FUNC(void) PyErr_NormalizeException(PyObject**, PyObject**, PyObject**); +PyAPI_FUNC(void) _PyErr_ReplaceException(PyObject *, PyObject *, PyObject *); + +/* */ + +#define PyExceptionClass_Check(x) \ + (PyClass_Check((x)) || (PyType_Check((x)) && \ + PyType_FastSubclass((PyTypeObject*)(x), Py_TPFLAGS_BASE_EXC_SUBCLASS))) + +#define PyExceptionInstance_Check(x) \ + (PyInstance_Check((x)) || \ + PyType_FastSubclass((x)->ob_type, Py_TPFLAGS_BASE_EXC_SUBCLASS)) + +#define PyExceptionClass_Name(x) \ + (PyClass_Check((x)) \ + ? PyString_AS_STRING(((PyClassObject*)(x))->cl_name) \ + : (char *)(((PyTypeObject*)(x))->tp_name)) + +#define PyExceptionInstance_Class(x) \ + ((PyInstance_Check((x)) \ + ? (PyObject*)((PyInstanceObject*)(x))->in_class \ + : (PyObject*)((x)->ob_type))) + + +/* Predefined exceptions */ + +PyAPI_DATA(PyObject *) PyExc_BaseException; +PyAPI_DATA(PyObject *) PyExc_Exception; +PyAPI_DATA(PyObject *) PyExc_StopIteration; +PyAPI_DATA(PyObject *) PyExc_GeneratorExit; +PyAPI_DATA(PyObject *) PyExc_StandardError; +PyAPI_DATA(PyObject *) PyExc_ArithmeticError; +PyAPI_DATA(PyObject *) PyExc_LookupError; + +PyAPI_DATA(PyObject *) PyExc_AssertionError; +PyAPI_DATA(PyObject *) PyExc_AttributeError; +PyAPI_DATA(PyObject *) PyExc_EOFError; +PyAPI_DATA(PyObject *) PyExc_FloatingPointError; +PyAPI_DATA(PyObject *) PyExc_EnvironmentError; +PyAPI_DATA(PyObject *) PyExc_IOError; +PyAPI_DATA(PyObject *) PyExc_OSError; +PyAPI_DATA(PyObject *) PyExc_ImportError; +PyAPI_DATA(PyObject *) PyExc_IndexError; +PyAPI_DATA(PyObject *) PyExc_KeyError; +PyAPI_DATA(PyObject *) PyExc_KeyboardInterrupt; +PyAPI_DATA(PyObject *) PyExc_MemoryError; +PyAPI_DATA(PyObject *) PyExc_NameError; +PyAPI_DATA(PyObject *) PyExc_OverflowError; +PyAPI_DATA(PyObject *) PyExc_RuntimeError; +PyAPI_DATA(PyObject *) PyExc_NotImplementedError; +PyAPI_DATA(PyObject *) PyExc_SyntaxError; +PyAPI_DATA(PyObject *) PyExc_IndentationError; +PyAPI_DATA(PyObject *) PyExc_TabError; +PyAPI_DATA(PyObject *) PyExc_ReferenceError; +PyAPI_DATA(PyObject *) PyExc_SystemError; +PyAPI_DATA(PyObject *) PyExc_SystemExit; +PyAPI_DATA(PyObject *) PyExc_TypeError; +PyAPI_DATA(PyObject *) PyExc_UnboundLocalError; +PyAPI_DATA(PyObject *) PyExc_UnicodeError; +PyAPI_DATA(PyObject *) PyExc_UnicodeEncodeError; +PyAPI_DATA(PyObject *) PyExc_UnicodeDecodeError; +PyAPI_DATA(PyObject *) PyExc_UnicodeTranslateError; +PyAPI_DATA(PyObject *) PyExc_ValueError; +PyAPI_DATA(PyObject *) PyExc_ZeroDivisionError; +#ifdef MS_WINDOWS +PyAPI_DATA(PyObject *) PyExc_WindowsError; +#endif +#ifdef __VMS +PyAPI_DATA(PyObject *) PyExc_VMSError; +#endif + +PyAPI_DATA(PyObject *) PyExc_BufferError; + +PyAPI_DATA(PyObject *) PyExc_MemoryErrorInst; +PyAPI_DATA(PyObject *) PyExc_RecursionErrorInst; + +/* Predefined warning categories */ +PyAPI_DATA(PyObject *) PyExc_Warning; +PyAPI_DATA(PyObject *) PyExc_UserWarning; +PyAPI_DATA(PyObject *) PyExc_DeprecationWarning; +PyAPI_DATA(PyObject *) PyExc_PendingDeprecationWarning; +PyAPI_DATA(PyObject *) PyExc_SyntaxWarning; +PyAPI_DATA(PyObject *) PyExc_RuntimeWarning; +PyAPI_DATA(PyObject *) PyExc_FutureWarning; +PyAPI_DATA(PyObject *) PyExc_ImportWarning; +PyAPI_DATA(PyObject *) PyExc_UnicodeWarning; +PyAPI_DATA(PyObject *) PyExc_BytesWarning; + + +/* Convenience functions */ + +PyAPI_FUNC(int) PyErr_BadArgument(void); +PyAPI_FUNC(PyObject *) PyErr_NoMemory(void); +PyAPI_FUNC(PyObject *) PyErr_SetFromErrno(PyObject *); +PyAPI_FUNC(PyObject *) PyErr_SetFromErrnoWithFilenameObject( + PyObject *, PyObject *); +PyAPI_FUNC(PyObject *) PyErr_SetFromErrnoWithFilename( + PyObject *, const char *); +#ifdef MS_WINDOWS +PyAPI_FUNC(PyObject *) PyErr_SetFromErrnoWithUnicodeFilename( + PyObject *, const Py_UNICODE *); +#endif /* MS_WINDOWS */ + +PyAPI_FUNC(PyObject *) PyErr_Format(PyObject *, const char *, ...) + Py_GCC_ATTRIBUTE((format(printf, 2, 3))); + +#ifdef MS_WINDOWS +PyAPI_FUNC(PyObject *) PyErr_SetFromWindowsErrWithFilenameObject( + int, const char *); +PyAPI_FUNC(PyObject *) PyErr_SetFromWindowsErrWithFilename( + int, const char *); +PyAPI_FUNC(PyObject *) PyErr_SetFromWindowsErrWithUnicodeFilename( + int, const Py_UNICODE *); +PyAPI_FUNC(PyObject *) PyErr_SetFromWindowsErr(int); +PyAPI_FUNC(PyObject *) PyErr_SetExcFromWindowsErrWithFilenameObject( + PyObject *,int, PyObject *); +PyAPI_FUNC(PyObject *) PyErr_SetExcFromWindowsErrWithFilename( + PyObject *,int, const char *); +PyAPI_FUNC(PyObject *) PyErr_SetExcFromWindowsErrWithUnicodeFilename( + PyObject *,int, const Py_UNICODE *); +PyAPI_FUNC(PyObject *) PyErr_SetExcFromWindowsErr(PyObject *, int); +#endif /* MS_WINDOWS */ + +/* Export the old function so that the existing API remains available: */ +PyAPI_FUNC(void) PyErr_BadInternalCall(void); +PyAPI_FUNC(void) _PyErr_BadInternalCall(char *filename, int lineno); +/* Mask the old API with a call to the new API for code compiled under + Python 2.0: */ +#define PyErr_BadInternalCall() _PyErr_BadInternalCall(__FILE__, __LINE__) + +/* Function to create a new exception */ +PyAPI_FUNC(PyObject *) PyErr_NewException( + char *name, PyObject *base, PyObject *dict); +PyAPI_FUNC(PyObject *) PyErr_NewExceptionWithDoc( + char *name, char *doc, PyObject *base, PyObject *dict); +PyAPI_FUNC(void) PyErr_WriteUnraisable(PyObject *); + +/* In sigcheck.c or signalmodule.c */ +PyAPI_FUNC(int) PyErr_CheckSignals(void); +PyAPI_FUNC(void) PyErr_SetInterrupt(void); + +/* In signalmodule.c */ +int PySignal_SetWakeupFd(int fd); + +/* Support for adding program text to SyntaxErrors */ +PyAPI_FUNC(void) PyErr_SyntaxLocation(const char *, int); +PyAPI_FUNC(PyObject *) PyErr_ProgramText(const char *, int); + +#ifdef Py_USING_UNICODE +/* The following functions are used to create and modify unicode + exceptions from C */ + +/* create a UnicodeDecodeError object */ +PyAPI_FUNC(PyObject *) PyUnicodeDecodeError_Create( + const char *, const char *, Py_ssize_t, Py_ssize_t, Py_ssize_t, const char *); + +/* create a UnicodeEncodeError object */ +PyAPI_FUNC(PyObject *) PyUnicodeEncodeError_Create( + const char *, const Py_UNICODE *, Py_ssize_t, Py_ssize_t, Py_ssize_t, const char *); + +/* create a UnicodeTranslateError object */ +PyAPI_FUNC(PyObject *) PyUnicodeTranslateError_Create( + const Py_UNICODE *, Py_ssize_t, Py_ssize_t, Py_ssize_t, const char *); + +/* get the encoding attribute */ +PyAPI_FUNC(PyObject *) PyUnicodeEncodeError_GetEncoding(PyObject *); +PyAPI_FUNC(PyObject *) PyUnicodeDecodeError_GetEncoding(PyObject *); + +/* get the object attribute */ +PyAPI_FUNC(PyObject *) PyUnicodeEncodeError_GetObject(PyObject *); +PyAPI_FUNC(PyObject *) PyUnicodeDecodeError_GetObject(PyObject *); +PyAPI_FUNC(PyObject *) PyUnicodeTranslateError_GetObject(PyObject *); + +/* get the value of the start attribute (the int * may not be NULL) + return 0 on success, -1 on failure */ +PyAPI_FUNC(int) PyUnicodeEncodeError_GetStart(PyObject *, Py_ssize_t *); +PyAPI_FUNC(int) PyUnicodeDecodeError_GetStart(PyObject *, Py_ssize_t *); +PyAPI_FUNC(int) PyUnicodeTranslateError_GetStart(PyObject *, Py_ssize_t *); + +/* assign a new value to the start attribute + return 0 on success, -1 on failure */ +PyAPI_FUNC(int) PyUnicodeEncodeError_SetStart(PyObject *, Py_ssize_t); +PyAPI_FUNC(int) PyUnicodeDecodeError_SetStart(PyObject *, Py_ssize_t); +PyAPI_FUNC(int) PyUnicodeTranslateError_SetStart(PyObject *, Py_ssize_t); + +/* get the value of the end attribute (the int *may not be NULL) + return 0 on success, -1 on failure */ +PyAPI_FUNC(int) PyUnicodeEncodeError_GetEnd(PyObject *, Py_ssize_t *); +PyAPI_FUNC(int) PyUnicodeDecodeError_GetEnd(PyObject *, Py_ssize_t *); +PyAPI_FUNC(int) PyUnicodeTranslateError_GetEnd(PyObject *, Py_ssize_t *); + +/* assign a new value to the end attribute + return 0 on success, -1 on failure */ +PyAPI_FUNC(int) PyUnicodeEncodeError_SetEnd(PyObject *, Py_ssize_t); +PyAPI_FUNC(int) PyUnicodeDecodeError_SetEnd(PyObject *, Py_ssize_t); +PyAPI_FUNC(int) PyUnicodeTranslateError_SetEnd(PyObject *, Py_ssize_t); + +/* get the value of the reason attribute */ +PyAPI_FUNC(PyObject *) PyUnicodeEncodeError_GetReason(PyObject *); +PyAPI_FUNC(PyObject *) PyUnicodeDecodeError_GetReason(PyObject *); +PyAPI_FUNC(PyObject *) PyUnicodeTranslateError_GetReason(PyObject *); + +/* assign a new value to the reason attribute + return 0 on success, -1 on failure */ +PyAPI_FUNC(int) PyUnicodeEncodeError_SetReason( + PyObject *, const char *); +PyAPI_FUNC(int) PyUnicodeDecodeError_SetReason( + PyObject *, const char *); +PyAPI_FUNC(int) PyUnicodeTranslateError_SetReason( + PyObject *, const char *); +#endif + + +/* These APIs aren't really part of the error implementation, but + often needed to format error messages; the native C lib APIs are + not available on all platforms, which is why we provide emulations + for those platforms in Python/mysnprintf.c, + WARNING: The return value of snprintf varies across platforms; do + not rely on any particular behavior; eventually the C99 defn may + be reliable. +*/ +#if defined(MS_WIN32) && !defined(HAVE_SNPRINTF) +# define HAVE_SNPRINTF +# define snprintf _snprintf +# define vsnprintf _vsnprintf +#endif + +#include +PyAPI_FUNC(int) PyOS_snprintf(char *str, size_t size, const char *format, ...) + Py_GCC_ATTRIBUTE((format(printf, 3, 4))); +PyAPI_FUNC(int) PyOS_vsnprintf(char *str, size_t size, const char *format, va_list va) + Py_GCC_ATTRIBUTE((format(printf, 3, 0))); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_ERRORS_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/pyexpat.h b/AppPkg/Applications/Python/Python-2.7.10/Include/pyexpat.h new file mode 100644 index 0000000000..fdce98862f --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/pyexpat.h @@ -0,0 +1,48 @@ +/* Stuff to export relevant 'expat' entry points from pyexpat to other + * parser modules, such as cElementTree. */ + +/* note: you must import expat.h before importing this module! */ + +#define PyExpat_CAPI_MAGIC "pyexpat.expat_CAPI 1.0" +#define PyExpat_CAPSULE_NAME "pyexpat.expat_CAPI" + +struct PyExpat_CAPI +{ + char* magic; /* set to PyExpat_CAPI_MAGIC */ + int size; /* set to sizeof(struct PyExpat_CAPI) */ + int MAJOR_VERSION; + int MINOR_VERSION; + int MICRO_VERSION; + /* pointers to selected expat functions. add new functions at + the end, if needed */ + const XML_LChar * (*ErrorString)(enum XML_Error code); + enum XML_Error (*GetErrorCode)(XML_Parser parser); + XML_Size (*GetErrorColumnNumber)(XML_Parser parser); + XML_Size (*GetErrorLineNumber)(XML_Parser parser); + enum XML_Status (*Parse)( + XML_Parser parser, const char *s, int len, int isFinal); + XML_Parser (*ParserCreate_MM)( + const XML_Char *encoding, const XML_Memory_Handling_Suite *memsuite, + const XML_Char *namespaceSeparator); + void (*ParserFree)(XML_Parser parser); + void (*SetCharacterDataHandler)( + XML_Parser parser, XML_CharacterDataHandler handler); + void (*SetCommentHandler)( + XML_Parser parser, XML_CommentHandler handler); + void (*SetDefaultHandlerExpand)( + XML_Parser parser, XML_DefaultHandler handler); + void (*SetElementHandler)( + XML_Parser parser, XML_StartElementHandler start, + XML_EndElementHandler end); + void (*SetNamespaceDeclHandler)( + XML_Parser parser, XML_StartNamespaceDeclHandler start, + XML_EndNamespaceDeclHandler end); + void (*SetProcessingInstructionHandler)( + XML_Parser parser, XML_ProcessingInstructionHandler handler); + void (*SetUnknownEncodingHandler)( + XML_Parser parser, XML_UnknownEncodingHandler handler, + void *encodingHandlerData); + void (*SetUserData)(XML_Parser parser, void *userData); + /* always add new stuff to the end! */ +}; + diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/pyfpe.h b/AppPkg/Applications/Python/Python-2.7.10/Include/pyfpe.h new file mode 100644 index 0000000000..66716163fb --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/pyfpe.h @@ -0,0 +1,176 @@ +#ifndef Py_PYFPE_H +#define Py_PYFPE_H +#ifdef __cplusplus +extern "C" { +#endif +/* + --------------------------------------------------------------------- + / Copyright (c) 1996. \ + | The Regents of the University of California. | + | All rights reserved. | + | | + | Permission to use, copy, modify, and distribute this software for | + | any purpose without fee is hereby granted, provided that this en- | + | tire notice is included in all copies of any software which is or | + | includes a copy or modification of this software and in all | + | copies of the supporting documentation for such software. | + | | + | This work was produced at the University of California, Lawrence | + | Livermore National Laboratory under contract no. W-7405-ENG-48 | + | between the U.S. Department of Energy and The Regents of the | + | University of California for the operation of UC LLNL. | + | | + | DISCLAIMER | + | | + | This software was prepared as an account of work sponsored by an | + | agency of the United States Government. Neither the United States | + | Government nor the University of California nor any of their em- | + | ployees, makes any warranty, express or implied, or assumes any | + | liability or responsibility for the accuracy, completeness, or | + | usefulness of any information, apparatus, product, or process | + | disclosed, or represents that its use would not infringe | + | privately-owned rights. Reference herein to any specific commer- | + | cial products, process, or service by trade name, trademark, | + | manufacturer, or otherwise, does not necessarily constitute or | + | imply its endorsement, recommendation, or favoring by the United | + | States Government or the University of California. The views and | + | opinions of authors expressed herein do not necessarily state or | + | reflect those of the United States Government or the University | + | of California, and shall not be used for advertising or product | + \ endorsement purposes. / + --------------------------------------------------------------------- +*/ + +/* + * Define macros for handling SIGFPE. + * Lee Busby, LLNL, November, 1996 + * busby1@llnl.gov + * + ********************************************* + * Overview of the system for handling SIGFPE: + * + * This file (Include/pyfpe.h) defines a couple of "wrapper" macros for + * insertion into your Python C code of choice. Their proper use is + * discussed below. The file Python/pyfpe.c defines a pair of global + * variables PyFPE_jbuf and PyFPE_counter which are used by the signal + * handler for SIGFPE to decide if a particular exception was protected + * by the macros. The signal handler itself, and code for enabling the + * generation of SIGFPE in the first place, is in a (new) Python module + * named fpectl. This module is standard in every respect. It can be loaded + * either statically or dynamically as you choose, and like any other + * Python module, has no effect until you import it. + * + * In the general case, there are three steps toward handling SIGFPE in any + * Python code: + * + * 1) Add the *_PROTECT macros to your C code as required to protect + * dangerous floating point sections. + * + * 2) Turn on the inclusion of the code by adding the ``--with-fpectl'' + * flag at the time you run configure. If the fpectl or other modules + * which use the *_PROTECT macros are to be dynamically loaded, be + * sure they are compiled with WANT_SIGFPE_HANDLER defined. + * + * 3) When python is built and running, import fpectl, and execute + * fpectl.turnon_sigfpe(). This sets up the signal handler and enables + * generation of SIGFPE whenever an exception occurs. From this point + * on, any properly trapped SIGFPE should result in the Python + * FloatingPointError exception. + * + * Step 1 has been done already for the Python kernel code, and should be + * done soon for the NumPy array package. Step 2 is usually done once at + * python install time. Python's behavior with respect to SIGFPE is not + * changed unless you also do step 3. Thus you can control this new + * facility at compile time, or run time, or both. + * + ******************************** + * Using the macros in your code: + * + * static PyObject *foobar(PyObject *self,PyObject *args) + * { + * .... + * PyFPE_START_PROTECT("Error in foobar", return 0) + * result = dangerous_op(somearg1, somearg2, ...); + * PyFPE_END_PROTECT(result) + * .... + * } + * + * If a floating point error occurs in dangerous_op, foobar returns 0 (NULL), + * after setting the associated value of the FloatingPointError exception to + * "Error in foobar". ``Dangerous_op'' can be a single operation, or a block + * of code, function calls, or any combination, so long as no alternate + * return is possible before the PyFPE_END_PROTECT macro is reached. + * + * The macros can only be used in a function context where an error return + * can be recognized as signaling a Python exception. (Generally, most + * functions that return a PyObject * will qualify.) + * + * Guido's original design suggestion for PyFPE_START_PROTECT and + * PyFPE_END_PROTECT had them open and close a local block, with a locally + * defined jmp_buf and jmp_buf pointer. This would allow recursive nesting + * of the macros. The Ansi C standard makes it clear that such local + * variables need to be declared with the "volatile" type qualifier to keep + * setjmp from corrupting their values. Some current implementations seem + * to be more restrictive. For example, the HPUX man page for setjmp says + * + * Upon the return from a setjmp() call caused by a longjmp(), the + * values of any non-static local variables belonging to the routine + * from which setjmp() was called are undefined. Code which depends on + * such values is not guaranteed to be portable. + * + * I therefore decided on a more limited form of nesting, using a counter + * variable (PyFPE_counter) to keep track of any recursion. If an exception + * occurs in an ``inner'' pair of macros, the return will apparently + * come from the outermost level. + * + */ + +#ifdef WANT_SIGFPE_HANDLER +#include +#include +#include +extern jmp_buf PyFPE_jbuf; +extern int PyFPE_counter; +extern double PyFPE_dummy(void *); + +#define PyFPE_START_PROTECT(err_string, leave_stmt) \ +if (!PyFPE_counter++ && setjmp(PyFPE_jbuf)) { \ + PyErr_SetString(PyExc_FloatingPointError, err_string); \ + PyFPE_counter = 0; \ + leave_stmt; \ +} + +/* + * This (following) is a heck of a way to decrement a counter. However, + * unless the macro argument is provided, code optimizers will sometimes move + * this statement so that it gets executed *before* the unsafe expression + * which we're trying to protect. That pretty well messes things up, + * of course. + * + * If the expression(s) you're trying to protect don't happen to return a + * value, you will need to manufacture a dummy result just to preserve the + * correct ordering of statements. Note that the macro passes the address + * of its argument (so you need to give it something which is addressable). + * If your expression returns multiple results, pass the last such result + * to PyFPE_END_PROTECT. + * + * Note that PyFPE_dummy returns a double, which is cast to int. + * This seeming insanity is to tickle the Floating Point Unit (FPU). + * If an exception has occurred in a preceding floating point operation, + * some architectures (notably Intel 80x86) will not deliver the interrupt + * until the *next* floating point operation. This is painful if you've + * already decremented PyFPE_counter. + */ +#define PyFPE_END_PROTECT(v) PyFPE_counter -= (int)PyFPE_dummy(&(v)); + +#else + +#define PyFPE_START_PROTECT(err_string, leave_stmt) +#define PyFPE_END_PROTECT(v) + +#endif + +#ifdef __cplusplus +} +#endif +#endif /* !Py_PYFPE_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/pygetopt.h b/AppPkg/Applications/Python/Python-2.7.10/Include/pygetopt.h new file mode 100644 index 0000000000..024f1738af --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/pygetopt.h @@ -0,0 +1,18 @@ + +#ifndef Py_PYGETOPT_H +#define Py_PYGETOPT_H +#ifdef __cplusplus +extern "C" { +#endif + +PyAPI_DATA(int) _PyOS_opterr; +PyAPI_DATA(int) _PyOS_optind; +PyAPI_DATA(char *) _PyOS_optarg; + +PyAPI_FUNC(void) _PyOS_ResetGetOpt(void); +PyAPI_FUNC(int) _PyOS_GetOpt(int argc, char **argv, char *optstring); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_PYGETOPT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/pymacconfig.h b/AppPkg/Applications/Python/Python-2.7.10/Include/pymacconfig.h new file mode 100644 index 0000000000..f647b478ca --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/pymacconfig.h @@ -0,0 +1,102 @@ +#ifndef PYMACCONFIG_H +#define PYMACCONFIG_H + /* + * This file moves some of the autoconf magic to compile-time + * when building on MacOSX. This is needed for building 4-way + * universal binaries and for 64-bit universal binaries because + * the values redefined below aren't configure-time constant but + * only compile-time constant in these scenarios. + */ + +#if defined(__APPLE__) + +# undef SIZEOF_LONG +# undef SIZEOF_PTHREAD_T +# undef SIZEOF_SIZE_T +# undef SIZEOF_TIME_T +# undef SIZEOF_VOID_P +# undef SIZEOF__BOOL +# undef SIZEOF_UINTPTR_T +# undef SIZEOF_PTHREAD_T +# undef WORDS_BIGENDIAN +# undef DOUBLE_IS_ARM_MIXED_ENDIAN_IEEE754 +# undef DOUBLE_IS_BIG_ENDIAN_IEEE754 +# undef DOUBLE_IS_LITTLE_ENDIAN_IEEE754 +# undef HAVE_GCC_ASM_FOR_X87 + +# undef VA_LIST_IS_ARRAY +# if defined(__LP64__) && defined(__x86_64__) +# define VA_LIST_IS_ARRAY 1 +# endif + +# undef HAVE_LARGEFILE_SUPPORT +# ifndef __LP64__ +# define HAVE_LARGEFILE_SUPPORT 1 +# endif + +# undef SIZEOF_LONG +# ifdef __LP64__ +# define SIZEOF__BOOL 1 +# define SIZEOF__BOOL 1 +# define SIZEOF_LONG 8 +# define SIZEOF_PTHREAD_T 8 +# define SIZEOF_SIZE_T 8 +# define SIZEOF_TIME_T 8 +# define SIZEOF_VOID_P 8 +# define SIZEOF_UINTPTR_T 8 +# define SIZEOF_PTHREAD_T 8 +# else +# ifdef __ppc__ +# define SIZEOF__BOOL 4 +# else +# define SIZEOF__BOOL 1 +# endif +# define SIZEOF_LONG 4 +# define SIZEOF_PTHREAD_T 4 +# define SIZEOF_SIZE_T 4 +# define SIZEOF_TIME_T 4 +# define SIZEOF_VOID_P 4 +# define SIZEOF_UINTPTR_T 4 +# define SIZEOF_PTHREAD_T 4 +# endif + +# if defined(__LP64__) + /* MacOSX 10.4 (the first release to support 64-bit code + * at all) only supports 64-bit in the UNIX layer. + * Therefore surpress the toolbox-glue in 64-bit mode. + */ + + /* In 64-bit mode setpgrp always has no argments, in 32-bit + * mode that depends on the compilation environment + */ +# undef SETPGRP_HAVE_ARG + +# endif + +#ifdef __BIG_ENDIAN__ +#define WORDS_BIGENDIAN 1 +#define DOUBLE_IS_BIG_ENDIAN_IEEE754 +#else +#define DOUBLE_IS_LITTLE_ENDIAN_IEEE754 +#endif /* __BIG_ENDIAN */ + +#ifdef __i386__ +# define HAVE_GCC_ASM_FOR_X87 +#endif + + /* + * The definition in pyconfig.h is only valid on the OS release + * where configure ran on and not necessarily for all systems where + * the executable can be used on. + * + * Specifically: OSX 10.4 has limited supported for '%zd', while + * 10.5 has full support for '%zd'. A binary built on 10.5 won't + * work properly on 10.4 unless we surpress the definition + * of PY_FORMAT_SIZE_T + */ +#undef PY_FORMAT_SIZE_T + + +#endif /* defined(_APPLE__) */ + +#endif /* PYMACCONFIG_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/pymactoolbox.h b/AppPkg/Applications/Python/Python-2.7.10/Include/pymactoolbox.h new file mode 100644 index 0000000000..a0ac1c26b7 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/pymactoolbox.h @@ -0,0 +1,217 @@ +/* +** pymactoolbox.h - globals defined in mactoolboxglue.c +*/ +#ifndef Py_PYMACTOOLBOX_H +#define Py_PYMACTOOLBOX_H +#ifdef __cplusplus + extern "C" { +#endif + +#include + +#ifndef __LP64__ +#include +#endif /* !__LP64__ */ + +/* +** Helper routines for error codes and such. +*/ +char *PyMac_StrError(int); /* strerror with mac errors */ +extern PyObject *PyMac_OSErrException; /* Exception for OSErr */ +PyObject *PyMac_GetOSErrException(void); /* Initialize & return it */ +PyObject *PyErr_Mac(PyObject *, int); /* Exception with a mac error */ +PyObject *PyMac_Error(OSErr); /* Uses PyMac_GetOSErrException */ +#ifndef __LP64__ +extern OSErr PyMac_GetFullPathname(FSSpec *, char *, int); /* convert + fsspec->path */ +#endif /* __LP64__ */ + +/* +** These conversion routines are defined in mactoolboxglue.c itself. +*/ +int PyMac_GetOSType(PyObject *, OSType *); /* argument parser for OSType */ +PyObject *PyMac_BuildOSType(OSType); /* Convert OSType to PyObject */ + +PyObject *PyMac_BuildNumVersion(NumVersion);/* Convert NumVersion to PyObject */ + +int PyMac_GetStr255(PyObject *, Str255); /* argument parser for Str255 */ +PyObject *PyMac_BuildStr255(Str255); /* Convert Str255 to PyObject */ +PyObject *PyMac_BuildOptStr255(Str255); /* Convert Str255 to PyObject, + NULL to None */ + +int PyMac_GetRect(PyObject *, Rect *); /* argument parser for Rect */ +PyObject *PyMac_BuildRect(Rect *); /* Convert Rect to PyObject */ + +int PyMac_GetPoint(PyObject *, Point *); /* argument parser for Point */ +PyObject *PyMac_BuildPoint(Point); /* Convert Point to PyObject */ + +int PyMac_GetEventRecord(PyObject *, EventRecord *); /* argument parser for + EventRecord */ +PyObject *PyMac_BuildEventRecord(EventRecord *); /* Convert EventRecord to + PyObject */ + +int PyMac_GetFixed(PyObject *, Fixed *); /* argument parser for Fixed */ +PyObject *PyMac_BuildFixed(Fixed); /* Convert Fixed to PyObject */ +int PyMac_Getwide(PyObject *, wide *); /* argument parser for wide */ +PyObject *PyMac_Buildwide(wide *); /* Convert wide to PyObject */ + +/* +** The rest of the routines are implemented by extension modules. If they are +** dynamically loaded mactoolboxglue will contain a stub implementation of the +** routine, which imports the module, whereupon the module's init routine will +** communicate the routine pointer back to the stub. +** If USE_TOOLBOX_OBJECT_GLUE is not defined there is no glue code, and the +** extension modules simply declare the routine. This is the case for static +** builds (and could be the case for MacPython CFM builds, because CFM extension +** modules can reference each other without problems). +*/ + +#ifdef USE_TOOLBOX_OBJECT_GLUE +/* +** These macros are used in the module init code. If we use toolbox object glue +** it sets the function pointer to point to the real function. +*/ +#define PyMac_INIT_TOOLBOX_OBJECT_NEW(object, rtn) { \ + extern PyObject *(*PyMacGluePtr_##rtn)(object); \ + PyMacGluePtr_##rtn = _##rtn; \ +} +#define PyMac_INIT_TOOLBOX_OBJECT_CONVERT(object, rtn) { \ + extern int (*PyMacGluePtr_##rtn)(PyObject *, object *); \ + PyMacGluePtr_##rtn = _##rtn; \ +} +#else +/* +** If we don't use toolbox object glue the init macros are empty. Moreover, we define +** _xxx_New to be the same as xxx_New, and the code in mactoolboxglue isn't included. +*/ +#define PyMac_INIT_TOOLBOX_OBJECT_NEW(object, rtn) +#define PyMac_INIT_TOOLBOX_OBJECT_CONVERT(object, rtn) +#endif /* USE_TOOLBOX_OBJECT_GLUE */ + +/* macfs exports */ +#ifndef __LP64__ +int PyMac_GetFSSpec(PyObject *, FSSpec *); /* argument parser for FSSpec */ +PyObject *PyMac_BuildFSSpec(FSSpec *); /* Convert FSSpec to PyObject */ +#endif /* !__LP64__ */ + +int PyMac_GetFSRef(PyObject *, FSRef *); /* argument parser for FSRef */ +PyObject *PyMac_BuildFSRef(FSRef *); /* Convert FSRef to PyObject */ + +/* AE exports */ +extern PyObject *AEDesc_New(AppleEvent *); /* XXXX Why passed by address?? */ +extern PyObject *AEDesc_NewBorrowed(AppleEvent *); +extern int AEDesc_Convert(PyObject *, AppleEvent *); + +/* Cm exports */ +extern PyObject *CmpObj_New(Component); +extern int CmpObj_Convert(PyObject *, Component *); +extern PyObject *CmpInstObj_New(ComponentInstance); +extern int CmpInstObj_Convert(PyObject *, ComponentInstance *); + +/* Ctl exports */ +#ifndef __LP64__ +extern PyObject *CtlObj_New(ControlHandle); +extern int CtlObj_Convert(PyObject *, ControlHandle *); +#endif /* !__LP64__ */ + +/* Dlg exports */ +#ifndef __LP64__ +extern PyObject *DlgObj_New(DialogPtr); +extern int DlgObj_Convert(PyObject *, DialogPtr *); +extern PyObject *DlgObj_WhichDialog(DialogPtr); +#endif /* !__LP64__ */ + +/* Drag exports */ +#ifndef __LP64__ +extern PyObject *DragObj_New(DragReference); +extern int DragObj_Convert(PyObject *, DragReference *); +#endif /* !__LP64__ */ + +/* List exports */ +#ifndef __LP64__ +extern PyObject *ListObj_New(ListHandle); +extern int ListObj_Convert(PyObject *, ListHandle *); +#endif /* !__LP64__ */ + +/* Menu exports */ +#ifndef __LP64__ +extern PyObject *MenuObj_New(MenuHandle); +extern int MenuObj_Convert(PyObject *, MenuHandle *); +#endif /* !__LP64__ */ + +/* Qd exports */ +#ifndef __LP64__ +extern PyObject *GrafObj_New(GrafPtr); +extern int GrafObj_Convert(PyObject *, GrafPtr *); +extern PyObject *BMObj_New(BitMapPtr); +extern int BMObj_Convert(PyObject *, BitMapPtr *); +extern PyObject *QdRGB_New(RGBColor *); +extern int QdRGB_Convert(PyObject *, RGBColor *); +#endif /* !__LP64__ */ + +/* Qdoffs exports */ +#ifndef __LP64__ +extern PyObject *GWorldObj_New(GWorldPtr); +extern int GWorldObj_Convert(PyObject *, GWorldPtr *); +#endif /* !__LP64__ */ + +/* Qt exports */ +#ifndef __LP64__ +extern PyObject *TrackObj_New(Track); +extern int TrackObj_Convert(PyObject *, Track *); +extern PyObject *MovieObj_New(Movie); +extern int MovieObj_Convert(PyObject *, Movie *); +extern PyObject *MovieCtlObj_New(MovieController); +extern int MovieCtlObj_Convert(PyObject *, MovieController *); +extern PyObject *TimeBaseObj_New(TimeBase); +extern int TimeBaseObj_Convert(PyObject *, TimeBase *); +extern PyObject *UserDataObj_New(UserData); +extern int UserDataObj_Convert(PyObject *, UserData *); +extern PyObject *MediaObj_New(Media); +extern int MediaObj_Convert(PyObject *, Media *); +#endif /* !__LP64__ */ + +/* Res exports */ +extern PyObject *ResObj_New(Handle); +extern int ResObj_Convert(PyObject *, Handle *); +extern PyObject *OptResObj_New(Handle); +extern int OptResObj_Convert(PyObject *, Handle *); + +/* TE exports */ +#ifndef __LP64__ +extern PyObject *TEObj_New(TEHandle); +extern int TEObj_Convert(PyObject *, TEHandle *); +#endif /* !__LP64__ */ + +/* Win exports */ +#ifndef __LP64__ +extern PyObject *WinObj_New(WindowPtr); +extern int WinObj_Convert(PyObject *, WindowPtr *); +extern PyObject *WinObj_WhichWindow(WindowPtr); +#endif /* !__LP64__ */ + +/* CF exports */ +extern PyObject *CFObj_New(CFTypeRef); +extern int CFObj_Convert(PyObject *, CFTypeRef *); +extern PyObject *CFTypeRefObj_New(CFTypeRef); +extern int CFTypeRefObj_Convert(PyObject *, CFTypeRef *); +extern PyObject *CFStringRefObj_New(CFStringRef); +extern int CFStringRefObj_Convert(PyObject *, CFStringRef *); +extern PyObject *CFMutableStringRefObj_New(CFMutableStringRef); +extern int CFMutableStringRefObj_Convert(PyObject *, CFMutableStringRef *); +extern PyObject *CFArrayRefObj_New(CFArrayRef); +extern int CFArrayRefObj_Convert(PyObject *, CFArrayRef *); +extern PyObject *CFMutableArrayRefObj_New(CFMutableArrayRef); +extern int CFMutableArrayRefObj_Convert(PyObject *, CFMutableArrayRef *); +extern PyObject *CFDictionaryRefObj_New(CFDictionaryRef); +extern int CFDictionaryRefObj_Convert(PyObject *, CFDictionaryRef *); +extern PyObject *CFMutableDictionaryRefObj_New(CFMutableDictionaryRef); +extern int CFMutableDictionaryRefObj_Convert(PyObject *, CFMutableDictionaryRef *); +extern PyObject *CFURLRefObj_New(CFURLRef); +extern int CFURLRefObj_Convert(PyObject *, CFURLRef *); +extern int OptionalCFURLRefObj_Convert(PyObject *, CFURLRef *); + +#ifdef __cplusplus + } +#endif +#endif diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/pymath.h b/AppPkg/Applications/Python/Python-2.7.10/Include/pymath.h new file mode 100644 index 0000000000..f63ddb7a69 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/pymath.h @@ -0,0 +1,192 @@ +#ifndef Py_PYMATH_H +#define Py_PYMATH_H + +#include "pyconfig.h" /* include for defines */ + +/************************************************************************** +Symbols and macros to supply platform-independent interfaces to mathematical +functions and constants +**************************************************************************/ + +/* Python provides implementations for copysign, round and hypot in + * Python/pymath.c just in case your math library doesn't provide the + * functions. + * + *Note: PC/pyconfig.h defines copysign as _copysign + */ +#ifndef HAVE_COPYSIGN +extern double copysign(double, double); +#endif + +#ifndef HAVE_ROUND +extern double round(double); +#endif + +#ifndef HAVE_HYPOT +extern double hypot(double, double); +#endif + +/* extra declarations */ +#ifndef _MSC_VER +#ifndef __STDC__ +extern double fmod (double, double); +extern double frexp (double, int *); +extern double ldexp (double, int); +extern double modf (double, double *); +extern double pow(double, double); +#endif /* __STDC__ */ +#endif /* _MSC_VER */ + +#ifdef _OSF_SOURCE +/* OSF1 5.1 doesn't make these available with XOPEN_SOURCE_EXTENDED defined */ +extern int finite(double); +extern double copysign(double, double); +#endif + +/* High precision defintion of pi and e (Euler) + * The values are taken from libc6's math.h. + */ +#ifndef Py_MATH_PIl +#define Py_MATH_PIl 3.1415926535897932384626433832795029L +#endif +#ifndef Py_MATH_PI +#define Py_MATH_PI 3.14159265358979323846 +#endif + +#ifndef Py_MATH_El +#define Py_MATH_El 2.7182818284590452353602874713526625L +#endif + +#ifndef Py_MATH_E +#define Py_MATH_E 2.7182818284590452354 +#endif + +/* On x86, Py_FORCE_DOUBLE forces a floating-point number out of an x87 FPU + register and into a 64-bit memory location, rounding from extended + precision to double precision in the process. On other platforms it does + nothing. */ + +/* we take double rounding as evidence of x87 usage */ +#ifndef Py_FORCE_DOUBLE +# ifdef X87_DOUBLE_ROUNDING +PyAPI_FUNC(double) _Py_force_double(double); +# define Py_FORCE_DOUBLE(X) (_Py_force_double(X)) +# else +# define Py_FORCE_DOUBLE(X) (X) +# endif +#endif + +#ifdef HAVE_GCC_ASM_FOR_X87 +PyAPI_FUNC(unsigned short) _Py_get_387controlword(void); +PyAPI_FUNC(void) _Py_set_387controlword(unsigned short); +#endif + +/* Py_IS_NAN(X) + * Return 1 if float or double arg is a NaN, else 0. + * Caution: + * X is evaluated more than once. + * This may not work on all platforms. Each platform has *some* + * way to spell this, though -- override in pyconfig.h if you have + * a platform where it doesn't work. + * Note: PC/pyconfig.h defines Py_IS_NAN as _isnan + */ +#ifndef Py_IS_NAN +#if defined HAVE_DECL_ISNAN && HAVE_DECL_ISNAN == 1 +#define Py_IS_NAN(X) isnan(X) +#else +#define Py_IS_NAN(X) ((X) != (X)) +#endif +#endif + +/* Py_IS_INFINITY(X) + * Return 1 if float or double arg is an infinity, else 0. + * Caution: + * X is evaluated more than once. + * This implementation may set the underflow flag if |X| is very small; + * it really can't be implemented correctly (& easily) before C99. + * Override in pyconfig.h if you have a better spelling on your platform. + * Py_FORCE_DOUBLE is used to avoid getting false negatives from a + * non-infinite value v sitting in an 80-bit x87 register such that + * v becomes infinite when spilled from the register to 64-bit memory. + * Note: PC/pyconfig.h defines Py_IS_INFINITY as _isinf + */ +#ifndef Py_IS_INFINITY +# if defined HAVE_DECL_ISINF && HAVE_DECL_ISINF == 1 +# define Py_IS_INFINITY(X) isinf(X) +# else +# define Py_IS_INFINITY(X) ((X) && \ + (Py_FORCE_DOUBLE(X)*0.5 == Py_FORCE_DOUBLE(X))) +# endif +#endif + +/* Py_IS_FINITE(X) + * Return 1 if float or double arg is neither infinite nor NAN, else 0. + * Some compilers (e.g. VisualStudio) have intrisics for this, so a special + * macro for this particular test is useful + * Note: PC/pyconfig.h defines Py_IS_FINITE as _finite + */ +#ifndef Py_IS_FINITE +#if defined HAVE_DECL_ISFINITE && HAVE_DECL_ISFINITE == 1 +#define Py_IS_FINITE(X) isfinite(X) +#elif defined HAVE_FINITE +#define Py_IS_FINITE(X) finite(X) +#else +#define Py_IS_FINITE(X) (!Py_IS_INFINITY(X) && !Py_IS_NAN(X)) +#endif +#endif + +/* HUGE_VAL is supposed to expand to a positive double infinity. Python + * uses Py_HUGE_VAL instead because some platforms are broken in this + * respect. We used to embed code in pyport.h to try to worm around that, + * but different platforms are broken in conflicting ways. If you're on + * a platform where HUGE_VAL is defined incorrectly, fiddle your Python + * config to #define Py_HUGE_VAL to something that works on your platform. + */ +#ifndef Py_HUGE_VAL +#define Py_HUGE_VAL HUGE_VAL +#endif + +/* Py_NAN + * A value that evaluates to a NaN. On IEEE 754 platforms INF*0 or + * INF/INF works. Define Py_NO_NAN in pyconfig.h if your platform + * doesn't support NaNs. + */ +#if !defined(Py_NAN) && !defined(Py_NO_NAN) +#define Py_NAN (Py_HUGE_VAL * 0.) +#endif + +/* Py_OVERFLOWED(X) + * Return 1 iff a libm function overflowed. Set errno to 0 before calling + * a libm function, and invoke this macro after, passing the function + * result. + * Caution: + * This isn't reliable. C99 no longer requires libm to set errno under + * any exceptional condition, but does require +- HUGE_VAL return + * values on overflow. A 754 box *probably* maps HUGE_VAL to a + * double infinity, and we're cool if that's so, unless the input + * was an infinity and an infinity is the expected result. A C89 + * system sets errno to ERANGE, so we check for that too. We're + * out of luck if a C99 754 box doesn't map HUGE_VAL to +Inf, or + * if the returned result is a NaN, or if a C89 box returns HUGE_VAL + * in non-overflow cases. + * X is evaluated more than once. + * Some platforms have better way to spell this, so expect some #ifdef'ery. + * + * OpenBSD uses 'isinf()' because a compiler bug on that platform causes + * the longer macro version to be mis-compiled. This isn't optimal, and + * should be removed once a newer compiler is available on that platform. + * The system that had the failure was running OpenBSD 3.2 on Intel, with + * gcc 2.95.3. + * + * According to Tim's checkin, the FreeBSD systems use isinf() to work + * around a FPE bug on that platform. + */ +#if defined(__FreeBSD__) || defined(__OpenBSD__) +#define Py_OVERFLOWED(X) isinf(X) +#else +#define Py_OVERFLOWED(X) ((X) != 0.0 && (errno == ERANGE || \ + (X) == Py_HUGE_VAL || \ + (X) == -Py_HUGE_VAL)) +#endif + +#endif /* Py_PYMATH_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/pymem.h b/AppPkg/Applications/Python/Python-2.7.10/Include/pymem.h new file mode 100644 index 0000000000..27c72f132f --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/pymem.h @@ -0,0 +1,122 @@ +/* The PyMem_ family: low-level memory allocation interfaces. + See objimpl.h for the PyObject_ memory family. +*/ + +#ifndef Py_PYMEM_H +#define Py_PYMEM_H + +#include "pyport.h" + +#ifdef __cplusplus +extern "C" { +#endif + +/* BEWARE: + + Each interface exports both functions and macros. Extension modules should + use the functions, to ensure binary compatibility across Python versions. + Because the Python implementation is free to change internal details, and + the macros may (or may not) expose details for speed, if you do use the + macros you must recompile your extensions with each Python release. + + Never mix calls to PyMem_ with calls to the platform malloc/realloc/ + calloc/free. For example, on Windows different DLLs may end up using + different heaps, and if you use PyMem_Malloc you'll get the memory from the + heap used by the Python DLL; it could be a disaster if you free()'ed that + directly in your own extension. Using PyMem_Free instead ensures Python + can return the memory to the proper heap. As another example, in + PYMALLOC_DEBUG mode, Python wraps all calls to all PyMem_ and PyObject_ + memory functions in special debugging wrappers that add additional + debugging info to dynamic memory blocks. The system routines have no idea + what to do with that stuff, and the Python wrappers have no idea what to do + with raw blocks obtained directly by the system routines then. + + The GIL must be held when using these APIs. +*/ + +/* + * Raw memory interface + * ==================== + */ + +/* Functions + + Functions supplying platform-independent semantics for malloc/realloc/ + free. These functions make sure that allocating 0 bytes returns a distinct + non-NULL pointer (whenever possible -- if we're flat out of memory, NULL + may be returned), even if the platform malloc and realloc don't. + Returned pointers must be checked for NULL explicitly. No action is + performed on failure (no exception is set, no warning is printed, etc). +*/ + +PyAPI_FUNC(void *) PyMem_Malloc(size_t); +PyAPI_FUNC(void *) PyMem_Realloc(void *, size_t); +PyAPI_FUNC(void) PyMem_Free(void *); + +/* Starting from Python 1.6, the wrappers Py_{Malloc,Realloc,Free} are + no longer supported. They used to call PyErr_NoMemory() on failure. */ + +/* Macros. */ +#ifdef PYMALLOC_DEBUG +/* Redirect all memory operations to Python's debugging allocator. */ +#define PyMem_MALLOC _PyMem_DebugMalloc +#define PyMem_REALLOC _PyMem_DebugRealloc +#define PyMem_FREE _PyMem_DebugFree + +#else /* ! PYMALLOC_DEBUG */ + +/* PyMem_MALLOC(0) means malloc(1). Some systems would return NULL + for malloc(0), which would be treated as an error. Some platforms + would return a pointer with no memory behind it, which would break + pymalloc. To solve these problems, allocate an extra byte. */ +/* Returns NULL to indicate error if a negative size or size larger than + Py_ssize_t can represent is supplied. Helps prevents security holes. */ +#define PyMem_MALLOC(n) ((size_t)(n) > (size_t)PY_SSIZE_T_MAX ? NULL \ + : malloc((n) ? (n) : 1)) +#define PyMem_REALLOC(p, n) ((size_t)(n) > (size_t)PY_SSIZE_T_MAX ? NULL \ + : realloc((p), (n) ? (n) : 1)) +#define PyMem_FREE free + +#endif /* PYMALLOC_DEBUG */ + +/* + * Type-oriented memory interface + * ============================== + * + * Allocate memory for n objects of the given type. Returns a new pointer + * or NULL if the request was too large or memory allocation failed. Use + * these macros rather than doing the multiplication yourself so that proper + * overflow checking is always done. + */ + +#define PyMem_New(type, n) \ + ( ((size_t)(n) > PY_SSIZE_T_MAX / sizeof(type)) ? NULL : \ + ( (type *) PyMem_Malloc((n) * sizeof(type)) ) ) +#define PyMem_NEW(type, n) \ + ( ((size_t)(n) > PY_SSIZE_T_MAX / sizeof(type)) ? NULL : \ + ( (type *) PyMem_MALLOC((n) * sizeof(type)) ) ) + +/* + * The value of (p) is always clobbered by this macro regardless of success. + * The caller MUST check if (p) is NULL afterwards and deal with the memory + * error if so. This means the original value of (p) MUST be saved for the + * caller's memory error handler to not lose track of it. + */ +#define PyMem_Resize(p, type, n) \ + ( (p) = ((size_t)(n) > PY_SSIZE_T_MAX / sizeof(type)) ? NULL : \ + (type *) PyMem_Realloc((p), (n) * sizeof(type)) ) +#define PyMem_RESIZE(p, type, n) \ + ( (p) = ((size_t)(n) > PY_SSIZE_T_MAX / sizeof(type)) ? NULL : \ + (type *) PyMem_REALLOC((p), (n) * sizeof(type)) ) + +/* PyMem{Del,DEL} are left over from ancient days, and shouldn't be used + * anymore. They're just confusing aliases for PyMem_{Free,FREE} now. + */ +#define PyMem_Del PyMem_Free +#define PyMem_DEL PyMem_FREE + +#ifdef __cplusplus +} +#endif + +#endif /* !Py_PYMEM_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/pyport.h b/AppPkg/Applications/Python/Python-2.7.10/Include/pyport.h new file mode 100644 index 0000000000..ff43d6ef9c --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/pyport.h @@ -0,0 +1,941 @@ +#ifndef Py_PYPORT_H +#define Py_PYPORT_H + +#include "pyconfig.h" /* include for defines */ + +/* Some versions of HP-UX & Solaris need inttypes.h for int32_t, + INT32_MAX, etc. */ +#ifdef HAVE_INTTYPES_H +#include +#endif + +#ifdef HAVE_STDINT_H +#include +#endif + +/************************************************************************** +Symbols and macros to supply platform-independent interfaces to basic +C language & library operations whose spellings vary across platforms. + +Please try to make documentation here as clear as possible: by definition, +the stuff here is trying to illuminate C's darkest corners. + +Config #defines referenced here: + +SIGNED_RIGHT_SHIFT_ZERO_FILLS +Meaning: To be defined iff i>>j does not extend the sign bit when i is a + signed integral type and i < 0. +Used in: Py_ARITHMETIC_RIGHT_SHIFT + +Py_DEBUG +Meaning: Extra checks compiled in for debug mode. +Used in: Py_SAFE_DOWNCAST + +HAVE_UINTPTR_T +Meaning: The C9X type uintptr_t is supported by the compiler +Used in: Py_uintptr_t + +HAVE_LONG_LONG +Meaning: The compiler supports the C type "long long" +Used in: PY_LONG_LONG + +**************************************************************************/ + + +/* For backward compatibility only. Obsolete, do not use. */ +#ifdef HAVE_PROTOTYPES +#define Py_PROTO(x) x +#else +#define Py_PROTO(x) () +#endif +#ifndef Py_FPROTO +#define Py_FPROTO(x) Py_PROTO(x) +#endif + +/* typedefs for some C9X-defined synonyms for integral types. + * + * The names in Python are exactly the same as the C9X names, except with a + * Py_ prefix. Until C9X is universally implemented, this is the only way + * to ensure that Python gets reliable names that don't conflict with names + * in non-Python code that are playing their own tricks to define the C9X + * names. + * + * NOTE: don't go nuts here! Python has no use for *most* of the C9X + * integral synonyms. Only define the ones we actually need. + */ + +#ifdef HAVE_LONG_LONG +#ifndef PY_LONG_LONG +#define PY_LONG_LONG long long +#if defined(LLONG_MAX) +/* If LLONG_MAX is defined in limits.h, use that. */ +#define PY_LLONG_MIN LLONG_MIN +#define PY_LLONG_MAX LLONG_MAX +#define PY_ULLONG_MAX ULLONG_MAX +#elif defined(__LONG_LONG_MAX__) +/* Otherwise, if GCC has a builtin define, use that. */ +#define PY_LLONG_MAX __LONG_LONG_MAX__ +#define PY_LLONG_MIN (-PY_LLONG_MAX-1) +#define PY_ULLONG_MAX (__LONG_LONG_MAX__*2ULL + 1ULL) +#else +/* Otherwise, rely on two's complement. */ +#define PY_ULLONG_MAX (~0ULL) +#define PY_LLONG_MAX ((long long)(PY_ULLONG_MAX>>1)) +#define PY_LLONG_MIN (-PY_LLONG_MAX-1) +#endif /* LLONG_MAX */ +#endif +#endif /* HAVE_LONG_LONG */ + +/* a build with 30-bit digits for Python long integers needs an exact-width + * 32-bit unsigned integer type to store those digits. (We could just use + * type 'unsigned long', but that would be wasteful on a system where longs + * are 64-bits.) On Unix systems, the autoconf macro AC_TYPE_UINT32_T defines + * uint32_t to be such a type unless stdint.h or inttypes.h defines uint32_t. + * However, it doesn't set HAVE_UINT32_T, so we do that here. + */ +#ifdef uint32_t +#define HAVE_UINT32_T 1 +#endif + +#ifdef HAVE_UINT32_T +#ifndef PY_UINT32_T +#define PY_UINT32_T uint32_t +#endif +#endif + +/* Macros for a 64-bit unsigned integer type; used for type 'twodigits' in the + * long integer implementation, when 30-bit digits are enabled. + */ +#ifdef uint64_t +#define HAVE_UINT64_T 1 +#endif + +#ifdef HAVE_UINT64_T +#ifndef PY_UINT64_T +#define PY_UINT64_T uint64_t +#endif +#endif + +/* Signed variants of the above */ +#ifdef int32_t +#define HAVE_INT32_T 1 +#endif + +#ifdef HAVE_INT32_T +#ifndef PY_INT32_T +#define PY_INT32_T int32_t +#endif +#endif + +#ifdef int64_t +#define HAVE_INT64_T 1 +#endif + +#ifdef HAVE_INT64_T +#ifndef PY_INT64_T +#define PY_INT64_T int64_t +#endif +#endif + +/* If PYLONG_BITS_IN_DIGIT is not defined then we'll use 30-bit digits if all + the necessary integer types are available, and we're on a 64-bit platform + (as determined by SIZEOF_VOID_P); otherwise we use 15-bit digits. */ + +#ifndef PYLONG_BITS_IN_DIGIT +#if (defined HAVE_UINT64_T && defined HAVE_INT64_T && \ + defined HAVE_UINT32_T && defined HAVE_INT32_T && SIZEOF_VOID_P >= 8) +#define PYLONG_BITS_IN_DIGIT 30 +#else +#define PYLONG_BITS_IN_DIGIT 15 +#endif +#endif + +/* uintptr_t is the C9X name for an unsigned integral type such that a + * legitimate void* can be cast to uintptr_t and then back to void* again + * without loss of information. Similarly for intptr_t, wrt a signed + * integral type. + */ +#ifdef HAVE_UINTPTR_T +typedef uintptr_t Py_uintptr_t; +typedef intptr_t Py_intptr_t; + +#elif SIZEOF_VOID_P <= SIZEOF_INT +typedef unsigned int Py_uintptr_t; +typedef int Py_intptr_t; + +#elif SIZEOF_VOID_P <= SIZEOF_LONG +typedef unsigned long Py_uintptr_t; +typedef long Py_intptr_t; + +#elif defined(HAVE_LONG_LONG) && (SIZEOF_VOID_P <= SIZEOF_LONG_LONG) +typedef unsigned PY_LONG_LONG Py_uintptr_t; +typedef PY_LONG_LONG Py_intptr_t; + +#else +# error "Python needs a typedef for Py_uintptr_t in pyport.h." +#endif /* HAVE_UINTPTR_T */ + +/* Py_ssize_t is a signed integral type such that sizeof(Py_ssize_t) == + * sizeof(size_t). C99 doesn't define such a thing directly (size_t is an + * unsigned integral type). See PEP 353 for details. + */ +#ifdef HAVE_SSIZE_T +typedef ssize_t Py_ssize_t; +#elif SIZEOF_VOID_P == SIZEOF_SIZE_T +typedef Py_intptr_t Py_ssize_t; +#else +# error "Python needs a typedef for Py_ssize_t in pyport.h." +#endif + +/* Largest possible value of size_t. + SIZE_MAX is part of C99, so it might be defined on some + platforms. If it is not defined, (size_t)-1 is a portable + definition for C89, due to the way signed->unsigned + conversion is defined. */ +#ifdef SIZE_MAX +#define PY_SIZE_MAX SIZE_MAX +#else +#define PY_SIZE_MAX ((size_t)-1) +#endif + +/* Largest positive value of type Py_ssize_t. */ +#define PY_SSIZE_T_MAX ((Py_ssize_t)(((size_t)-1)>>1)) +/* Smallest negative value of type Py_ssize_t. */ +#define PY_SSIZE_T_MIN (-PY_SSIZE_T_MAX-1) + +#if SIZEOF_PID_T > SIZEOF_LONG +# error "Python doesn't support sizeof(pid_t) > sizeof(long)" +#endif + +/* PY_FORMAT_SIZE_T is a platform-specific modifier for use in a printf + * format to convert an argument with the width of a size_t or Py_ssize_t. + * C99 introduced "z" for this purpose, but not all platforms support that; + * e.g., MS compilers use "I" instead. + * + * These "high level" Python format functions interpret "z" correctly on + * all platforms (Python interprets the format string itself, and does whatever + * the platform C requires to convert a size_t/Py_ssize_t argument): + * + * PyString_FromFormat + * PyErr_Format + * PyString_FromFormatV + * + * Lower-level uses require that you interpolate the correct format modifier + * yourself (e.g., calling printf, fprintf, sprintf, PyOS_snprintf); for + * example, + * + * Py_ssize_t index; + * fprintf(stderr, "index %" PY_FORMAT_SIZE_T "d sucks\n", index); + * + * That will expand to %ld, or %Id, or to something else correct for a + * Py_ssize_t on the platform. + */ +#ifndef PY_FORMAT_SIZE_T +# if SIZEOF_SIZE_T == SIZEOF_INT && !defined(__APPLE__) +# define PY_FORMAT_SIZE_T "" +# elif SIZEOF_SIZE_T == SIZEOF_LONG +# define PY_FORMAT_SIZE_T "l" +# elif defined(MS_WINDOWS) +# define PY_FORMAT_SIZE_T "I" +# else +# error "This platform's pyconfig.h needs to define PY_FORMAT_SIZE_T" +# endif +#endif + +/* PY_FORMAT_LONG_LONG is analogous to PY_FORMAT_SIZE_T above, but for + * the long long type instead of the size_t type. It's only available + * when HAVE_LONG_LONG is defined. The "high level" Python format + * functions listed above will interpret "lld" or "llu" correctly on + * all platforms. + */ +#ifdef HAVE_LONG_LONG +# ifndef PY_FORMAT_LONG_LONG +# if defined(MS_WIN64) || defined(MS_WINDOWS) +# define PY_FORMAT_LONG_LONG "I64" +# else +# error "This platform's pyconfig.h needs to define PY_FORMAT_LONG_LONG" +# endif +# endif +#endif + +/* Py_LOCAL can be used instead of static to get the fastest possible calling + * convention for functions that are local to a given module. + * + * Py_LOCAL_INLINE does the same thing, and also explicitly requests inlining, + * for platforms that support that. + * + * If PY_LOCAL_AGGRESSIVE is defined before python.h is included, more + * "aggressive" inlining/optimizaion is enabled for the entire module. This + * may lead to code bloat, and may slow things down for those reasons. It may + * also lead to errors, if the code relies on pointer aliasing. Use with + * care. + * + * NOTE: You can only use this for functions that are entirely local to a + * module; functions that are exported via method tables, callbacks, etc, + * should keep using static. + */ + +#undef USE_INLINE /* XXX - set via configure? */ + +#if defined(_MSC_VER) +#if defined(PY_LOCAL_AGGRESSIVE) +/* enable more aggressive optimization for visual studio */ +#pragma optimize("agtw", on) +#endif +/* ignore warnings if the compiler decides not to inline a function */ +#pragma warning(disable: 4710) +/* fastest possible local call under MSVC */ +#define Py_LOCAL(type) static type __fastcall +#define Py_LOCAL_INLINE(type) static __inline type __fastcall +#elif defined(USE_INLINE) +#define Py_LOCAL(type) static type +#define Py_LOCAL_INLINE(type) static inline type +#else +#define Py_LOCAL(type) static type +#define Py_LOCAL_INLINE(type) static type +#endif + +/* Py_MEMCPY can be used instead of memcpy in cases where the copied blocks + * are often very short. While most platforms have highly optimized code for + * large transfers, the setup costs for memcpy are often quite high. MEMCPY + * solves this by doing short copies "in line". + */ + +#if defined(_MSC_VER) +#define Py_MEMCPY(target, source, length) do { \ + size_t i_, n_ = (length); \ + char *t_ = (void*) (target); \ + const char *s_ = (void*) (source); \ + if (n_ >= 16) \ + memcpy(t_, s_, n_); \ + else \ + for (i_ = 0; i_ < n_; i_++) \ + t_[i_] = s_[i_]; \ + } while (0) +#else +#define Py_MEMCPY memcpy +#endif + +#include + +#ifdef HAVE_IEEEFP_H +#include /* needed for 'finite' declaration on some platforms */ +#endif + +#include /* Moved here from the math section, before extern "C" */ + +/******************************************** + * WRAPPER FOR and/or * + ********************************************/ + +#ifdef TIME_WITH_SYS_TIME +#include +#include +#else /* !TIME_WITH_SYS_TIME */ +#ifdef HAVE_SYS_TIME_H +#include +#else /* !HAVE_SYS_TIME_H */ +#include +#endif /* !HAVE_SYS_TIME_H */ +#endif /* !TIME_WITH_SYS_TIME */ + + +/****************************** + * WRAPPER FOR * + ******************************/ + +/* NB caller must include */ + +#ifdef HAVE_SYS_SELECT_H + +#include + +#endif /* !HAVE_SYS_SELECT_H */ + +/******************************* + * stat() and fstat() fiddling * + *******************************/ + +/* We expect that stat and fstat exist on most systems. + * It's confirmed on Unix, Mac and Windows. + * If you don't have them, add + * #define DONT_HAVE_STAT + * and/or + * #define DONT_HAVE_FSTAT + * to your pyconfig.h. Python code beyond this should check HAVE_STAT and + * HAVE_FSTAT instead. + * Also + * #define HAVE_SYS_STAT_H + * if exists on your platform, and + * #define HAVE_STAT_H + * if does. + */ +#ifndef DONT_HAVE_STAT +#define HAVE_STAT +#endif + +#ifndef DONT_HAVE_FSTAT +#define HAVE_FSTAT +#endif + +#ifdef RISCOS +#include +#include "unixstuff.h" +#endif + +#ifdef HAVE_SYS_STAT_H +#if defined(PYOS_OS2) && defined(PYCC_GCC) +#include +#endif +#include +#elif defined(HAVE_STAT_H) +#include +#endif + +#if defined(PYCC_VACPP) +/* VisualAge C/C++ Failed to Define MountType Field in sys/stat.h */ +#define S_IFMT (S_IFDIR|S_IFCHR|S_IFREG) +#endif + +#ifndef S_ISREG +#define S_ISREG(x) (((x) & S_IFMT) == S_IFREG) +#endif + +#ifndef S_ISDIR +#define S_ISDIR(x) (((x) & S_IFMT) == S_IFDIR) +#endif + + +#ifdef __cplusplus +/* Move this down here since some C++ #include's don't like to be included + inside an extern "C" */ +extern "C" { +#endif + + +/* Py_ARITHMETIC_RIGHT_SHIFT + * C doesn't define whether a right-shift of a signed integer sign-extends + * or zero-fills. Here a macro to force sign extension: + * Py_ARITHMETIC_RIGHT_SHIFT(TYPE, I, J) + * Return I >> J, forcing sign extension. Arithmetically, return the + * floor of I/2**J. + * Requirements: + * I should have signed integer type. In the terminology of C99, this can + * be either one of the five standard signed integer types (signed char, + * short, int, long, long long) or an extended signed integer type. + * J is an integer >= 0 and strictly less than the number of bits in the + * type of I (because C doesn't define what happens for J outside that + * range either). + * TYPE used to specify the type of I, but is now ignored. It's been left + * in for backwards compatibility with versions <= 2.6 or 3.0. + * Caution: + * I may be evaluated more than once. + */ +#ifdef SIGNED_RIGHT_SHIFT_ZERO_FILLS +#define Py_ARITHMETIC_RIGHT_SHIFT(TYPE, I, J) \ + ((I) < 0 ? -1-((-1-(I)) >> (J)) : (I) >> (J)) +#else +#define Py_ARITHMETIC_RIGHT_SHIFT(TYPE, I, J) ((I) >> (J)) +#endif + +/* Py_FORCE_EXPANSION(X) + * "Simply" returns its argument. However, macro expansions within the + * argument are evaluated. This unfortunate trickery is needed to get + * token-pasting to work as desired in some cases. + */ +#define Py_FORCE_EXPANSION(X) X + +/* Py_SAFE_DOWNCAST(VALUE, WIDE, NARROW) + * Cast VALUE to type NARROW from type WIDE. In Py_DEBUG mode, this + * assert-fails if any information is lost. + * Caution: + * VALUE may be evaluated more than once. + */ +#ifdef Py_DEBUG +#define Py_SAFE_DOWNCAST(VALUE, WIDE, NARROW) \ + (assert((WIDE)(NARROW)(VALUE) == (VALUE)), (NARROW)(VALUE)) +#else +#define Py_SAFE_DOWNCAST(VALUE, WIDE, NARROW) (NARROW)(VALUE) +#endif + +/* Py_SET_ERRNO_ON_MATH_ERROR(x) + * If a libm function did not set errno, but it looks like the result + * overflowed or not-a-number, set errno to ERANGE or EDOM. Set errno + * to 0 before calling a libm function, and invoke this macro after, + * passing the function result. + * Caution: + * This isn't reliable. See Py_OVERFLOWED comments. + * X is evaluated more than once. + */ +#if defined(__FreeBSD__) || defined(__OpenBSD__) || (defined(__hpux) && defined(__ia64)) +#define _Py_SET_EDOM_FOR_NAN(X) if (isnan(X)) errno = EDOM; +#else +#define _Py_SET_EDOM_FOR_NAN(X) ; +#endif +#define Py_SET_ERRNO_ON_MATH_ERROR(X) \ + do { \ + if (errno == 0) { \ + if ((X) == Py_HUGE_VAL || (X) == -Py_HUGE_VAL) \ + errno = ERANGE; \ + else _Py_SET_EDOM_FOR_NAN(X) \ + } \ + } while(0) + +/* Py_SET_ERANGE_ON_OVERFLOW(x) + * An alias of Py_SET_ERRNO_ON_MATH_ERROR for backward-compatibility. + */ +#define Py_SET_ERANGE_IF_OVERFLOW(X) Py_SET_ERRNO_ON_MATH_ERROR(X) + +/* Py_ADJUST_ERANGE1(x) + * Py_ADJUST_ERANGE2(x, y) + * Set errno to 0 before calling a libm function, and invoke one of these + * macros after, passing the function result(s) (Py_ADJUST_ERANGE2 is useful + * for functions returning complex results). This makes two kinds of + * adjustments to errno: (A) If it looks like the platform libm set + * errno=ERANGE due to underflow, clear errno. (B) If it looks like the + * platform libm overflowed but didn't set errno, force errno to ERANGE. In + * effect, we're trying to force a useful implementation of C89 errno + * behavior. + * Caution: + * This isn't reliable. See Py_OVERFLOWED comments. + * X and Y may be evaluated more than once. + */ +#define Py_ADJUST_ERANGE1(X) \ + do { \ + if (errno == 0) { \ + if ((X) == Py_HUGE_VAL || (X) == -Py_HUGE_VAL) \ + errno = ERANGE; \ + } \ + else if (errno == ERANGE && (X) == 0.0) \ + errno = 0; \ + } while(0) + +#define Py_ADJUST_ERANGE2(X, Y) \ + do { \ + if ((X) == Py_HUGE_VAL || (X) == -Py_HUGE_VAL || \ + (Y) == Py_HUGE_VAL || (Y) == -Py_HUGE_VAL) { \ + if (errno == 0) \ + errno = ERANGE; \ + } \ + else if (errno == ERANGE) \ + errno = 0; \ + } while(0) + +/* The functions _Py_dg_strtod and _Py_dg_dtoa in Python/dtoa.c (which are + * required to support the short float repr introduced in Python 3.1) require + * that the floating-point unit that's being used for arithmetic operations + * on C doubles is set to use 53-bit precision. It also requires that the + * FPU rounding mode is round-half-to-even, but that's less often an issue. + * + * If your FPU isn't already set to 53-bit precision/round-half-to-even, and + * you want to make use of _Py_dg_strtod and _Py_dg_dtoa, then you should + * + * #define HAVE_PY_SET_53BIT_PRECISION 1 + * + * and also give appropriate definitions for the following three macros: + * + * _PY_SET_53BIT_PRECISION_START : store original FPU settings, and + * set FPU to 53-bit precision/round-half-to-even + * _PY_SET_53BIT_PRECISION_END : restore original FPU settings + * _PY_SET_53BIT_PRECISION_HEADER : any variable declarations needed to + * use the two macros above. + * + * The macros are designed to be used within a single C function: see + * Python/pystrtod.c for an example of their use. + */ + +/* get and set x87 control word for gcc/x86 */ +#ifdef HAVE_GCC_ASM_FOR_X87 +#define HAVE_PY_SET_53BIT_PRECISION 1 +/* _Py_get/set_387controlword functions are defined in Python/pymath.c */ +#define _Py_SET_53BIT_PRECISION_HEADER \ + unsigned short old_387controlword, new_387controlword +#define _Py_SET_53BIT_PRECISION_START \ + do { \ + old_387controlword = _Py_get_387controlword(); \ + new_387controlword = (old_387controlword & ~0x0f00) | 0x0200; \ + if (new_387controlword != old_387controlword) \ + _Py_set_387controlword(new_387controlword); \ + } while (0) +#define _Py_SET_53BIT_PRECISION_END \ + if (new_387controlword != old_387controlword) \ + _Py_set_387controlword(old_387controlword) +#endif + +/* get and set x87 control word for VisualStudio/x86 */ +#if defined(_MSC_VER) && !defined(_WIN64) /* x87 not supported in 64-bit */ +#define HAVE_PY_SET_53BIT_PRECISION 1 +#define _Py_SET_53BIT_PRECISION_HEADER \ + unsigned int old_387controlword, new_387controlword, out_387controlword +/* We use the __control87_2 function to set only the x87 control word. + The SSE control word is unaffected. */ +#define _Py_SET_53BIT_PRECISION_START \ + do { \ + __control87_2(0, 0, &old_387controlword, NULL); \ + new_387controlword = \ + (old_387controlword & ~(_MCW_PC | _MCW_RC)) | (_PC_53 | _RC_NEAR); \ + if (new_387controlword != old_387controlword) \ + __control87_2(new_387controlword, _MCW_PC | _MCW_RC, \ + &out_387controlword, NULL); \ + } while (0) +#define _Py_SET_53BIT_PRECISION_END \ + do { \ + if (new_387controlword != old_387controlword) \ + __control87_2(old_387controlword, _MCW_PC | _MCW_RC, \ + &out_387controlword, NULL); \ + } while (0) +#endif + +/* default definitions are empty */ +#ifndef HAVE_PY_SET_53BIT_PRECISION +#define _Py_SET_53BIT_PRECISION_HEADER +#define _Py_SET_53BIT_PRECISION_START +#define _Py_SET_53BIT_PRECISION_END +#endif + +/* If we can't guarantee 53-bit precision, don't use the code + in Python/dtoa.c, but fall back to standard code. This + means that repr of a float will be long (17 sig digits). + + Realistically, there are two things that could go wrong: + + (1) doubles aren't IEEE 754 doubles, or + (2) we're on x86 with the rounding precision set to 64-bits + (extended precision), and we don't know how to change + the rounding precision. + */ + +#if !defined(DOUBLE_IS_LITTLE_ENDIAN_IEEE754) && \ + !defined(DOUBLE_IS_BIG_ENDIAN_IEEE754) && \ + !defined(DOUBLE_IS_ARM_MIXED_ENDIAN_IEEE754) +#define PY_NO_SHORT_FLOAT_REPR +#endif + +/* double rounding is symptomatic of use of extended precision on x86. If + we're seeing double rounding, and we don't have any mechanism available for + changing the FPU rounding precision, then don't use Python/dtoa.c. */ +#if defined(X87_DOUBLE_ROUNDING) && !defined(HAVE_PY_SET_53BIT_PRECISION) +#define PY_NO_SHORT_FLOAT_REPR +#endif + +/* Py_DEPRECATED(version) + * Declare a variable, type, or function deprecated. + * Usage: + * extern int old_var Py_DEPRECATED(2.3); + * typedef int T1 Py_DEPRECATED(2.4); + * extern int x() Py_DEPRECATED(2.5); + */ +#if defined(__GNUC__) && ((__GNUC__ >= 4) || \ + (__GNUC__ == 3) && (__GNUC_MINOR__ >= 1)) +#define Py_DEPRECATED(VERSION_UNUSED) __attribute__((__deprecated__)) +#else +#define Py_DEPRECATED(VERSION_UNUSED) +#endif + +/************************************************************************** +Prototypes that are missing from the standard include files on some systems +(and possibly only some versions of such systems.) + +Please be conservative with adding new ones, document them and enclose them +in platform-specific #ifdefs. +**************************************************************************/ + +#ifdef SOLARIS +/* Unchecked */ +extern int gethostname(char *, int); +#endif + +#ifdef __BEOS__ +/* Unchecked */ +/* It's in the libs, but not the headers... - [cjh] */ +int shutdown( int, int ); +#endif + +#ifdef HAVE__GETPTY +#include /* we need to import mode_t */ +extern char * _getpty(int *, int, mode_t, int); +#endif + +/* On QNX 6, struct termio must be declared by including sys/termio.h + if TCGETA, TCSETA, TCSETAW, or TCSETAF are used. sys/termio.h must + be included before termios.h or it will generate an error. */ +#if defined(HAVE_SYS_TERMIO_H) && !defined(__hpux) +#include +#endif + +#if defined(HAVE_OPENPTY) || defined(HAVE_FORKPTY) +#if !defined(HAVE_PTY_H) && !defined(HAVE_LIBUTIL_H) && !defined(HAVE_UTIL_H) +/* BSDI does not supply a prototype for the 'openpty' and 'forkpty' + functions, even though they are included in libutil. */ +#include +extern int openpty(int *, int *, char *, struct termios *, struct winsize *); +extern pid_t forkpty(int *, char *, struct termios *, struct winsize *); +#endif /* !defined(HAVE_PTY_H) && !defined(HAVE_LIBUTIL_H) */ +#endif /* defined(HAVE_OPENPTY) || defined(HAVE_FORKPTY) */ + + +/* These are pulled from various places. It isn't obvious on what platforms + they are necessary, nor what the exact prototype should look like (which + is likely to vary between platforms!) If you find you need one of these + declarations, please move them to a platform-specific block and include + proper prototypes. */ +#if 0 + +/* From Modules/resource.c */ +extern int getrusage(); +extern int getpagesize(); + +/* From Python/sysmodule.c and Modules/posixmodule.c */ +extern int fclose(FILE *); + +/* From Modules/posixmodule.c */ +extern int fdatasync(int); +#endif /* 0 */ + + +/* On 4.4BSD-descendants, ctype functions serves the whole range of + * wchar_t character set rather than single byte code points only. + * This characteristic can break some operations of string object + * including str.upper() and str.split() on UTF-8 locales. This + * workaround was provided by Tim Robbins of FreeBSD project. + */ + +#ifdef __FreeBSD__ +#include +#if __FreeBSD_version > 500039 +# define _PY_PORT_CTYPE_UTF8_ISSUE +#endif +#endif + + +#if defined(__APPLE__) +# define _PY_PORT_CTYPE_UTF8_ISSUE +#endif + +#ifdef _PY_PORT_CTYPE_UTF8_ISSUE +#include +#include +#undef isalnum +#define isalnum(c) iswalnum(btowc(c)) +#undef isalpha +#define isalpha(c) iswalpha(btowc(c)) +#undef islower +#define islower(c) iswlower(btowc(c)) +#undef isspace +#define isspace(c) iswspace(btowc(c)) +#undef isupper +#define isupper(c) iswupper(btowc(c)) +#undef tolower +#define tolower(c) towlower(btowc(c)) +#undef toupper +#define toupper(c) towupper(btowc(c)) +#endif + + +/* Declarations for symbol visibility. + + PyAPI_FUNC(type): Declares a public Python API function and return type + PyAPI_DATA(type): Declares public Python data and its type + PyMODINIT_FUNC: A Python module init function. If these functions are + inside the Python core, they are private to the core. + If in an extension module, it may be declared with + external linkage depending on the platform. + + As a number of platforms support/require "__declspec(dllimport/dllexport)", + we support a HAVE_DECLSPEC_DLL macro to save duplication. +*/ + +/* + All windows ports, except cygwin, are handled in PC/pyconfig.h. + + BeOS and cygwin are the only other autoconf platform requiring special + linkage handling and both of these use __declspec(). +*/ +#if defined(__CYGWIN__) || defined(__BEOS__) +# define HAVE_DECLSPEC_DLL +#endif + +/* only get special linkage if built as shared or platform is Cygwin */ +#if defined(Py_ENABLE_SHARED) || defined(__CYGWIN__) +# if defined(HAVE_DECLSPEC_DLL) +# ifdef Py_BUILD_CORE +# define PyAPI_FUNC(RTYPE) __declspec(dllexport) RTYPE +# define PyAPI_DATA(RTYPE) extern __declspec(dllexport) RTYPE + /* module init functions inside the core need no external linkage */ + /* except for Cygwin to handle embedding (FIXME: BeOS too?) */ +# if defined(__CYGWIN__) +# define PyMODINIT_FUNC __declspec(dllexport) void +# else /* __CYGWIN__ */ +# define PyMODINIT_FUNC void +# endif /* __CYGWIN__ */ +# else /* Py_BUILD_CORE */ + /* Building an extension module, or an embedded situation */ + /* public Python functions and data are imported */ + /* Under Cygwin, auto-import functions to prevent compilation */ + /* failures similar to those described at the bottom of 4.1: */ + /* http://docs.python.org/extending/windows.html#a-cookbook-approach */ +# if !defined(__CYGWIN__) +# define PyAPI_FUNC(RTYPE) __declspec(dllimport) RTYPE +# endif /* !__CYGWIN__ */ +# define PyAPI_DATA(RTYPE) extern __declspec(dllimport) RTYPE + /* module init functions outside the core must be exported */ +# if defined(__cplusplus) +# define PyMODINIT_FUNC extern "C" __declspec(dllexport) void +# else /* __cplusplus */ +# define PyMODINIT_FUNC __declspec(dllexport) void +# endif /* __cplusplus */ +# endif /* Py_BUILD_CORE */ +# endif /* HAVE_DECLSPEC */ +#endif /* Py_ENABLE_SHARED */ + +/* If no external linkage macros defined by now, create defaults */ +#ifndef PyAPI_FUNC +# define PyAPI_FUNC(RTYPE) RTYPE +#endif +#ifndef PyAPI_DATA +# define PyAPI_DATA(RTYPE) extern RTYPE +#endif +#ifndef PyMODINIT_FUNC +# if defined(__cplusplus) +# define PyMODINIT_FUNC extern "C" void +# else /* __cplusplus */ +# define PyMODINIT_FUNC void +# endif /* __cplusplus */ +#endif + +/* Deprecated DL_IMPORT and DL_EXPORT macros */ +#if defined(Py_ENABLE_SHARED) && defined (HAVE_DECLSPEC_DLL) +# if defined(Py_BUILD_CORE) +# define DL_IMPORT(RTYPE) __declspec(dllexport) RTYPE +# define DL_EXPORT(RTYPE) __declspec(dllexport) RTYPE +# else +# define DL_IMPORT(RTYPE) __declspec(dllimport) RTYPE +# define DL_EXPORT(RTYPE) __declspec(dllexport) RTYPE +# endif +#endif +#ifndef DL_EXPORT +# define DL_EXPORT(RTYPE) RTYPE +#endif +#ifndef DL_IMPORT +# define DL_IMPORT(RTYPE) RTYPE +#endif +/* End of deprecated DL_* macros */ + +/* If the fd manipulation macros aren't defined, + here is a set that should do the job */ + +#if 0 /* disabled and probably obsolete */ + +#ifndef FD_SETSIZE +#define FD_SETSIZE 256 +#endif + +#ifndef FD_SET + +typedef long fd_mask; + +#define NFDBITS (sizeof(fd_mask) * NBBY) /* bits per mask */ +#ifndef howmany +#define howmany(x, y) (((x)+((y)-1))/(y)) +#endif /* howmany */ + +typedef struct fd_set { + fd_mask fds_bits[howmany(FD_SETSIZE, NFDBITS)]; +} fd_set; + +#define FD_SET(n, p) ((p)->fds_bits[(n)/NFDBITS] |= (1 << ((n) % NFDBITS))) +#define FD_CLR(n, p) ((p)->fds_bits[(n)/NFDBITS] &= ~(1 << ((n) % NFDBITS))) +#define FD_ISSET(n, p) ((p)->fds_bits[(n)/NFDBITS] & (1 << ((n) % NFDBITS))) +#define FD_ZERO(p) memset((char *)(p), '\0', sizeof(*(p))) + +#endif /* FD_SET */ + +#endif /* fd manipulation macros */ + + +/* limits.h constants that may be missing */ + +#ifndef INT_MAX +#define INT_MAX 2147483647 +#endif + +#ifndef LONG_MAX +#if SIZEOF_LONG == 4 +#define LONG_MAX 0X7FFFFFFFL +#elif SIZEOF_LONG == 8 +#define LONG_MAX 0X7FFFFFFFFFFFFFFFL +#else +#error "could not set LONG_MAX in pyport.h" +#endif +#endif + +#ifndef LONG_MIN +#define LONG_MIN (-LONG_MAX-1) +#endif + +#ifndef LONG_BIT +#define LONG_BIT (8 * SIZEOF_LONG) +#endif + +#if LONG_BIT != 8 * SIZEOF_LONG +/* 04-Oct-2000 LONG_BIT is apparently (mis)defined as 64 on some recent + * 32-bit platforms using gcc. We try to catch that here at compile-time + * rather than waiting for integer multiplication to trigger bogus + * overflows. + */ +#error "LONG_BIT definition appears wrong for platform (bad gcc/glibc config?)." +#endif + +#ifdef __cplusplus +} +#endif + +/* + * Hide GCC attributes from compilers that don't support them. + */ +#if (!defined(__GNUC__) || __GNUC__ < 2 || \ + (__GNUC__ == 2 && __GNUC_MINOR__ < 7) ) && \ + !defined(RISCOS) +#define Py_GCC_ATTRIBUTE(x) +#else +#define Py_GCC_ATTRIBUTE(x) __attribute__(x) +#endif + +/* + * Add PyArg_ParseTuple format where available. + */ +#ifdef HAVE_ATTRIBUTE_FORMAT_PARSETUPLE +#define Py_FORMAT_PARSETUPLE(func,p1,p2) __attribute__((format(func,p1,p2))) +#else +#define Py_FORMAT_PARSETUPLE(func,p1,p2) +#endif + +/* + * Specify alignment on compilers that support it. + */ +#if defined(__GNUC__) && __GNUC__ >= 3 +#define Py_ALIGNED(x) __attribute__((aligned(x))) +#else +#define Py_ALIGNED(x) +#endif + +/* Eliminate end-of-loop code not reached warnings from SunPro C + * when using do{...}while(0) macros + */ +#ifdef __SUNPRO_C +#pragma error_messages (off,E_END_OF_LOOP_CODE_NOT_REACHED) +#endif + +/* + * Older Microsoft compilers don't support the C99 long long literal suffixes, + * so these will be defined in PC/pyconfig.h for those compilers. + */ +#ifndef Py_LL +#define Py_LL(x) x##LL +#endif + +#ifndef Py_ULL +#define Py_ULL(x) Py_LL(x##U) +#endif + +#endif /* Py_PYPORT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/pystate.h b/AppPkg/Applications/Python/Python-2.7.10/Include/pystate.h new file mode 100644 index 0000000000..62ada41452 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/pystate.h @@ -0,0 +1,200 @@ + +/* Thread and interpreter state structures and their interfaces */ + + +#ifndef Py_PYSTATE_H +#define Py_PYSTATE_H +#ifdef __cplusplus +extern "C" { +#endif + +/* State shared between threads */ + +struct _ts; /* Forward */ +struct _is; /* Forward */ + +typedef struct _is { + + struct _is *next; + struct _ts *tstate_head; + + PyObject *modules; + PyObject *sysdict; + PyObject *builtins; + PyObject *modules_reloading; + + PyObject *codec_search_path; + PyObject *codec_search_cache; + PyObject *codec_error_registry; + +#ifdef HAVE_DLOPEN + int dlopenflags; +#endif +#ifdef WITH_TSC + int tscdump; +#endif + +} PyInterpreterState; + + +/* State unique per thread */ + +struct _frame; /* Avoid including frameobject.h */ + +/* Py_tracefunc return -1 when raising an exception, or 0 for success. */ +typedef int (*Py_tracefunc)(PyObject *, struct _frame *, int, PyObject *); + +/* The following values are used for 'what' for tracefunc functions: */ +#define PyTrace_CALL 0 +#define PyTrace_EXCEPTION 1 +#define PyTrace_LINE 2 +#define PyTrace_RETURN 3 +#define PyTrace_C_CALL 4 +#define PyTrace_C_EXCEPTION 5 +#define PyTrace_C_RETURN 6 + +typedef struct _ts { + /* See Python/ceval.c for comments explaining most fields */ + + struct _ts *next; + PyInterpreterState *interp; + + struct _frame *frame; + int recursion_depth; + /* 'tracing' keeps track of the execution depth when tracing/profiling. + This is to prevent the actual trace/profile code from being recorded in + the trace/profile. */ + int tracing; + int use_tracing; + + Py_tracefunc c_profilefunc; + Py_tracefunc c_tracefunc; + PyObject *c_profileobj; + PyObject *c_traceobj; + + PyObject *curexc_type; + PyObject *curexc_value; + PyObject *curexc_traceback; + + PyObject *exc_type; + PyObject *exc_value; + PyObject *exc_traceback; + + PyObject *dict; /* Stores per-thread state */ + + /* tick_counter is incremented whenever the check_interval ticker + * reaches zero. The purpose is to give a useful measure of the number + * of interpreted bytecode instructions in a given thread. This + * extremely lightweight statistic collector may be of interest to + * profilers (like psyco.jit()), although nothing in the core uses it. + */ + int tick_counter; + + int gilstate_counter; + + PyObject *async_exc; /* Asynchronous exception to raise */ + long thread_id; /* Thread id where this tstate was created */ + + int trash_delete_nesting; + PyObject *trash_delete_later; + + /* XXX signal handlers should also be here */ + +} PyThreadState; + + +PyAPI_FUNC(PyInterpreterState *) PyInterpreterState_New(void); +PyAPI_FUNC(void) PyInterpreterState_Clear(PyInterpreterState *); +PyAPI_FUNC(void) PyInterpreterState_Delete(PyInterpreterState *); + +PyAPI_FUNC(PyThreadState *) PyThreadState_New(PyInterpreterState *); +PyAPI_FUNC(PyThreadState *) _PyThreadState_Prealloc(PyInterpreterState *); +PyAPI_FUNC(void) _PyThreadState_Init(PyThreadState *); +PyAPI_FUNC(void) PyThreadState_Clear(PyThreadState *); +PyAPI_FUNC(void) PyThreadState_Delete(PyThreadState *); +#ifdef WITH_THREAD +PyAPI_FUNC(void) PyThreadState_DeleteCurrent(void); +#endif + +PyAPI_FUNC(PyThreadState *) PyThreadState_Get(void); +PyAPI_FUNC(PyThreadState *) PyThreadState_Swap(PyThreadState *); +PyAPI_FUNC(PyObject *) PyThreadState_GetDict(void); +PyAPI_FUNC(int) PyThreadState_SetAsyncExc(long, PyObject *); + + +/* Variable and macro for in-line access to current thread state */ + +PyAPI_DATA(PyThreadState *) _PyThreadState_Current; + +#ifdef Py_DEBUG +#define PyThreadState_GET() PyThreadState_Get() +#else +#define PyThreadState_GET() (_PyThreadState_Current) +#endif + +typedef + enum {PyGILState_LOCKED, PyGILState_UNLOCKED} + PyGILState_STATE; + +/* Ensure that the current thread is ready to call the Python + C API, regardless of the current state of Python, or of its + thread lock. This may be called as many times as desired + by a thread so long as each call is matched with a call to + PyGILState_Release(). In general, other thread-state APIs may + be used between _Ensure() and _Release() calls, so long as the + thread-state is restored to its previous state before the Release(). + For example, normal use of the Py_BEGIN_ALLOW_THREADS/ + Py_END_ALLOW_THREADS macros are acceptable. + + The return value is an opaque "handle" to the thread state when + PyGILState_Ensure() was called, and must be passed to + PyGILState_Release() to ensure Python is left in the same state. Even + though recursive calls are allowed, these handles can *not* be shared - + each unique call to PyGILState_Ensure must save the handle for its + call to PyGILState_Release. + + When the function returns, the current thread will hold the GIL. + + Failure is a fatal error. +*/ +PyAPI_FUNC(PyGILState_STATE) PyGILState_Ensure(void); + +/* Release any resources previously acquired. After this call, Python's + state will be the same as it was prior to the corresponding + PyGILState_Ensure() call (but generally this state will be unknown to + the caller, hence the use of the GILState API.) + + Every call to PyGILState_Ensure must be matched by a call to + PyGILState_Release on the same thread. +*/ +PyAPI_FUNC(void) PyGILState_Release(PyGILState_STATE); + +/* Helper/diagnostic function - get the current thread state for + this thread. May return NULL if no GILState API has been used + on the current thread. Note that the main thread always has such a + thread-state, even if no auto-thread-state call has been made + on the main thread. +*/ +PyAPI_FUNC(PyThreadState *) PyGILState_GetThisThreadState(void); + +/* The implementation of sys._current_frames() Returns a dict mapping + thread id to that thread's current frame. +*/ +PyAPI_FUNC(PyObject *) _PyThread_CurrentFrames(void); + +/* Routines for advanced debuggers, requested by David Beazley. + Don't use unless you know what you are doing! */ +PyAPI_FUNC(PyInterpreterState *) PyInterpreterState_Head(void); +PyAPI_FUNC(PyInterpreterState *) PyInterpreterState_Next(PyInterpreterState *); +PyAPI_FUNC(PyThreadState *) PyInterpreterState_ThreadHead(PyInterpreterState *); +PyAPI_FUNC(PyThreadState *) PyThreadState_Next(PyThreadState *); + +typedef struct _frame *(*PyThreadFrameGetter)(PyThreadState *self_); + +/* hook for PyEval_GetFrame(), requested for Psyco */ +PyAPI_DATA(PyThreadFrameGetter) _PyThreadState_GetFrame; + +#ifdef __cplusplus +} +#endif +#endif /* !Py_PYSTATE_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/pystrcmp.h b/AppPkg/Applications/Python/Python-2.7.10/Include/pystrcmp.h new file mode 100644 index 0000000000..542399de36 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/pystrcmp.h @@ -0,0 +1,23 @@ +#ifndef Py_STRCMP_H +#define Py_STRCMP_H + +#ifdef __cplusplus +extern "C" { +#endif + +PyAPI_FUNC(int) PyOS_mystrnicmp(const char *, const char *, Py_ssize_t); +PyAPI_FUNC(int) PyOS_mystricmp(const char *, const char *); + +#if defined(MS_WINDOWS) || defined(PYOS_OS2) +#define PyOS_strnicmp strnicmp +#define PyOS_stricmp stricmp +#else +#define PyOS_strnicmp PyOS_mystrnicmp +#define PyOS_stricmp PyOS_mystricmp +#endif + +#ifdef __cplusplus +} +#endif + +#endif /* !Py_STRCMP_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/pystrtod.h b/AppPkg/Applications/Python/Python-2.7.10/Include/pystrtod.h new file mode 100644 index 0000000000..f2ecc60e23 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/pystrtod.h @@ -0,0 +1,45 @@ +#ifndef Py_STRTOD_H +#define Py_STRTOD_H + +#ifdef __cplusplus +extern "C" { +#endif + + +PyAPI_FUNC(double) PyOS_ascii_strtod(const char *str, char **ptr); +PyAPI_FUNC(double) PyOS_ascii_atof(const char *str); + +/* Deprecated in 2.7 and 3.1. Will disappear in 2.8 (if it exists) and 3.2 */ +PyAPI_FUNC(char *) PyOS_ascii_formatd(char *buffer, size_t buf_len, + const char *format, double d); +PyAPI_FUNC(double) PyOS_string_to_double(const char *str, + char **endptr, + PyObject *overflow_exception); + +/* The caller is responsible for calling PyMem_Free to free the buffer + that's is returned. */ +PyAPI_FUNC(char *) PyOS_double_to_string(double val, + char format_code, + int precision, + int flags, + int *type); + +PyAPI_FUNC(double) _Py_parse_inf_or_nan(const char *p, char **endptr); + + +/* PyOS_double_to_string's "flags" parameter can be set to 0 or more of: */ +#define Py_DTSF_SIGN 0x01 /* always add the sign */ +#define Py_DTSF_ADD_DOT_0 0x02 /* if the result is an integer add ".0" */ +#define Py_DTSF_ALT 0x04 /* "alternate" formatting. it's format_code + specific */ + +/* PyOS_double_to_string's "type", if non-NULL, will be set to one of: */ +#define Py_DTST_FINITE 0 +#define Py_DTST_INFINITE 1 +#define Py_DTST_NAN 2 + +#ifdef __cplusplus +} +#endif + +#endif /* !Py_STRTOD_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/pythonrun.h b/AppPkg/Applications/Python/Python-2.7.10/Include/pythonrun.h new file mode 100644 index 0000000000..58e18313e7 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/pythonrun.h @@ -0,0 +1,182 @@ + +/* Interfaces to parse and execute pieces of python code */ + +#ifndef Py_PYTHONRUN_H +#define Py_PYTHONRUN_H +#ifdef __cplusplus +extern "C" { +#endif + +#define PyCF_MASK (CO_FUTURE_DIVISION | CO_FUTURE_ABSOLUTE_IMPORT | \ + CO_FUTURE_WITH_STATEMENT | CO_FUTURE_PRINT_FUNCTION | \ + CO_FUTURE_UNICODE_LITERALS) +#define PyCF_MASK_OBSOLETE (CO_NESTED) +#define PyCF_SOURCE_IS_UTF8 0x0100 +#define PyCF_DONT_IMPLY_DEDENT 0x0200 +#define PyCF_ONLY_AST 0x0400 + +typedef struct { + int cf_flags; /* bitmask of CO_xxx flags relevant to future */ +} PyCompilerFlags; + +PyAPI_FUNC(void) Py_SetProgramName(char *); +PyAPI_FUNC(char *) Py_GetProgramName(void); + +PyAPI_FUNC(void) Py_SetPythonHome(char *); +PyAPI_FUNC(char *) Py_GetPythonHome(void); + +PyAPI_FUNC(void) Py_Initialize(void); +PyAPI_FUNC(void) Py_InitializeEx(int); +PyAPI_FUNC(void) Py_Finalize(void); +PyAPI_FUNC(int) Py_IsInitialized(void); +PyAPI_FUNC(PyThreadState *) Py_NewInterpreter(void); +PyAPI_FUNC(void) Py_EndInterpreter(PyThreadState *); + +PyAPI_FUNC(int) PyRun_AnyFileFlags(FILE *, const char *, PyCompilerFlags *); +PyAPI_FUNC(int) PyRun_AnyFileExFlags(FILE *, const char *, int, PyCompilerFlags *); +PyAPI_FUNC(int) PyRun_SimpleStringFlags(const char *, PyCompilerFlags *); +PyAPI_FUNC(int) PyRun_SimpleFileExFlags(FILE *, const char *, int, PyCompilerFlags *); +PyAPI_FUNC(int) PyRun_InteractiveOneFlags(FILE *, const char *, PyCompilerFlags *); +PyAPI_FUNC(int) PyRun_InteractiveLoopFlags(FILE *, const char *, PyCompilerFlags *); + +PyAPI_FUNC(struct _mod *) PyParser_ASTFromString(const char *, const char *, + int, PyCompilerFlags *flags, + PyArena *); +PyAPI_FUNC(struct _mod *) PyParser_ASTFromFile(FILE *, const char *, int, + char *, char *, + PyCompilerFlags *, int *, + PyArena *); +#define PyParser_SimpleParseString(S, B) \ + PyParser_SimpleParseStringFlags(S, B, 0) +#define PyParser_SimpleParseFile(FP, S, B) \ + PyParser_SimpleParseFileFlags(FP, S, B, 0) +PyAPI_FUNC(struct _node *) PyParser_SimpleParseStringFlags(const char *, int, + int); +PyAPI_FUNC(struct _node *) PyParser_SimpleParseFileFlags(FILE *, const char *, + int, int); + +PyAPI_FUNC(PyObject *) PyRun_StringFlags(const char *, int, PyObject *, + PyObject *, PyCompilerFlags *); + +PyAPI_FUNC(PyObject *) PyRun_FileExFlags(FILE *, const char *, int, + PyObject *, PyObject *, int, + PyCompilerFlags *); + +#define Py_CompileString(str, p, s) Py_CompileStringFlags(str, p, s, NULL) +PyAPI_FUNC(PyObject *) Py_CompileStringFlags(const char *, const char *, int, + PyCompilerFlags *); +PyAPI_FUNC(struct symtable *) Py_SymtableString(const char *, const char *, int); + +PyAPI_FUNC(void) PyErr_Print(void); +PyAPI_FUNC(void) PyErr_PrintEx(int); +PyAPI_FUNC(void) PyErr_Display(PyObject *, PyObject *, PyObject *); + +PyAPI_FUNC(int) Py_AtExit(void (*func)(void)); + +PyAPI_FUNC(void) Py_Exit(int); + +PyAPI_FUNC(int) Py_FdIsInteractive(FILE *, const char *); + +/* Bootstrap */ +PyAPI_FUNC(int) Py_Main(int argc, char **argv); + +/* Use macros for a bunch of old variants */ +#define PyRun_String(str, s, g, l) PyRun_StringFlags(str, s, g, l, NULL) +#define PyRun_AnyFile(fp, name) PyRun_AnyFileExFlags(fp, name, 0, NULL) +#define PyRun_AnyFileEx(fp, name, closeit) \ + PyRun_AnyFileExFlags(fp, name, closeit, NULL) +#define PyRun_AnyFileFlags(fp, name, flags) \ + PyRun_AnyFileExFlags(fp, name, 0, flags) +#define PyRun_SimpleString(s) PyRun_SimpleStringFlags(s, NULL) +#define PyRun_SimpleFile(f, p) PyRun_SimpleFileExFlags(f, p, 0, NULL) +#define PyRun_SimpleFileEx(f, p, c) PyRun_SimpleFileExFlags(f, p, c, NULL) +#define PyRun_InteractiveOne(f, p) PyRun_InteractiveOneFlags(f, p, NULL) +#define PyRun_InteractiveLoop(f, p) PyRun_InteractiveLoopFlags(f, p, NULL) +#define PyRun_File(fp, p, s, g, l) \ + PyRun_FileExFlags(fp, p, s, g, l, 0, NULL) +#define PyRun_FileEx(fp, p, s, g, l, c) \ + PyRun_FileExFlags(fp, p, s, g, l, c, NULL) +#define PyRun_FileFlags(fp, p, s, g, l, flags) \ + PyRun_FileExFlags(fp, p, s, g, l, 0, flags) + +/* In getpath.c */ +PyAPI_FUNC(char *) Py_GetProgramFullPath(void); +PyAPI_FUNC(char *) Py_GetPrefix(void); +PyAPI_FUNC(char *) Py_GetExecPrefix(void); +PyAPI_FUNC(char *) Py_GetPath(void); + +/* In their own files */ +PyAPI_FUNC(const char *) Py_GetVersion(void); +PyAPI_FUNC(const char *) Py_GetPlatform(void); +PyAPI_FUNC(const char *) Py_GetCopyright(void); +PyAPI_FUNC(const char *) Py_GetCompiler(void); +PyAPI_FUNC(const char *) Py_GetBuildInfo(void); +PyAPI_FUNC(const char *) _Py_svnversion(void); +PyAPI_FUNC(const char *) Py_SubversionRevision(void); +PyAPI_FUNC(const char *) Py_SubversionShortBranch(void); +PyAPI_FUNC(const char *) _Py_hgidentifier(void); +PyAPI_FUNC(const char *) _Py_hgversion(void); + +/* Internal -- various one-time initializations */ +PyAPI_FUNC(PyObject *) _PyBuiltin_Init(void); +PyAPI_FUNC(PyObject *) _PySys_Init(void); +PyAPI_FUNC(void) _PyImport_Init(void); +PyAPI_FUNC(void) _PyExc_Init(void); +PyAPI_FUNC(void) _PyImportHooks_Init(void); +PyAPI_FUNC(int) _PyFrame_Init(void); +PyAPI_FUNC(int) _PyInt_Init(void); +PyAPI_FUNC(int) _PyLong_Init(void); +PyAPI_FUNC(void) _PyFloat_Init(void); +PyAPI_FUNC(int) PyByteArray_Init(void); +PyAPI_FUNC(void) _PyRandom_Init(void); + +/* Various internal finalizers */ +PyAPI_FUNC(void) _PyExc_Fini(void); +PyAPI_FUNC(void) _PyImport_Fini(void); +PyAPI_FUNC(void) PyMethod_Fini(void); +PyAPI_FUNC(void) PyFrame_Fini(void); +PyAPI_FUNC(void) PyCFunction_Fini(void); +PyAPI_FUNC(void) PyDict_Fini(void); +PyAPI_FUNC(void) PyTuple_Fini(void); +PyAPI_FUNC(void) PyList_Fini(void); +PyAPI_FUNC(void) PySet_Fini(void); +PyAPI_FUNC(void) PyString_Fini(void); +PyAPI_FUNC(void) PyInt_Fini(void); +PyAPI_FUNC(void) PyFloat_Fini(void); +PyAPI_FUNC(void) PyOS_FiniInterrupts(void); +PyAPI_FUNC(void) PyByteArray_Fini(void); +PyAPI_FUNC(void) _PyRandom_Fini(void); + +/* Stuff with no proper home (yet) */ +PyAPI_FUNC(char *) PyOS_Readline(FILE *, FILE *, char *); +PyAPI_DATA(int) (*PyOS_InputHook)(void); +PyAPI_DATA(char) *(*PyOS_ReadlineFunctionPointer)(FILE *, FILE *, char *); +PyAPI_DATA(PyThreadState*) _PyOS_ReadlineTState; + +/* Stack size, in "pointers" (so we get extra safety margins + on 64-bit platforms). On a 32-bit platform, this translates + to a 8k margin. */ +#define PYOS_STACK_MARGIN 2048 + +#if defined(WIN32) && !defined(MS_WIN64) && defined(_MSC_VER) && _MSC_VER >= 1300 +/* Enable stack checking under Microsoft C */ +#define USE_STACKCHECK +#endif + +#ifdef USE_STACKCHECK +/* Check that we aren't overflowing our stack */ +PyAPI_FUNC(int) PyOS_CheckStack(void); +#endif + +/* Signals */ +typedef void (*PyOS_sighandler_t)(int); +PyAPI_FUNC(PyOS_sighandler_t) PyOS_getsig(int); +PyAPI_FUNC(PyOS_sighandler_t) PyOS_setsig(int, PyOS_sighandler_t); + +/* Random */ +PyAPI_FUNC(int) _PyOS_URandom (void *buffer, Py_ssize_t size); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_PYTHONRUN_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/pythread.h b/AppPkg/Applications/Python/Python-2.7.10/Include/pythread.h new file mode 100644 index 0000000000..d3c587b6f8 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/pythread.h @@ -0,0 +1,41 @@ + +#ifndef Py_PYTHREAD_H +#define Py_PYTHREAD_H + +typedef void *PyThread_type_lock; +typedef void *PyThread_type_sema; + +#ifdef __cplusplus +extern "C" { +#endif + +PyAPI_FUNC(void) PyThread_init_thread(void); +PyAPI_FUNC(long) PyThread_start_new_thread(void (*)(void *), void *); +PyAPI_FUNC(void) PyThread_exit_thread(void); +PyAPI_FUNC(long) PyThread_get_thread_ident(void); + +PyAPI_FUNC(PyThread_type_lock) PyThread_allocate_lock(void); +PyAPI_FUNC(void) PyThread_free_lock(PyThread_type_lock); +PyAPI_FUNC(int) PyThread_acquire_lock(PyThread_type_lock, int); +#define WAIT_LOCK 1 +#define NOWAIT_LOCK 0 +PyAPI_FUNC(void) PyThread_release_lock(PyThread_type_lock); + +PyAPI_FUNC(size_t) PyThread_get_stacksize(void); +PyAPI_FUNC(int) PyThread_set_stacksize(size_t); + +/* Thread Local Storage (TLS) API */ +PyAPI_FUNC(int) PyThread_create_key(void); +PyAPI_FUNC(void) PyThread_delete_key(int); +PyAPI_FUNC(int) PyThread_set_key_value(int, void *); +PyAPI_FUNC(void *) PyThread_get_key_value(int); +PyAPI_FUNC(void) PyThread_delete_key_value(int key); + +/* Cleanup after a fork */ +PyAPI_FUNC(void) PyThread_ReInitTLS(void); + +#ifdef __cplusplus +} +#endif + +#endif /* !Py_PYTHREAD_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/rangeobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/rangeobject.h new file mode 100644 index 0000000000..b8dcb40223 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/rangeobject.h @@ -0,0 +1,28 @@ + +/* Range object interface */ + +#ifndef Py_RANGEOBJECT_H +#define Py_RANGEOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +/* This is about the type 'xrange', not the built-in function range(), which + returns regular lists. */ + +/* +A range object represents an integer range. This is an immutable object; +a range cannot change its value after creation. + +Range objects behave like the corresponding tuple objects except that +they are represented by a start, stop, and step datamembers. +*/ + +PyAPI_DATA(PyTypeObject) PyRange_Type; + +#define PyRange_Check(op) (Py_TYPE(op) == &PyRange_Type) + +#ifdef __cplusplus +} +#endif +#endif /* !Py_RANGEOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/setobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/setobject.h new file mode 100644 index 0000000000..6ded153449 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/setobject.h @@ -0,0 +1,99 @@ +/* Set object interface */ + +#ifndef Py_SETOBJECT_H +#define Py_SETOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + + +/* +There are three kinds of slots in the table: + +1. Unused: key == NULL +2. Active: key != NULL and key != dummy +3. Dummy: key == dummy + +Note: .pop() abuses the hash field of an Unused or Dummy slot to +hold a search finger. The hash field of Unused or Dummy slots has +no meaning otherwise. +*/ + +#define PySet_MINSIZE 8 + +typedef struct { + long hash; /* cached hash code for the entry key */ + PyObject *key; +} setentry; + + +/* +This data structure is shared by set and frozenset objects. +*/ + +typedef struct _setobject PySetObject; +struct _setobject { + PyObject_HEAD + + Py_ssize_t fill; /* # Active + # Dummy */ + Py_ssize_t used; /* # Active */ + + /* The table contains mask + 1 slots, and that's a power of 2. + * We store the mask instead of the size because the mask is more + * frequently needed. + */ + Py_ssize_t mask; + + /* table points to smalltable for small tables, else to + * additional malloc'ed memory. table is never NULL! This rule + * saves repeated runtime null-tests. + */ + setentry *table; + setentry *(*lookup)(PySetObject *so, PyObject *key, long hash); + setentry smalltable[PySet_MINSIZE]; + + long hash; /* only used by frozenset objects */ + PyObject *weakreflist; /* List of weak references */ +}; + +PyAPI_DATA(PyTypeObject) PySet_Type; +PyAPI_DATA(PyTypeObject) PyFrozenSet_Type; + +/* Invariants for frozensets: + * data is immutable. + * hash is the hash of the frozenset or -1 if not computed yet. + * Invariants for sets: + * hash is -1 + */ + +#define PyFrozenSet_CheckExact(ob) (Py_TYPE(ob) == &PyFrozenSet_Type) +#define PyAnySet_CheckExact(ob) \ + (Py_TYPE(ob) == &PySet_Type || Py_TYPE(ob) == &PyFrozenSet_Type) +#define PyAnySet_Check(ob) \ + (Py_TYPE(ob) == &PySet_Type || Py_TYPE(ob) == &PyFrozenSet_Type || \ + PyType_IsSubtype(Py_TYPE(ob), &PySet_Type) || \ + PyType_IsSubtype(Py_TYPE(ob), &PyFrozenSet_Type)) +#define PySet_Check(ob) \ + (Py_TYPE(ob) == &PySet_Type || \ + PyType_IsSubtype(Py_TYPE(ob), &PySet_Type)) +#define PyFrozenSet_Check(ob) \ + (Py_TYPE(ob) == &PyFrozenSet_Type || \ + PyType_IsSubtype(Py_TYPE(ob), &PyFrozenSet_Type)) + +PyAPI_FUNC(PyObject *) PySet_New(PyObject *); +PyAPI_FUNC(PyObject *) PyFrozenSet_New(PyObject *); +PyAPI_FUNC(Py_ssize_t) PySet_Size(PyObject *anyset); +#define PySet_GET_SIZE(so) (((PySetObject *)(so))->used) +PyAPI_FUNC(int) PySet_Clear(PyObject *set); +PyAPI_FUNC(int) PySet_Contains(PyObject *anyset, PyObject *key); +PyAPI_FUNC(int) PySet_Discard(PyObject *set, PyObject *key); +PyAPI_FUNC(int) PySet_Add(PyObject *set, PyObject *key); +PyAPI_FUNC(int) _PySet_Next(PyObject *set, Py_ssize_t *pos, PyObject **key); +PyAPI_FUNC(int) _PySet_NextEntry(PyObject *set, Py_ssize_t *pos, PyObject **key, long *hash); +PyAPI_FUNC(PyObject *) PySet_Pop(PyObject *set); +PyAPI_FUNC(int) _PySet_Update(PyObject *set, PyObject *iterable); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_SETOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/sliceobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/sliceobject.h new file mode 100644 index 0000000000..469921a99a --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/sliceobject.h @@ -0,0 +1,44 @@ +#ifndef Py_SLICEOBJECT_H +#define Py_SLICEOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +/* The unique ellipsis object "..." */ + +PyAPI_DATA(PyObject) _Py_EllipsisObject; /* Don't use this directly */ + +#define Py_Ellipsis (&_Py_EllipsisObject) + +/* Slice object interface */ + +/* + +A slice object containing start, stop, and step data members (the +names are from range). After much talk with Guido, it was decided to +let these be any arbitrary python type. Py_None stands for omitted values. +*/ + +typedef struct { + PyObject_HEAD + PyObject *start, *stop, *step; /* not NULL */ +} PySliceObject; + +PyAPI_DATA(PyTypeObject) PySlice_Type; +PyAPI_DATA(PyTypeObject) PyEllipsis_Type; + +#define PySlice_Check(op) (Py_TYPE(op) == &PySlice_Type) + +PyAPI_FUNC(PyObject *) PySlice_New(PyObject* start, PyObject* stop, + PyObject* step); +PyAPI_FUNC(PyObject *) _PySlice_FromIndices(Py_ssize_t start, Py_ssize_t stop); +PyAPI_FUNC(int) PySlice_GetIndices(PySliceObject *r, Py_ssize_t length, + Py_ssize_t *start, Py_ssize_t *stop, Py_ssize_t *step); +PyAPI_FUNC(int) PySlice_GetIndicesEx(PySliceObject *r, Py_ssize_t length, + Py_ssize_t *start, Py_ssize_t *stop, + Py_ssize_t *step, Py_ssize_t *slicelength); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_SLICEOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/stringobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/stringobject.h new file mode 100644 index 0000000000..d20d98611d --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/stringobject.h @@ -0,0 +1,210 @@ + +/* String (str/bytes) object interface */ + +#ifndef Py_STRINGOBJECT_H +#define Py_STRINGOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +#include + +/* +Type PyStringObject represents a character string. An extra zero byte is +reserved at the end to ensure it is zero-terminated, but a size is +present so strings with null bytes in them can be represented. This +is an immutable object type. + +There are functions to create new string objects, to test +an object for string-ness, and to get the +string value. The latter function returns a null pointer +if the object is not of the proper type. +There is a variant that takes an explicit size as well as a +variant that assumes a zero-terminated string. Note that none of the +functions should be applied to nil objects. +*/ + +/* Caching the hash (ob_shash) saves recalculation of a string's hash value. + Interning strings (ob_sstate) tries to ensure that only one string + object with a given value exists, so equality tests can be one pointer + comparison. This is generally restricted to strings that "look like" + Python identifiers, although the intern() builtin can be used to force + interning of any string. + Together, these sped the interpreter by up to 20%. */ + +typedef struct { + PyObject_VAR_HEAD + long ob_shash; + int ob_sstate; + char ob_sval[1]; + + /* Invariants: + * ob_sval contains space for 'ob_size+1' elements. + * ob_sval[ob_size] == 0. + * ob_shash is the hash of the string or -1 if not computed yet. + * ob_sstate != 0 iff the string object is in stringobject.c's + * 'interned' dictionary; in this case the two references + * from 'interned' to this object are *not counted* in ob_refcnt. + */ +} PyStringObject; + +#define SSTATE_NOT_INTERNED 0 +#define SSTATE_INTERNED_MORTAL 1 +#define SSTATE_INTERNED_IMMORTAL 2 + +PyAPI_DATA(PyTypeObject) PyBaseString_Type; +PyAPI_DATA(PyTypeObject) PyString_Type; + +#define PyString_Check(op) \ + PyType_FastSubclass(Py_TYPE(op), Py_TPFLAGS_STRING_SUBCLASS) +#define PyString_CheckExact(op) (Py_TYPE(op) == &PyString_Type) + +PyAPI_FUNC(PyObject *) PyString_FromStringAndSize(const char *, Py_ssize_t); +PyAPI_FUNC(PyObject *) PyString_FromString(const char *); +PyAPI_FUNC(PyObject *) PyString_FromFormatV(const char*, va_list) + Py_GCC_ATTRIBUTE((format(printf, 1, 0))); +PyAPI_FUNC(PyObject *) PyString_FromFormat(const char*, ...) + Py_GCC_ATTRIBUTE((format(printf, 1, 2))); +PyAPI_FUNC(Py_ssize_t) PyString_Size(PyObject *); +PyAPI_FUNC(char *) PyString_AsString(PyObject *); +PyAPI_FUNC(PyObject *) PyString_Repr(PyObject *, int); +PyAPI_FUNC(void) PyString_Concat(PyObject **, PyObject *); +PyAPI_FUNC(void) PyString_ConcatAndDel(PyObject **, PyObject *); +PyAPI_FUNC(int) _PyString_Resize(PyObject **, Py_ssize_t); +PyAPI_FUNC(int) _PyString_Eq(PyObject *, PyObject*); +PyAPI_FUNC(PyObject *) PyString_Format(PyObject *, PyObject *); +PyAPI_FUNC(PyObject *) _PyString_FormatLong(PyObject*, int, int, + int, char**, int*); +PyAPI_FUNC(PyObject *) PyString_DecodeEscape(const char *, Py_ssize_t, + const char *, Py_ssize_t, + const char *); + +PyAPI_FUNC(void) PyString_InternInPlace(PyObject **); +PyAPI_FUNC(void) PyString_InternImmortal(PyObject **); +PyAPI_FUNC(PyObject *) PyString_InternFromString(const char *); +PyAPI_FUNC(void) _Py_ReleaseInternedStrings(void); + +/* Use only if you know it's a string */ +#define PyString_CHECK_INTERNED(op) (((PyStringObject *)(op))->ob_sstate) + +/* Macro, trading safety for speed */ +#define PyString_AS_STRING(op) (((PyStringObject *)(op))->ob_sval) +#define PyString_GET_SIZE(op) Py_SIZE(op) + +/* _PyString_Join(sep, x) is like sep.join(x). sep must be PyStringObject*, + x must be an iterable object. */ +PyAPI_FUNC(PyObject *) _PyString_Join(PyObject *sep, PyObject *x); + +/* --- Generic Codecs ----------------------------------------------------- */ + +/* Create an object by decoding the encoded string s of the + given size. */ + +PyAPI_FUNC(PyObject*) PyString_Decode( + const char *s, /* encoded string */ + Py_ssize_t size, /* size of buffer */ + const char *encoding, /* encoding */ + const char *errors /* error handling */ + ); + +/* Encodes a char buffer of the given size and returns a + Python object. */ + +PyAPI_FUNC(PyObject*) PyString_Encode( + const char *s, /* string char buffer */ + Py_ssize_t size, /* number of chars to encode */ + const char *encoding, /* encoding */ + const char *errors /* error handling */ + ); + +/* Encodes a string object and returns the result as Python + object. */ + +PyAPI_FUNC(PyObject*) PyString_AsEncodedObject( + PyObject *str, /* string object */ + const char *encoding, /* encoding */ + const char *errors /* error handling */ + ); + +/* Encodes a string object and returns the result as Python string + object. + + If the codec returns an Unicode object, the object is converted + back to a string using the default encoding. + + DEPRECATED - use PyString_AsEncodedObject() instead. */ + +PyAPI_FUNC(PyObject*) PyString_AsEncodedString( + PyObject *str, /* string object */ + const char *encoding, /* encoding */ + const char *errors /* error handling */ + ); + +/* Decodes a string object and returns the result as Python + object. */ + +PyAPI_FUNC(PyObject*) PyString_AsDecodedObject( + PyObject *str, /* string object */ + const char *encoding, /* encoding */ + const char *errors /* error handling */ + ); + +/* Decodes a string object and returns the result as Python string + object. + + If the codec returns an Unicode object, the object is converted + back to a string using the default encoding. + + DEPRECATED - use PyString_AsDecodedObject() instead. */ + +PyAPI_FUNC(PyObject*) PyString_AsDecodedString( + PyObject *str, /* string object */ + const char *encoding, /* encoding */ + const char *errors /* error handling */ + ); + +/* Provides access to the internal data buffer and size of a string + object or the default encoded version of an Unicode object. Passing + NULL as *len parameter will force the string buffer to be + 0-terminated (passing a string with embedded NULL characters will + cause an exception). */ + +PyAPI_FUNC(int) PyString_AsStringAndSize( + register PyObject *obj, /* string or Unicode object */ + register char **s, /* pointer to buffer variable */ + register Py_ssize_t *len /* pointer to length variable or NULL + (only possible for 0-terminated + strings) */ + ); + + +/* Using the current locale, insert the thousands grouping + into the string pointed to by buffer. For the argument descriptions, + see Objects/stringlib/localeutil.h */ +PyAPI_FUNC(Py_ssize_t) _PyString_InsertThousandsGroupingLocale(char *buffer, + Py_ssize_t n_buffer, + char *digits, + Py_ssize_t n_digits, + Py_ssize_t min_width); + +/* Using explicit passed-in values, insert the thousands grouping + into the string pointed to by buffer. For the argument descriptions, + see Objects/stringlib/localeutil.h */ +PyAPI_FUNC(Py_ssize_t) _PyString_InsertThousandsGrouping(char *buffer, + Py_ssize_t n_buffer, + char *digits, + Py_ssize_t n_digits, + Py_ssize_t min_width, + const char *grouping, + const char *thousands_sep); + +/* Format the object based on the format_spec, as defined in PEP 3101 + (Advanced String Formatting). */ +PyAPI_FUNC(PyObject *) _PyBytes_FormatAdvanced(PyObject *obj, + char *format_spec, + Py_ssize_t format_spec_len); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_STRINGOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/structmember.h b/AppPkg/Applications/Python/Python-2.7.10/Include/structmember.h new file mode 100644 index 0000000000..8e2425bc79 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/structmember.h @@ -0,0 +1,99 @@ +#ifndef Py_STRUCTMEMBER_H +#define Py_STRUCTMEMBER_H +#ifdef __cplusplus +extern "C" { +#endif + + +/* Interface to map C struct members to Python object attributes */ + +#include /* For offsetof */ + +/* The offsetof() macro calculates the offset of a structure member + in its structure. Unfortunately this cannot be written down + portably, hence it is provided by a Standard C header file. + For pre-Standard C compilers, here is a version that usually works + (but watch out!): */ + +#ifndef offsetof +#define offsetof(type, member) ( (int) & ((type*)0) -> member ) +#endif + +/* An array of memberlist structures defines the name, type and offset + of selected members of a C structure. These can be read by + PyMember_Get() and set by PyMember_Set() (except if their READONLY flag + is set). The array must be terminated with an entry whose name + pointer is NULL. */ + +struct memberlist { + /* Obsolete version, for binary backwards compatibility */ + char *name; + int type; + int offset; + int flags; +}; + +typedef struct PyMemberDef { + /* Current version, use this */ + char *name; + int type; + Py_ssize_t offset; + int flags; + char *doc; +} PyMemberDef; + +/* Types */ +#define T_SHORT 0 +#define T_INT 1 +#define T_LONG 2 +#define T_FLOAT 3 +#define T_DOUBLE 4 +#define T_STRING 5 +#define T_OBJECT 6 +/* XXX the ordering here is weird for binary compatibility */ +#define T_CHAR 7 /* 1-character string */ +#define T_BYTE 8 /* 8-bit signed int */ +/* unsigned variants: */ +#define T_UBYTE 9 +#define T_USHORT 10 +#define T_UINT 11 +#define T_ULONG 12 + +/* Added by Jack: strings contained in the structure */ +#define T_STRING_INPLACE 13 + +/* Added by Lillo: bools contained in the structure (assumed char) */ +#define T_BOOL 14 + +#define T_OBJECT_EX 16 /* Like T_OBJECT, but raises AttributeError + when the value is NULL, instead of + converting to None. */ +#ifdef HAVE_LONG_LONG +#define T_LONGLONG 17 +#define T_ULONGLONG 18 +#endif /* HAVE_LONG_LONG */ + +#define T_PYSSIZET 19 /* Py_ssize_t */ + + +/* Flags */ +#define READONLY 1 +#define RO READONLY /* Shorthand */ +#define READ_RESTRICTED 2 +#define PY_WRITE_RESTRICTED 4 +#define RESTRICTED (READ_RESTRICTED | PY_WRITE_RESTRICTED) + + +/* Obsolete API, for binary backwards compatibility */ +PyAPI_FUNC(PyObject *) PyMember_Get(const char *, struct memberlist *, const char *); +PyAPI_FUNC(int) PyMember_Set(char *, struct memberlist *, const char *, PyObject *); + +/* Current API, use this */ +PyAPI_FUNC(PyObject *) PyMember_GetOne(const char *, struct PyMemberDef *); +PyAPI_FUNC(int) PyMember_SetOne(char *, struct PyMemberDef *, PyObject *); + + +#ifdef __cplusplus +} +#endif +#endif /* !Py_STRUCTMEMBER_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/structseq.h b/AppPkg/Applications/Python/Python-2.7.10/Include/structseq.h new file mode 100644 index 0000000000..74b1a88120 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/structseq.h @@ -0,0 +1,41 @@ + +/* Tuple object interface */ + +#ifndef Py_STRUCTSEQ_H +#define Py_STRUCTSEQ_H +#ifdef __cplusplus +extern "C" { +#endif + +typedef struct PyStructSequence_Field { + char *name; + char *doc; +} PyStructSequence_Field; + +typedef struct PyStructSequence_Desc { + char *name; + char *doc; + struct PyStructSequence_Field *fields; + int n_in_sequence; +} PyStructSequence_Desc; + +extern char* PyStructSequence_UnnamedField; + +PyAPI_FUNC(void) PyStructSequence_InitType(PyTypeObject *type, + PyStructSequence_Desc *desc); + +PyAPI_FUNC(PyObject *) PyStructSequence_New(PyTypeObject* type); + +typedef struct { + PyObject_VAR_HEAD + PyObject *ob_item[1]; +} PyStructSequence; + +/* Macro, *only* to be used to fill in brand new objects */ +#define PyStructSequence_SET_ITEM(op, i, v) \ + (((PyStructSequence *)(op))->ob_item[i] = v) + +#ifdef __cplusplus +} +#endif +#endif /* !Py_STRUCTSEQ_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/symtable.h b/AppPkg/Applications/Python/Python-2.7.10/Include/symtable.h new file mode 100644 index 0000000000..dd3e360642 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/symtable.h @@ -0,0 +1,98 @@ +#ifndef Py_SYMTABLE_H +#define Py_SYMTABLE_H + +#ifdef __cplusplus +extern "C" { +#endif + +typedef enum _block_type { FunctionBlock, ClassBlock, ModuleBlock } + _Py_block_ty; + +struct _symtable_entry; + +struct symtable { + const char *st_filename; /* name of file being compiled */ + struct _symtable_entry *st_cur; /* current symbol table entry */ + struct _symtable_entry *st_top; /* module entry */ + PyObject *st_symbols; /* dictionary of symbol table entries */ + PyObject *st_stack; /* stack of namespace info */ + PyObject *st_global; /* borrowed ref to MODULE in st_symbols */ + int st_nblocks; /* number of blocks */ + PyObject *st_private; /* name of current class or NULL */ + PyFutureFeatures *st_future; /* module's future features */ +}; + +typedef struct _symtable_entry { + PyObject_HEAD + PyObject *ste_id; /* int: key in st_symbols */ + PyObject *ste_symbols; /* dict: name to flags */ + PyObject *ste_name; /* string: name of block */ + PyObject *ste_varnames; /* list of variable names */ + PyObject *ste_children; /* list of child ids */ + _Py_block_ty ste_type; /* module, class, or function */ + int ste_unoptimized; /* false if namespace is optimized */ + int ste_nested; /* true if block is nested */ + unsigned ste_free : 1; /* true if block has free variables */ + unsigned ste_child_free : 1; /* true if a child block has free vars, + including free refs to globals */ + unsigned ste_generator : 1; /* true if namespace is a generator */ + unsigned ste_varargs : 1; /* true if block has varargs */ + unsigned ste_varkeywords : 1; /* true if block has varkeywords */ + unsigned ste_returns_value : 1; /* true if namespace uses return with + an argument */ + int ste_lineno; /* first line of block */ + int ste_opt_lineno; /* lineno of last exec or import * */ + int ste_tmpname; /* counter for listcomp temp vars */ + struct symtable *ste_table; +} PySTEntryObject; + +PyAPI_DATA(PyTypeObject) PySTEntry_Type; + +#define PySTEntry_Check(op) (Py_TYPE(op) == &PySTEntry_Type) + +PyAPI_FUNC(int) PyST_GetScope(PySTEntryObject *, PyObject *); + +PyAPI_FUNC(struct symtable *) PySymtable_Build(mod_ty, const char *, + PyFutureFeatures *); +PyAPI_FUNC(PySTEntryObject *) PySymtable_Lookup(struct symtable *, void *); + +PyAPI_FUNC(void) PySymtable_Free(struct symtable *); + +/* Flags for def-use information */ + +#define DEF_GLOBAL 1 /* global stmt */ +#define DEF_LOCAL 2 /* assignment in code block */ +#define DEF_PARAM 2<<1 /* formal parameter */ +#define USE 2<<2 /* name is used */ +#define DEF_FREE 2<<3 /* name used but not defined in nested block */ +#define DEF_FREE_CLASS 2<<4 /* free variable from class's method */ +#define DEF_IMPORT 2<<5 /* assignment occurred via import */ + +#define DEF_BOUND (DEF_LOCAL | DEF_PARAM | DEF_IMPORT) + +/* GLOBAL_EXPLICIT and GLOBAL_IMPLICIT are used internally by the symbol + table. GLOBAL is returned from PyST_GetScope() for either of them. + It is stored in ste_symbols at bits 12-14. +*/ +#define SCOPE_OFF 11 +#define SCOPE_MASK 7 + +#define LOCAL 1 +#define GLOBAL_EXPLICIT 2 +#define GLOBAL_IMPLICIT 3 +#define FREE 4 +#define CELL 5 + +/* The following three names are used for the ste_unoptimized bit field */ +#define OPT_IMPORT_STAR 1 +#define OPT_EXEC 2 +#define OPT_BARE_EXEC 4 +#define OPT_TOPLEVEL 8 /* top-level names, including eval and exec */ + +#define GENERATOR 1 +#define GENERATOR_EXPRESSION 2 + +#ifdef __cplusplus +} +#endif +#endif /* !Py_SYMTABLE_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/sysmodule.h b/AppPkg/Applications/Python/Python-2.7.10/Include/sysmodule.h new file mode 100644 index 0000000000..5a8bee766b --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/sysmodule.h @@ -0,0 +1,31 @@ + +/* System module interface */ + +#ifndef Py_SYSMODULE_H +#define Py_SYSMODULE_H +#ifdef __cplusplus +extern "C" { +#endif + +PyAPI_FUNC(PyObject *) PySys_GetObject(char *); +PyAPI_FUNC(int) PySys_SetObject(char *, PyObject *); +PyAPI_FUNC(FILE *) PySys_GetFile(char *, FILE *); +PyAPI_FUNC(void) PySys_SetArgv(int, char **); +PyAPI_FUNC(void) PySys_SetArgvEx(int, char **, int); +PyAPI_FUNC(void) PySys_SetPath(char *); + +PyAPI_FUNC(void) PySys_WriteStdout(const char *format, ...) + Py_GCC_ATTRIBUTE((format(printf, 1, 2))); +PyAPI_FUNC(void) PySys_WriteStderr(const char *format, ...) + Py_GCC_ATTRIBUTE((format(printf, 1, 2))); + +PyAPI_FUNC(void) PySys_ResetWarnOptions(void); +PyAPI_FUNC(void) PySys_AddWarnOption(char *); +PyAPI_FUNC(int) PySys_HasWarnOptions(void); + +PyAPI_FUNC(size_t) _PySys_GetSizeOf(PyObject *); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_SYSMODULE_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/timefuncs.h b/AppPkg/Applications/Python/Python-2.7.10/Include/timefuncs.h new file mode 100644 index 0000000000..ae5acf7e8b --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/timefuncs.h @@ -0,0 +1,26 @@ +/* timefuncs.h + */ + +/* Utility function related to timemodule.c. */ + +#ifndef TIMEFUNCS_H +#define TIMEFUNCS_H +#ifdef __cplusplus +extern "C" { +#endif + + +/* Cast double x to time_t, but raise ValueError if x is too large + * to fit in a time_t. ValueError is set on return iff the return + * value is (time_t)-1 and PyErr_Occurred(). + */ +PyAPI_FUNC(time_t) _PyTime_DoubleToTimet(double x); + +/* Get the current time since the epoch in seconds */ +PyAPI_FUNC(double) _PyTime_FloatTime(void); + + +#ifdef __cplusplus +} +#endif +#endif /* TIMEFUNCS_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/token.h b/AppPkg/Applications/Python/Python-2.7.10/Include/token.h new file mode 100644 index 0000000000..438f04ba87 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/token.h @@ -0,0 +1,85 @@ + +/* Token types */ + +#ifndef Py_TOKEN_H +#define Py_TOKEN_H +#ifdef __cplusplus +extern "C" { +#endif + +#undef TILDE /* Prevent clash of our definition with system macro. Ex AIX, ioctl.h */ + +#define ENDMARKER 0 +#define NAME 1 +#define NUMBER 2 +#define STRING 3 +#define NEWLINE 4 +#define INDENT 5 +#define DEDENT 6 +#define LPAR 7 +#define RPAR 8 +#define LSQB 9 +#define RSQB 10 +#define COLON 11 +#define COMMA 12 +#define SEMI 13 +#define PLUS 14 +#define MINUS 15 +#define STAR 16 +#define SLASH 17 +#define VBAR 18 +#define AMPER 19 +#define LESS 20 +#define GREATER 21 +#define EQUAL 22 +#define DOT 23 +#define PERCENT 24 +#define BACKQUOTE 25 +#define LBRACE 26 +#define RBRACE 27 +#define EQEQUAL 28 +#define NOTEQUAL 29 +#define LESSEQUAL 30 +#define GREATEREQUAL 31 +#define TILDE 32 +#define CIRCUMFLEX 33 +#define LEFTSHIFT 34 +#define RIGHTSHIFT 35 +#define DOUBLESTAR 36 +#define PLUSEQUAL 37 +#define MINEQUAL 38 +#define STAREQUAL 39 +#define SLASHEQUAL 40 +#define PERCENTEQUAL 41 +#define AMPEREQUAL 42 +#define VBAREQUAL 43 +#define CIRCUMFLEXEQUAL 44 +#define LEFTSHIFTEQUAL 45 +#define RIGHTSHIFTEQUAL 46 +#define DOUBLESTAREQUAL 47 +#define DOUBLESLASH 48 +#define DOUBLESLASHEQUAL 49 +#define AT 50 +/* Don't forget to update the table _PyParser_TokenNames in tokenizer.c! */ +#define OP 51 +#define ERRORTOKEN 52 +#define N_TOKENS 53 + +/* Special definitions for cooperation with parser */ + +#define NT_OFFSET 256 + +#define ISTERMINAL(x) ((x) < NT_OFFSET) +#define ISNONTERMINAL(x) ((x) >= NT_OFFSET) +#define ISEOF(x) ((x) == ENDMARKER) + + +PyAPI_DATA(char *) _PyParser_TokenNames[]; /* Token names */ +PyAPI_FUNC(int) PyToken_OneChar(int); +PyAPI_FUNC(int) PyToken_TwoChars(int, int); +PyAPI_FUNC(int) PyToken_ThreeChars(int, int, int); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_TOKEN_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/traceback.h b/AppPkg/Applications/Python/Python-2.7.10/Include/traceback.h new file mode 100644 index 0000000000..fce0607e3f --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/traceback.h @@ -0,0 +1,31 @@ + +#ifndef Py_TRACEBACK_H +#define Py_TRACEBACK_H +#ifdef __cplusplus +extern "C" { +#endif + +struct _frame; + +/* Traceback interface */ + +typedef struct _traceback { + PyObject_HEAD + struct _traceback *tb_next; + struct _frame *tb_frame; + int tb_lasti; + int tb_lineno; +} PyTracebackObject; + +PyAPI_FUNC(int) PyTraceBack_Here(struct _frame *); +PyAPI_FUNC(int) PyTraceBack_Print(PyObject *, PyObject *); +PyAPI_FUNC(int) _Py_DisplaySourceLine(PyObject *, const char *, int, int); + +/* Reveal traceback type so we can typecheck traceback objects */ +PyAPI_DATA(PyTypeObject) PyTraceBack_Type; +#define PyTraceBack_Check(v) (Py_TYPE(v) == &PyTraceBack_Type) + +#ifdef __cplusplus +} +#endif +#endif /* !Py_TRACEBACK_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/tupleobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/tupleobject.h new file mode 100644 index 0000000000..8fdfd596cf --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/tupleobject.h @@ -0,0 +1,61 @@ + +/* Tuple object interface */ + +#ifndef Py_TUPLEOBJECT_H +#define Py_TUPLEOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + +/* +Another generally useful object type is a tuple of object pointers. +For Python, this is an immutable type. C code can change the tuple items +(but not their number), and even use tuples are general-purpose arrays of +object references, but in general only brand new tuples should be mutated, +not ones that might already have been exposed to Python code. + +*** WARNING *** PyTuple_SetItem does not increment the new item's reference +count, but does decrement the reference count of the item it replaces, +if not nil. It does *decrement* the reference count if it is *not* +inserted in the tuple. Similarly, PyTuple_GetItem does not increment the +returned item's reference count. +*/ + +typedef struct { + PyObject_VAR_HEAD + PyObject *ob_item[1]; + + /* ob_item contains space for 'ob_size' elements. + * Items must normally not be NULL, except during construction when + * the tuple is not yet visible outside the function that builds it. + */ +} PyTupleObject; + +PyAPI_DATA(PyTypeObject) PyTuple_Type; + +#define PyTuple_Check(op) \ + PyType_FastSubclass(Py_TYPE(op), Py_TPFLAGS_TUPLE_SUBCLASS) +#define PyTuple_CheckExact(op) (Py_TYPE(op) == &PyTuple_Type) + +PyAPI_FUNC(PyObject *) PyTuple_New(Py_ssize_t size); +PyAPI_FUNC(Py_ssize_t) PyTuple_Size(PyObject *); +PyAPI_FUNC(PyObject *) PyTuple_GetItem(PyObject *, Py_ssize_t); +PyAPI_FUNC(int) PyTuple_SetItem(PyObject *, Py_ssize_t, PyObject *); +PyAPI_FUNC(PyObject *) PyTuple_GetSlice(PyObject *, Py_ssize_t, Py_ssize_t); +PyAPI_FUNC(int) _PyTuple_Resize(PyObject **, Py_ssize_t); +PyAPI_FUNC(PyObject *) PyTuple_Pack(Py_ssize_t, ...); +PyAPI_FUNC(void) _PyTuple_MaybeUntrack(PyObject *); + +/* Macro, trading safety for speed */ +#define PyTuple_GET_ITEM(op, i) (((PyTupleObject *)(op))->ob_item[i]) +#define PyTuple_GET_SIZE(op) Py_SIZE(op) + +/* Macro, *only* to be used to fill in brand new tuples */ +#define PyTuple_SET_ITEM(op, i, v) (((PyTupleObject *)(op))->ob_item[i] = v) + +PyAPI_FUNC(int) PyTuple_ClearFreeList(void); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_TUPLEOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/ucnhash.h b/AppPkg/Applications/Python/Python-2.7.10/Include/ucnhash.h new file mode 100644 index 0000000000..8158730bc0 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/ucnhash.h @@ -0,0 +1,33 @@ +/* Unicode name database interface */ + +#ifndef Py_UCNHASH_H +#define Py_UCNHASH_H +#ifdef __cplusplus +extern "C" { +#endif + +/* revised ucnhash CAPI interface (exported through a "wrapper") */ + +#define PyUnicodeData_CAPSULE_NAME "unicodedata.ucnhash_CAPI" + +typedef struct { + + /* Size of this struct */ + int size; + + /* Get name for a given character code. Returns non-zero if + success, zero if not. Does not set Python exceptions. + If self is NULL, data come from the default version of the database. + If it is not NULL, it should be a unicodedata.ucd_X_Y_Z object */ + int (*getname)(PyObject *self, Py_UCS4 code, char* buffer, int buflen); + + /* Get character code for a given name. Same error handling + as for getname. */ + int (*getcode)(PyObject *self, const char* name, int namelen, Py_UCS4* code); + +} _PyUnicode_Name_CAPI; + +#ifdef __cplusplus +} +#endif +#endif /* !Py_UCNHASH_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/unicodeobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/unicodeobject.h new file mode 100644 index 0000000000..de52416513 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/unicodeobject.h @@ -0,0 +1,1413 @@ +#ifndef Py_UNICODEOBJECT_H +#define Py_UNICODEOBJECT_H + +#include + +/* + +Unicode implementation based on original code by Fredrik Lundh, +modified by Marc-Andre Lemburg (mal@lemburg.com) according to the +Unicode Integration Proposal (see file Misc/unicode.txt). + +Copyright (c) Corporation for National Research Initiatives. + + + Original header: + -------------------------------------------------------------------- + + * Yet another Unicode string type for Python. This type supports the + * 16-bit Basic Multilingual Plane (BMP) only. + * + * Written by Fredrik Lundh, January 1999. + * + * Copyright (c) 1999 by Secret Labs AB. + * Copyright (c) 1999 by Fredrik Lundh. + * + * fredrik@pythonware.com + * http://www.pythonware.com + * + * -------------------------------------------------------------------- + * This Unicode String Type is + * + * Copyright (c) 1999 by Secret Labs AB + * Copyright (c) 1999 by Fredrik Lundh + * + * By obtaining, using, and/or copying this software and/or its + * associated documentation, you agree that you have read, understood, + * and will comply with the following terms and conditions: + * + * Permission to use, copy, modify, and distribute this software and its + * associated documentation for any purpose and without fee is hereby + * granted, provided that the above copyright notice appears in all + * copies, and that both that copyright notice and this permission notice + * appear in supporting documentation, and that the name of Secret Labs + * AB or the author not be used in advertising or publicity pertaining to + * distribution of the software without specific, written prior + * permission. + * + * SECRET LABS AB AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH REGARD TO + * THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND + * FITNESS. IN NO EVENT SHALL SECRET LABS AB OR THE AUTHOR BE LIABLE FOR + * ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES + * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN + * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT + * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * -------------------------------------------------------------------- */ + +#include + +/* === Internal API ======================================================= */ + +/* --- Internal Unicode Format -------------------------------------------- */ + +#ifndef Py_USING_UNICODE + +#define PyUnicode_Check(op) 0 +#define PyUnicode_CheckExact(op) 0 + +#else + +/* FIXME: MvL's new implementation assumes that Py_UNICODE_SIZE is + properly set, but the default rules below doesn't set it. I'll + sort this out some other day -- fredrik@pythonware.com */ + +#ifndef Py_UNICODE_SIZE +#error Must define Py_UNICODE_SIZE +#endif + +/* Setting Py_UNICODE_WIDE enables UCS-4 storage. Otherwise, Unicode + strings are stored as UCS-2 (with limited support for UTF-16) */ + +#if Py_UNICODE_SIZE >= 4 +#define Py_UNICODE_WIDE +#endif + +/* Set these flags if the platform has "wchar.h", "wctype.h" and the + wchar_t type is a 16-bit unsigned type */ +/* #define HAVE_WCHAR_H */ +/* #define HAVE_USABLE_WCHAR_T */ + +/* Defaults for various platforms */ +#ifndef PY_UNICODE_TYPE + +/* Windows has a usable wchar_t type (unless we're using UCS-4) */ +# if defined(MS_WIN32) && Py_UNICODE_SIZE == 2 +# define HAVE_USABLE_WCHAR_T +# define PY_UNICODE_TYPE wchar_t +# endif + +# if defined(Py_UNICODE_WIDE) +# define PY_UNICODE_TYPE Py_UCS4 +# endif + +#endif + +/* If the compiler provides a wchar_t type we try to support it + through the interface functions PyUnicode_FromWideChar() and + PyUnicode_AsWideChar(). */ + +#ifdef HAVE_USABLE_WCHAR_T +# ifndef HAVE_WCHAR_H +# define HAVE_WCHAR_H +# endif +#endif + +#ifdef HAVE_WCHAR_H +/* Work around a cosmetic bug in BSDI 4.x wchar.h; thanks to Thomas Wouters */ +# ifdef _HAVE_BSDI +# include +# endif +# include +#endif + +/* + * Use this typedef when you need to represent a UTF-16 surrogate pair + * as single unsigned integer. + */ +#if SIZEOF_INT >= 4 +typedef unsigned int Py_UCS4; +#elif SIZEOF_LONG >= 4 +typedef unsigned long Py_UCS4; +#endif + +/* Py_UNICODE is the native Unicode storage format (code unit) used by + Python and represents a single Unicode element in the Unicode + type. */ + +typedef PY_UNICODE_TYPE Py_UNICODE; + +/* --- UCS-2/UCS-4 Name Mangling ------------------------------------------ */ + +/* Unicode API names are mangled to assure that UCS-2 and UCS-4 builds + produce different external names and thus cause import errors in + case Python interpreters and extensions with mixed compiled in + Unicode width assumptions are combined. */ + +#ifndef Py_UNICODE_WIDE + +# define PyUnicode_AsASCIIString PyUnicodeUCS2_AsASCIIString +# define PyUnicode_AsCharmapString PyUnicodeUCS2_AsCharmapString +# define PyUnicode_AsEncodedObject PyUnicodeUCS2_AsEncodedObject +# define PyUnicode_AsEncodedString PyUnicodeUCS2_AsEncodedString +# define PyUnicode_AsLatin1String PyUnicodeUCS2_AsLatin1String +# define PyUnicode_AsRawUnicodeEscapeString PyUnicodeUCS2_AsRawUnicodeEscapeString +# define PyUnicode_AsUTF32String PyUnicodeUCS2_AsUTF32String +# define PyUnicode_AsUTF16String PyUnicodeUCS2_AsUTF16String +# define PyUnicode_AsUTF8String PyUnicodeUCS2_AsUTF8String +# define PyUnicode_AsUnicode PyUnicodeUCS2_AsUnicode +# define PyUnicode_AsUnicodeEscapeString PyUnicodeUCS2_AsUnicodeEscapeString +# define PyUnicode_AsWideChar PyUnicodeUCS2_AsWideChar +# define PyUnicode_ClearFreeList PyUnicodeUCS2_ClearFreelist +# define PyUnicode_Compare PyUnicodeUCS2_Compare +# define PyUnicode_Concat PyUnicodeUCS2_Concat +# define PyUnicode_Contains PyUnicodeUCS2_Contains +# define PyUnicode_Count PyUnicodeUCS2_Count +# define PyUnicode_Decode PyUnicodeUCS2_Decode +# define PyUnicode_DecodeASCII PyUnicodeUCS2_DecodeASCII +# define PyUnicode_DecodeCharmap PyUnicodeUCS2_DecodeCharmap +# define PyUnicode_DecodeLatin1 PyUnicodeUCS2_DecodeLatin1 +# define PyUnicode_DecodeRawUnicodeEscape PyUnicodeUCS2_DecodeRawUnicodeEscape +# define PyUnicode_DecodeUTF32 PyUnicodeUCS2_DecodeUTF32 +# define PyUnicode_DecodeUTF32Stateful PyUnicodeUCS2_DecodeUTF32Stateful +# define PyUnicode_DecodeUTF16 PyUnicodeUCS2_DecodeUTF16 +# define PyUnicode_DecodeUTF16Stateful PyUnicodeUCS2_DecodeUTF16Stateful +# define PyUnicode_DecodeUTF8 PyUnicodeUCS2_DecodeUTF8 +# define PyUnicode_DecodeUTF8Stateful PyUnicodeUCS2_DecodeUTF8Stateful +# define PyUnicode_DecodeUnicodeEscape PyUnicodeUCS2_DecodeUnicodeEscape +# define PyUnicode_Encode PyUnicodeUCS2_Encode +# define PyUnicode_EncodeASCII PyUnicodeUCS2_EncodeASCII +# define PyUnicode_EncodeCharmap PyUnicodeUCS2_EncodeCharmap +# define PyUnicode_EncodeDecimal PyUnicodeUCS2_EncodeDecimal +# define PyUnicode_EncodeLatin1 PyUnicodeUCS2_EncodeLatin1 +# define PyUnicode_EncodeRawUnicodeEscape PyUnicodeUCS2_EncodeRawUnicodeEscape +# define PyUnicode_EncodeUTF32 PyUnicodeUCS2_EncodeUTF32 +# define PyUnicode_EncodeUTF16 PyUnicodeUCS2_EncodeUTF16 +# define PyUnicode_EncodeUTF8 PyUnicodeUCS2_EncodeUTF8 +# define PyUnicode_EncodeUnicodeEscape PyUnicodeUCS2_EncodeUnicodeEscape +# define PyUnicode_Find PyUnicodeUCS2_Find +# define PyUnicode_Format PyUnicodeUCS2_Format +# define PyUnicode_FromEncodedObject PyUnicodeUCS2_FromEncodedObject +# define PyUnicode_FromFormat PyUnicodeUCS2_FromFormat +# define PyUnicode_FromFormatV PyUnicodeUCS2_FromFormatV +# define PyUnicode_FromObject PyUnicodeUCS2_FromObject +# define PyUnicode_FromOrdinal PyUnicodeUCS2_FromOrdinal +# define PyUnicode_FromString PyUnicodeUCS2_FromString +# define PyUnicode_FromStringAndSize PyUnicodeUCS2_FromStringAndSize +# define PyUnicode_FromUnicode PyUnicodeUCS2_FromUnicode +# define PyUnicode_FromWideChar PyUnicodeUCS2_FromWideChar +# define PyUnicode_GetDefaultEncoding PyUnicodeUCS2_GetDefaultEncoding +# define PyUnicode_GetMax PyUnicodeUCS2_GetMax +# define PyUnicode_GetSize PyUnicodeUCS2_GetSize +# define PyUnicode_Join PyUnicodeUCS2_Join +# define PyUnicode_Partition PyUnicodeUCS2_Partition +# define PyUnicode_RPartition PyUnicodeUCS2_RPartition +# define PyUnicode_RSplit PyUnicodeUCS2_RSplit +# define PyUnicode_Replace PyUnicodeUCS2_Replace +# define PyUnicode_Resize PyUnicodeUCS2_Resize +# define PyUnicode_RichCompare PyUnicodeUCS2_RichCompare +# define PyUnicode_SetDefaultEncoding PyUnicodeUCS2_SetDefaultEncoding +# define PyUnicode_Split PyUnicodeUCS2_Split +# define PyUnicode_Splitlines PyUnicodeUCS2_Splitlines +# define PyUnicode_Tailmatch PyUnicodeUCS2_Tailmatch +# define PyUnicode_Translate PyUnicodeUCS2_Translate +# define PyUnicode_TranslateCharmap PyUnicodeUCS2_TranslateCharmap +# define _PyUnicode_AsDefaultEncodedString _PyUnicodeUCS2_AsDefaultEncodedString +# define _PyUnicode_Fini _PyUnicodeUCS2_Fini +# define _PyUnicode_Init _PyUnicodeUCS2_Init +# define _PyUnicode_IsAlpha _PyUnicodeUCS2_IsAlpha +# define _PyUnicode_IsDecimalDigit _PyUnicodeUCS2_IsDecimalDigit +# define _PyUnicode_IsDigit _PyUnicodeUCS2_IsDigit +# define _PyUnicode_IsLinebreak _PyUnicodeUCS2_IsLinebreak +# define _PyUnicode_IsLowercase _PyUnicodeUCS2_IsLowercase +# define _PyUnicode_IsNumeric _PyUnicodeUCS2_IsNumeric +# define _PyUnicode_IsTitlecase _PyUnicodeUCS2_IsTitlecase +# define _PyUnicode_IsUppercase _PyUnicodeUCS2_IsUppercase +# define _PyUnicode_IsWhitespace _PyUnicodeUCS2_IsWhitespace +# define _PyUnicode_ToDecimalDigit _PyUnicodeUCS2_ToDecimalDigit +# define _PyUnicode_ToDigit _PyUnicodeUCS2_ToDigit +# define _PyUnicode_ToLowercase _PyUnicodeUCS2_ToLowercase +# define _PyUnicode_ToNumeric _PyUnicodeUCS2_ToNumeric +# define _PyUnicode_ToTitlecase _PyUnicodeUCS2_ToTitlecase +# define _PyUnicode_ToUppercase _PyUnicodeUCS2_ToUppercase + +#else + +# define PyUnicode_AsASCIIString PyUnicodeUCS4_AsASCIIString +# define PyUnicode_AsCharmapString PyUnicodeUCS4_AsCharmapString +# define PyUnicode_AsEncodedObject PyUnicodeUCS4_AsEncodedObject +# define PyUnicode_AsEncodedString PyUnicodeUCS4_AsEncodedString +# define PyUnicode_AsLatin1String PyUnicodeUCS4_AsLatin1String +# define PyUnicode_AsRawUnicodeEscapeString PyUnicodeUCS4_AsRawUnicodeEscapeString +# define PyUnicode_AsUTF32String PyUnicodeUCS4_AsUTF32String +# define PyUnicode_AsUTF16String PyUnicodeUCS4_AsUTF16String +# define PyUnicode_AsUTF8String PyUnicodeUCS4_AsUTF8String +# define PyUnicode_AsUnicode PyUnicodeUCS4_AsUnicode +# define PyUnicode_AsUnicodeEscapeString PyUnicodeUCS4_AsUnicodeEscapeString +# define PyUnicode_AsWideChar PyUnicodeUCS4_AsWideChar +# define PyUnicode_ClearFreeList PyUnicodeUCS4_ClearFreelist +# define PyUnicode_Compare PyUnicodeUCS4_Compare +# define PyUnicode_Concat PyUnicodeUCS4_Concat +# define PyUnicode_Contains PyUnicodeUCS4_Contains +# define PyUnicode_Count PyUnicodeUCS4_Count +# define PyUnicode_Decode PyUnicodeUCS4_Decode +# define PyUnicode_DecodeASCII PyUnicodeUCS4_DecodeASCII +# define PyUnicode_DecodeCharmap PyUnicodeUCS4_DecodeCharmap +# define PyUnicode_DecodeLatin1 PyUnicodeUCS4_DecodeLatin1 +# define PyUnicode_DecodeRawUnicodeEscape PyUnicodeUCS4_DecodeRawUnicodeEscape +# define PyUnicode_DecodeUTF32 PyUnicodeUCS4_DecodeUTF32 +# define PyUnicode_DecodeUTF32Stateful PyUnicodeUCS4_DecodeUTF32Stateful +# define PyUnicode_DecodeUTF16 PyUnicodeUCS4_DecodeUTF16 +# define PyUnicode_DecodeUTF16Stateful PyUnicodeUCS4_DecodeUTF16Stateful +# define PyUnicode_DecodeUTF8 PyUnicodeUCS4_DecodeUTF8 +# define PyUnicode_DecodeUTF8Stateful PyUnicodeUCS4_DecodeUTF8Stateful +# define PyUnicode_DecodeUnicodeEscape PyUnicodeUCS4_DecodeUnicodeEscape +# define PyUnicode_Encode PyUnicodeUCS4_Encode +# define PyUnicode_EncodeASCII PyUnicodeUCS4_EncodeASCII +# define PyUnicode_EncodeCharmap PyUnicodeUCS4_EncodeCharmap +# define PyUnicode_EncodeDecimal PyUnicodeUCS4_EncodeDecimal +# define PyUnicode_EncodeLatin1 PyUnicodeUCS4_EncodeLatin1 +# define PyUnicode_EncodeRawUnicodeEscape PyUnicodeUCS4_EncodeRawUnicodeEscape +# define PyUnicode_EncodeUTF32 PyUnicodeUCS4_EncodeUTF32 +# define PyUnicode_EncodeUTF16 PyUnicodeUCS4_EncodeUTF16 +# define PyUnicode_EncodeUTF8 PyUnicodeUCS4_EncodeUTF8 +# define PyUnicode_EncodeUnicodeEscape PyUnicodeUCS4_EncodeUnicodeEscape +# define PyUnicode_Find PyUnicodeUCS4_Find +# define PyUnicode_Format PyUnicodeUCS4_Format +# define PyUnicode_FromEncodedObject PyUnicodeUCS4_FromEncodedObject +# define PyUnicode_FromFormat PyUnicodeUCS4_FromFormat +# define PyUnicode_FromFormatV PyUnicodeUCS4_FromFormatV +# define PyUnicode_FromObject PyUnicodeUCS4_FromObject +# define PyUnicode_FromOrdinal PyUnicodeUCS4_FromOrdinal +# define PyUnicode_FromString PyUnicodeUCS4_FromString +# define PyUnicode_FromStringAndSize PyUnicodeUCS4_FromStringAndSize +# define PyUnicode_FromUnicode PyUnicodeUCS4_FromUnicode +# define PyUnicode_FromWideChar PyUnicodeUCS4_FromWideChar +# define PyUnicode_GetDefaultEncoding PyUnicodeUCS4_GetDefaultEncoding +# define PyUnicode_GetMax PyUnicodeUCS4_GetMax +# define PyUnicode_GetSize PyUnicodeUCS4_GetSize +# define PyUnicode_Join PyUnicodeUCS4_Join +# define PyUnicode_Partition PyUnicodeUCS4_Partition +# define PyUnicode_RPartition PyUnicodeUCS4_RPartition +# define PyUnicode_RSplit PyUnicodeUCS4_RSplit +# define PyUnicode_Replace PyUnicodeUCS4_Replace +# define PyUnicode_Resize PyUnicodeUCS4_Resize +# define PyUnicode_RichCompare PyUnicodeUCS4_RichCompare +# define PyUnicode_SetDefaultEncoding PyUnicodeUCS4_SetDefaultEncoding +# define PyUnicode_Split PyUnicodeUCS4_Split +# define PyUnicode_Splitlines PyUnicodeUCS4_Splitlines +# define PyUnicode_Tailmatch PyUnicodeUCS4_Tailmatch +# define PyUnicode_Translate PyUnicodeUCS4_Translate +# define PyUnicode_TranslateCharmap PyUnicodeUCS4_TranslateCharmap +# define _PyUnicode_AsDefaultEncodedString _PyUnicodeUCS4_AsDefaultEncodedString +# define _PyUnicode_Fini _PyUnicodeUCS4_Fini +# define _PyUnicode_Init _PyUnicodeUCS4_Init +# define _PyUnicode_IsAlpha _PyUnicodeUCS4_IsAlpha +# define _PyUnicode_IsDecimalDigit _PyUnicodeUCS4_IsDecimalDigit +# define _PyUnicode_IsDigit _PyUnicodeUCS4_IsDigit +# define _PyUnicode_IsLinebreak _PyUnicodeUCS4_IsLinebreak +# define _PyUnicode_IsLowercase _PyUnicodeUCS4_IsLowercase +# define _PyUnicode_IsNumeric _PyUnicodeUCS4_IsNumeric +# define _PyUnicode_IsTitlecase _PyUnicodeUCS4_IsTitlecase +# define _PyUnicode_IsUppercase _PyUnicodeUCS4_IsUppercase +# define _PyUnicode_IsWhitespace _PyUnicodeUCS4_IsWhitespace +# define _PyUnicode_ToDecimalDigit _PyUnicodeUCS4_ToDecimalDigit +# define _PyUnicode_ToDigit _PyUnicodeUCS4_ToDigit +# define _PyUnicode_ToLowercase _PyUnicodeUCS4_ToLowercase +# define _PyUnicode_ToNumeric _PyUnicodeUCS4_ToNumeric +# define _PyUnicode_ToTitlecase _PyUnicodeUCS4_ToTitlecase +# define _PyUnicode_ToUppercase _PyUnicodeUCS4_ToUppercase + + +#endif + +/* --- Internal Unicode Operations ---------------------------------------- */ + +/* If you want Python to use the compiler's wctype.h functions instead + of the ones supplied with Python, define WANT_WCTYPE_FUNCTIONS or + configure Python using --with-wctype-functions. This reduces the + interpreter's code size. */ + +#if defined(HAVE_USABLE_WCHAR_T) && defined(WANT_WCTYPE_FUNCTIONS) + +#include + +#define Py_UNICODE_ISSPACE(ch) iswspace(ch) + +#define Py_UNICODE_ISLOWER(ch) iswlower(ch) +#define Py_UNICODE_ISUPPER(ch) iswupper(ch) +#define Py_UNICODE_ISTITLE(ch) _PyUnicode_IsTitlecase(ch) +#define Py_UNICODE_ISLINEBREAK(ch) _PyUnicode_IsLinebreak(ch) + +#define Py_UNICODE_TOLOWER(ch) towlower(ch) +#define Py_UNICODE_TOUPPER(ch) towupper(ch) +#define Py_UNICODE_TOTITLE(ch) _PyUnicode_ToTitlecase(ch) + +#define Py_UNICODE_ISDECIMAL(ch) _PyUnicode_IsDecimalDigit(ch) +#define Py_UNICODE_ISDIGIT(ch) _PyUnicode_IsDigit(ch) +#define Py_UNICODE_ISNUMERIC(ch) _PyUnicode_IsNumeric(ch) + +#define Py_UNICODE_TODECIMAL(ch) _PyUnicode_ToDecimalDigit(ch) +#define Py_UNICODE_TODIGIT(ch) _PyUnicode_ToDigit(ch) +#define Py_UNICODE_TONUMERIC(ch) _PyUnicode_ToNumeric(ch) + +#define Py_UNICODE_ISALPHA(ch) iswalpha(ch) + +#else + +/* Since splitting on whitespace is an important use case, and + whitespace in most situations is solely ASCII whitespace, we + optimize for the common case by using a quick look-up table + _Py_ascii_whitespace (see below) with an inlined check. + + */ +#define Py_UNICODE_ISSPACE(ch) \ + ((ch) < 128U ? _Py_ascii_whitespace[(ch)] : _PyUnicode_IsWhitespace(ch)) + +#define Py_UNICODE_ISLOWER(ch) _PyUnicode_IsLowercase(ch) +#define Py_UNICODE_ISUPPER(ch) _PyUnicode_IsUppercase(ch) +#define Py_UNICODE_ISTITLE(ch) _PyUnicode_IsTitlecase(ch) +#define Py_UNICODE_ISLINEBREAK(ch) _PyUnicode_IsLinebreak(ch) + +#define Py_UNICODE_TOLOWER(ch) _PyUnicode_ToLowercase(ch) +#define Py_UNICODE_TOUPPER(ch) _PyUnicode_ToUppercase(ch) +#define Py_UNICODE_TOTITLE(ch) _PyUnicode_ToTitlecase(ch) + +#define Py_UNICODE_ISDECIMAL(ch) _PyUnicode_IsDecimalDigit(ch) +#define Py_UNICODE_ISDIGIT(ch) _PyUnicode_IsDigit(ch) +#define Py_UNICODE_ISNUMERIC(ch) _PyUnicode_IsNumeric(ch) + +#define Py_UNICODE_TODECIMAL(ch) _PyUnicode_ToDecimalDigit(ch) +#define Py_UNICODE_TODIGIT(ch) _PyUnicode_ToDigit(ch) +#define Py_UNICODE_TONUMERIC(ch) _PyUnicode_ToNumeric(ch) + +#define Py_UNICODE_ISALPHA(ch) _PyUnicode_IsAlpha(ch) + +#endif + +#define Py_UNICODE_ISALNUM(ch) \ + (Py_UNICODE_ISALPHA(ch) || \ + Py_UNICODE_ISDECIMAL(ch) || \ + Py_UNICODE_ISDIGIT(ch) || \ + Py_UNICODE_ISNUMERIC(ch)) + +#define Py_UNICODE_COPY(target, source, length) \ + Py_MEMCPY((target), (source), (length)*sizeof(Py_UNICODE)) + +#define Py_UNICODE_FILL(target, value, length) \ + do {Py_ssize_t i_; Py_UNICODE *t_ = (target); Py_UNICODE v_ = (value);\ + for (i_ = 0; i_ < (length); i_++) t_[i_] = v_;\ + } while (0) + +/* Check if substring matches at given offset. the offset must be + valid, and the substring must not be empty */ + +#define Py_UNICODE_MATCH(string, offset, substring) \ + ((*((string)->str + (offset)) == *((substring)->str)) && \ + ((*((string)->str + (offset) + (substring)->length-1) == *((substring)->str + (substring)->length-1))) && \ + !memcmp((string)->str + (offset), (substring)->str, (substring)->length*sizeof(Py_UNICODE))) + +#ifdef __cplusplus +extern "C" { +#endif + +/* --- Unicode Type ------------------------------------------------------- */ + +typedef struct { + PyObject_HEAD + Py_ssize_t length; /* Length of raw Unicode data in buffer */ + Py_UNICODE *str; /* Raw Unicode buffer */ + long hash; /* Hash value; -1 if not set */ + PyObject *defenc; /* (Default) Encoded version as Python + string, or NULL; this is used for + implementing the buffer protocol */ +} PyUnicodeObject; + +PyAPI_DATA(PyTypeObject) PyUnicode_Type; + +#define PyUnicode_Check(op) \ + PyType_FastSubclass(Py_TYPE(op), Py_TPFLAGS_UNICODE_SUBCLASS) +#define PyUnicode_CheckExact(op) (Py_TYPE(op) == &PyUnicode_Type) + +/* Fast access macros */ +#define PyUnicode_GET_SIZE(op) \ + (((PyUnicodeObject *)(op))->length) +#define PyUnicode_GET_DATA_SIZE(op) \ + (((PyUnicodeObject *)(op))->length * sizeof(Py_UNICODE)) +#define PyUnicode_AS_UNICODE(op) \ + (((PyUnicodeObject *)(op))->str) +#define PyUnicode_AS_DATA(op) \ + ((const char *)((PyUnicodeObject *)(op))->str) + +/* --- Constants ---------------------------------------------------------- */ + +/* This Unicode character will be used as replacement character during + decoding if the errors argument is set to "replace". Note: the + Unicode character U+FFFD is the official REPLACEMENT CHARACTER in + Unicode 3.0. */ + +#define Py_UNICODE_REPLACEMENT_CHARACTER ((Py_UNICODE) 0xFFFD) + +/* === Public API ========================================================= */ + +/* --- Plain Py_UNICODE --------------------------------------------------- */ + +/* Create a Unicode Object from the Py_UNICODE buffer u of the given + size. + + u may be NULL which causes the contents to be undefined. It is the + user's responsibility to fill in the needed data afterwards. Note + that modifying the Unicode object contents after construction is + only allowed if u was set to NULL. + + The buffer is copied into the new object. */ + +PyAPI_FUNC(PyObject*) PyUnicode_FromUnicode( + const Py_UNICODE *u, /* Unicode buffer */ + Py_ssize_t size /* size of buffer */ + ); + +/* Similar to PyUnicode_FromUnicode(), but u points to Latin-1 encoded bytes */ +PyAPI_FUNC(PyObject*) PyUnicode_FromStringAndSize( + const char *u, /* char buffer */ + Py_ssize_t size /* size of buffer */ + ); + +/* Similar to PyUnicode_FromUnicode(), but u points to null-terminated + Latin-1 encoded bytes */ +PyAPI_FUNC(PyObject*) PyUnicode_FromString( + const char *u /* string */ + ); + +/* Return a read-only pointer to the Unicode object's internal + Py_UNICODE buffer. */ + +PyAPI_FUNC(Py_UNICODE *) PyUnicode_AsUnicode( + PyObject *unicode /* Unicode object */ + ); + +/* Get the length of the Unicode object. */ + +PyAPI_FUNC(Py_ssize_t) PyUnicode_GetSize( + PyObject *unicode /* Unicode object */ + ); + +/* Get the maximum ordinal for a Unicode character. */ +PyAPI_FUNC(Py_UNICODE) PyUnicode_GetMax(void); + +/* Resize an already allocated Unicode object to the new size length. + + *unicode is modified to point to the new (resized) object and 0 + returned on success. + + This API may only be called by the function which also called the + Unicode constructor. The refcount on the object must be 1. Otherwise, + an error is returned. + + Error handling is implemented as follows: an exception is set, -1 + is returned and *unicode left untouched. + +*/ + +PyAPI_FUNC(int) PyUnicode_Resize( + PyObject **unicode, /* Pointer to the Unicode object */ + Py_ssize_t length /* New length */ + ); + +/* Coerce obj to an Unicode object and return a reference with + *incremented* refcount. + + Coercion is done in the following way: + + 1. String and other char buffer compatible objects are decoded + under the assumptions that they contain data using the current + default encoding. Decoding is done in "strict" mode. + + 2. All other objects (including Unicode objects) raise an + exception. + + The API returns NULL in case of an error. The caller is responsible + for decref'ing the returned objects. + +*/ + +PyAPI_FUNC(PyObject*) PyUnicode_FromEncodedObject( + register PyObject *obj, /* Object */ + const char *encoding, /* encoding */ + const char *errors /* error handling */ + ); + +/* Coerce obj to an Unicode object and return a reference with + *incremented* refcount. + + Unicode objects are passed back as-is (subclasses are converted to + true Unicode objects), all other objects are delegated to + PyUnicode_FromEncodedObject(obj, NULL, "strict") which results in + using the default encoding as basis for decoding the object. + + The API returns NULL in case of an error. The caller is responsible + for decref'ing the returned objects. + +*/ + +PyAPI_FUNC(PyObject*) PyUnicode_FromObject( + register PyObject *obj /* Object */ + ); + +PyAPI_FUNC(PyObject *) PyUnicode_FromFormatV(const char*, va_list); +PyAPI_FUNC(PyObject *) PyUnicode_FromFormat(const char*, ...); + +/* Format the object based on the format_spec, as defined in PEP 3101 + (Advanced String Formatting). */ +PyAPI_FUNC(PyObject *) _PyUnicode_FormatAdvanced(PyObject *obj, + Py_UNICODE *format_spec, + Py_ssize_t format_spec_len); + +/* --- wchar_t support for platforms which support it --------------------- */ + +#ifdef HAVE_WCHAR_H + +/* Create a Unicode Object from the whcar_t buffer w of the given + size. + + The buffer is copied into the new object. */ + +PyAPI_FUNC(PyObject*) PyUnicode_FromWideChar( + register const wchar_t *w, /* wchar_t buffer */ + Py_ssize_t size /* size of buffer */ + ); + +/* Copies the Unicode Object contents into the wchar_t buffer w. At + most size wchar_t characters are copied. + + Note that the resulting wchar_t string may or may not be + 0-terminated. It is the responsibility of the caller to make sure + that the wchar_t string is 0-terminated in case this is required by + the application. + + Returns the number of wchar_t characters copied (excluding a + possibly trailing 0-termination character) or -1 in case of an + error. */ + +PyAPI_FUNC(Py_ssize_t) PyUnicode_AsWideChar( + PyUnicodeObject *unicode, /* Unicode object */ + register wchar_t *w, /* wchar_t buffer */ + Py_ssize_t size /* size of buffer */ + ); + +#endif + +/* --- Unicode ordinals --------------------------------------------------- */ + +/* Create a Unicode Object from the given Unicode code point ordinal. + + The ordinal must be in range(0x10000) on narrow Python builds + (UCS2), and range(0x110000) on wide builds (UCS4). A ValueError is + raised in case it is not. + +*/ + +PyAPI_FUNC(PyObject*) PyUnicode_FromOrdinal(int ordinal); + +/* --- Free-list management ----------------------------------------------- */ + +/* Clear the free list used by the Unicode implementation. + + This can be used to release memory used for objects on the free + list back to the Python memory allocator. + +*/ + +PyAPI_FUNC(int) PyUnicode_ClearFreeList(void); + +/* === Builtin Codecs ===================================================== + + Many of these APIs take two arguments encoding and errors. These + parameters encoding and errors have the same semantics as the ones + of the builtin unicode() API. + + Setting encoding to NULL causes the default encoding to be used. + + Error handling is set by errors which may also be set to NULL + meaning to use the default handling defined for the codec. Default + error handling for all builtin codecs is "strict" (ValueErrors are + raised). + + The codecs all use a similar interface. Only deviation from the + generic ones are documented. + +*/ + +/* --- Manage the default encoding ---------------------------------------- */ + +/* Return a Python string holding the default encoded value of the + Unicode object. + + The resulting string is cached in the Unicode object for subsequent + usage by this function. The cached version is needed to implement + the character buffer interface and will live (at least) as long as + the Unicode object itself. + + The refcount of the string is *not* incremented. + + *** Exported for internal use by the interpreter only !!! *** + +*/ + +PyAPI_FUNC(PyObject *) _PyUnicode_AsDefaultEncodedString( + PyObject *, const char *); + +/* Returns the currently active default encoding. + + The default encoding is currently implemented as run-time settable + process global. This may change in future versions of the + interpreter to become a parameter which is managed on a per-thread + basis. + + */ + +PyAPI_FUNC(const char*) PyUnicode_GetDefaultEncoding(void); + +/* Sets the currently active default encoding. + + Returns 0 on success, -1 in case of an error. + + */ + +PyAPI_FUNC(int) PyUnicode_SetDefaultEncoding( + const char *encoding /* Encoding name in standard form */ + ); + +/* --- Generic Codecs ----------------------------------------------------- */ + +/* Create a Unicode object by decoding the encoded string s of the + given size. */ + +PyAPI_FUNC(PyObject*) PyUnicode_Decode( + const char *s, /* encoded string */ + Py_ssize_t size, /* size of buffer */ + const char *encoding, /* encoding */ + const char *errors /* error handling */ + ); + +/* Encodes a Py_UNICODE buffer of the given size and returns a + Python string object. */ + +PyAPI_FUNC(PyObject*) PyUnicode_Encode( + const Py_UNICODE *s, /* Unicode char buffer */ + Py_ssize_t size, /* number of Py_UNICODE chars to encode */ + const char *encoding, /* encoding */ + const char *errors /* error handling */ + ); + +/* Encodes a Unicode object and returns the result as Python + object. */ + +PyAPI_FUNC(PyObject*) PyUnicode_AsEncodedObject( + PyObject *unicode, /* Unicode object */ + const char *encoding, /* encoding */ + const char *errors /* error handling */ + ); + +/* Encodes a Unicode object and returns the result as Python string + object. */ + +PyAPI_FUNC(PyObject*) PyUnicode_AsEncodedString( + PyObject *unicode, /* Unicode object */ + const char *encoding, /* encoding */ + const char *errors /* error handling */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_BuildEncodingMap( + PyObject* string /* 256 character map */ + ); + + +/* --- UTF-7 Codecs ------------------------------------------------------- */ + +PyAPI_FUNC(PyObject*) PyUnicode_DecodeUTF7( + const char *string, /* UTF-7 encoded string */ + Py_ssize_t length, /* size of string */ + const char *errors /* error handling */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_DecodeUTF7Stateful( + const char *string, /* UTF-7 encoded string */ + Py_ssize_t length, /* size of string */ + const char *errors, /* error handling */ + Py_ssize_t *consumed /* bytes consumed */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_EncodeUTF7( + const Py_UNICODE *data, /* Unicode char buffer */ + Py_ssize_t length, /* number of Py_UNICODE chars to encode */ + int base64SetO, /* Encode RFC2152 Set O characters in base64 */ + int base64WhiteSpace, /* Encode whitespace (sp, ht, nl, cr) in base64 */ + const char *errors /* error handling */ + ); + +/* --- UTF-8 Codecs ------------------------------------------------------- */ + +PyAPI_FUNC(PyObject*) PyUnicode_DecodeUTF8( + const char *string, /* UTF-8 encoded string */ + Py_ssize_t length, /* size of string */ + const char *errors /* error handling */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_DecodeUTF8Stateful( + const char *string, /* UTF-8 encoded string */ + Py_ssize_t length, /* size of string */ + const char *errors, /* error handling */ + Py_ssize_t *consumed /* bytes consumed */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_AsUTF8String( + PyObject *unicode /* Unicode object */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_EncodeUTF8( + const Py_UNICODE *data, /* Unicode char buffer */ + Py_ssize_t length, /* number of Py_UNICODE chars to encode */ + const char *errors /* error handling */ + ); + +/* --- UTF-32 Codecs ------------------------------------------------------ */ + +/* Decodes length bytes from a UTF-32 encoded buffer string and returns + the corresponding Unicode object. + + errors (if non-NULL) defines the error handling. It defaults + to "strict". + + If byteorder is non-NULL, the decoder starts decoding using the + given byte order: + + *byteorder == -1: little endian + *byteorder == 0: native order + *byteorder == 1: big endian + + In native mode, the first four bytes of the stream are checked for a + BOM mark. If found, the BOM mark is analysed, the byte order + adjusted and the BOM skipped. In the other modes, no BOM mark + interpretation is done. After completion, *byteorder is set to the + current byte order at the end of input data. + + If byteorder is NULL, the codec starts in native order mode. + +*/ + +PyAPI_FUNC(PyObject*) PyUnicode_DecodeUTF32( + const char *string, /* UTF-32 encoded string */ + Py_ssize_t length, /* size of string */ + const char *errors, /* error handling */ + int *byteorder /* pointer to byteorder to use + 0=native;-1=LE,1=BE; updated on + exit */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_DecodeUTF32Stateful( + const char *string, /* UTF-32 encoded string */ + Py_ssize_t length, /* size of string */ + const char *errors, /* error handling */ + int *byteorder, /* pointer to byteorder to use + 0=native;-1=LE,1=BE; updated on + exit */ + Py_ssize_t *consumed /* bytes consumed */ + ); + +/* Returns a Python string using the UTF-32 encoding in native byte + order. The string always starts with a BOM mark. */ + +PyAPI_FUNC(PyObject*) PyUnicode_AsUTF32String( + PyObject *unicode /* Unicode object */ + ); + +/* Returns a Python string object holding the UTF-32 encoded value of + the Unicode data. + + If byteorder is not 0, output is written according to the following + byte order: + + byteorder == -1: little endian + byteorder == 0: native byte order (writes a BOM mark) + byteorder == 1: big endian + + If byteorder is 0, the output string will always start with the + Unicode BOM mark (U+FEFF). In the other two modes, no BOM mark is + prepended. + +*/ + +PyAPI_FUNC(PyObject*) PyUnicode_EncodeUTF32( + const Py_UNICODE *data, /* Unicode char buffer */ + Py_ssize_t length, /* number of Py_UNICODE chars to encode */ + const char *errors, /* error handling */ + int byteorder /* byteorder to use 0=BOM+native;-1=LE,1=BE */ + ); + +/* --- UTF-16 Codecs ------------------------------------------------------ */ + +/* Decodes length bytes from a UTF-16 encoded buffer string and returns + the corresponding Unicode object. + + errors (if non-NULL) defines the error handling. It defaults + to "strict". + + If byteorder is non-NULL, the decoder starts decoding using the + given byte order: + + *byteorder == -1: little endian + *byteorder == 0: native order + *byteorder == 1: big endian + + In native mode, the first two bytes of the stream are checked for a + BOM mark. If found, the BOM mark is analysed, the byte order + adjusted and the BOM skipped. In the other modes, no BOM mark + interpretation is done. After completion, *byteorder is set to the + current byte order at the end of input data. + + If byteorder is NULL, the codec starts in native order mode. + +*/ + +PyAPI_FUNC(PyObject*) PyUnicode_DecodeUTF16( + const char *string, /* UTF-16 encoded string */ + Py_ssize_t length, /* size of string */ + const char *errors, /* error handling */ + int *byteorder /* pointer to byteorder to use + 0=native;-1=LE,1=BE; updated on + exit */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_DecodeUTF16Stateful( + const char *string, /* UTF-16 encoded string */ + Py_ssize_t length, /* size of string */ + const char *errors, /* error handling */ + int *byteorder, /* pointer to byteorder to use + 0=native;-1=LE,1=BE; updated on + exit */ + Py_ssize_t *consumed /* bytes consumed */ + ); + +/* Returns a Python string using the UTF-16 encoding in native byte + order. The string always starts with a BOM mark. */ + +PyAPI_FUNC(PyObject*) PyUnicode_AsUTF16String( + PyObject *unicode /* Unicode object */ + ); + +/* Returns a Python string object holding the UTF-16 encoded value of + the Unicode data. + + If byteorder is not 0, output is written according to the following + byte order: + + byteorder == -1: little endian + byteorder == 0: native byte order (writes a BOM mark) + byteorder == 1: big endian + + If byteorder is 0, the output string will always start with the + Unicode BOM mark (U+FEFF). In the other two modes, no BOM mark is + prepended. + + Note that Py_UNICODE data is being interpreted as UTF-16 reduced to + UCS-2. This trick makes it possible to add full UTF-16 capabilities + at a later point without compromising the APIs. + +*/ + +PyAPI_FUNC(PyObject*) PyUnicode_EncodeUTF16( + const Py_UNICODE *data, /* Unicode char buffer */ + Py_ssize_t length, /* number of Py_UNICODE chars to encode */ + const char *errors, /* error handling */ + int byteorder /* byteorder to use 0=BOM+native;-1=LE,1=BE */ + ); + +/* --- Unicode-Escape Codecs ---------------------------------------------- */ + +PyAPI_FUNC(PyObject*) PyUnicode_DecodeUnicodeEscape( + const char *string, /* Unicode-Escape encoded string */ + Py_ssize_t length, /* size of string */ + const char *errors /* error handling */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_AsUnicodeEscapeString( + PyObject *unicode /* Unicode object */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_EncodeUnicodeEscape( + const Py_UNICODE *data, /* Unicode char buffer */ + Py_ssize_t length /* Number of Py_UNICODE chars to encode */ + ); + +/* --- Raw-Unicode-Escape Codecs ------------------------------------------ */ + +PyAPI_FUNC(PyObject*) PyUnicode_DecodeRawUnicodeEscape( + const char *string, /* Raw-Unicode-Escape encoded string */ + Py_ssize_t length, /* size of string */ + const char *errors /* error handling */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_AsRawUnicodeEscapeString( + PyObject *unicode /* Unicode object */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_EncodeRawUnicodeEscape( + const Py_UNICODE *data, /* Unicode char buffer */ + Py_ssize_t length /* Number of Py_UNICODE chars to encode */ + ); + +/* --- Unicode Internal Codec --------------------------------------------- + + Only for internal use in _codecsmodule.c */ + +PyObject *_PyUnicode_DecodeUnicodeInternal( + const char *string, + Py_ssize_t length, + const char *errors + ); + +/* --- Latin-1 Codecs ----------------------------------------------------- + + Note: Latin-1 corresponds to the first 256 Unicode ordinals. + +*/ + +PyAPI_FUNC(PyObject*) PyUnicode_DecodeLatin1( + const char *string, /* Latin-1 encoded string */ + Py_ssize_t length, /* size of string */ + const char *errors /* error handling */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_AsLatin1String( + PyObject *unicode /* Unicode object */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_EncodeLatin1( + const Py_UNICODE *data, /* Unicode char buffer */ + Py_ssize_t length, /* Number of Py_UNICODE chars to encode */ + const char *errors /* error handling */ + ); + +/* --- ASCII Codecs ------------------------------------------------------- + + Only 7-bit ASCII data is excepted. All other codes generate errors. + +*/ + +PyAPI_FUNC(PyObject*) PyUnicode_DecodeASCII( + const char *string, /* ASCII encoded string */ + Py_ssize_t length, /* size of string */ + const char *errors /* error handling */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_AsASCIIString( + PyObject *unicode /* Unicode object */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_EncodeASCII( + const Py_UNICODE *data, /* Unicode char buffer */ + Py_ssize_t length, /* Number of Py_UNICODE chars to encode */ + const char *errors /* error handling */ + ); + +/* --- Character Map Codecs ----------------------------------------------- + + This codec uses mappings to encode and decode characters. + + Decoding mappings must map single string characters to single + Unicode characters, integers (which are then interpreted as Unicode + ordinals) or None (meaning "undefined mapping" and causing an + error). + + Encoding mappings must map single Unicode characters to single + string characters, integers (which are then interpreted as Latin-1 + ordinals) or None (meaning "undefined mapping" and causing an + error). + + If a character lookup fails with a LookupError, the character is + copied as-is meaning that its ordinal value will be interpreted as + Unicode or Latin-1 ordinal resp. Because of this mappings only need + to contain those mappings which map characters to different code + points. + +*/ + +PyAPI_FUNC(PyObject*) PyUnicode_DecodeCharmap( + const char *string, /* Encoded string */ + Py_ssize_t length, /* size of string */ + PyObject *mapping, /* character mapping + (char ordinal -> unicode ordinal) */ + const char *errors /* error handling */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_AsCharmapString( + PyObject *unicode, /* Unicode object */ + PyObject *mapping /* character mapping + (unicode ordinal -> char ordinal) */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_EncodeCharmap( + const Py_UNICODE *data, /* Unicode char buffer */ + Py_ssize_t length, /* Number of Py_UNICODE chars to encode */ + PyObject *mapping, /* character mapping + (unicode ordinal -> char ordinal) */ + const char *errors /* error handling */ + ); + +/* Translate a Py_UNICODE buffer of the given length by applying a + character mapping table to it and return the resulting Unicode + object. + + The mapping table must map Unicode ordinal integers to Unicode + ordinal integers or None (causing deletion of the character). + + Mapping tables may be dictionaries or sequences. Unmapped character + ordinals (ones which cause a LookupError) are left untouched and + are copied as-is. + +*/ + +PyAPI_FUNC(PyObject *) PyUnicode_TranslateCharmap( + const Py_UNICODE *data, /* Unicode char buffer */ + Py_ssize_t length, /* Number of Py_UNICODE chars to encode */ + PyObject *table, /* Translate table */ + const char *errors /* error handling */ + ); + +#ifdef MS_WIN32 + +/* --- MBCS codecs for Windows -------------------------------------------- */ + +PyAPI_FUNC(PyObject*) PyUnicode_DecodeMBCS( + const char *string, /* MBCS encoded string */ + Py_ssize_t length, /* size of string */ + const char *errors /* error handling */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_DecodeMBCSStateful( + const char *string, /* MBCS encoded string */ + Py_ssize_t length, /* size of string */ + const char *errors, /* error handling */ + Py_ssize_t *consumed /* bytes consumed */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_AsMBCSString( + PyObject *unicode /* Unicode object */ + ); + +PyAPI_FUNC(PyObject*) PyUnicode_EncodeMBCS( + const Py_UNICODE *data, /* Unicode char buffer */ + Py_ssize_t length, /* Number of Py_UNICODE chars to encode */ + const char *errors /* error handling */ + ); + +#endif /* MS_WIN32 */ + +/* --- Decimal Encoder ---------------------------------------------------- */ + +/* Takes a Unicode string holding a decimal value and writes it into + an output buffer using standard ASCII digit codes. + + The output buffer has to provide at least length+1 bytes of storage + area. The output string is 0-terminated. + + The encoder converts whitespace to ' ', decimal characters to their + corresponding ASCII digit and all other Latin-1 characters except + \0 as-is. Characters outside this range (Unicode ordinals 1-256) + are treated as errors. This includes embedded NULL bytes. + + Error handling is defined by the errors argument: + + NULL or "strict": raise a ValueError + "ignore": ignore the wrong characters (these are not copied to the + output buffer) + "replace": replaces illegal characters with '?' + + Returns 0 on success, -1 on failure. + +*/ + +PyAPI_FUNC(int) PyUnicode_EncodeDecimal( + Py_UNICODE *s, /* Unicode buffer */ + Py_ssize_t length, /* Number of Py_UNICODE chars to encode */ + char *output, /* Output buffer; must have size >= length */ + const char *errors /* error handling */ + ); + +/* --- Methods & Slots ---------------------------------------------------- + + These are capable of handling Unicode objects and strings on input + (we refer to them as strings in the descriptions) and return + Unicode objects or integers as apporpriate. */ + +/* Concat two strings giving a new Unicode string. */ + +PyAPI_FUNC(PyObject*) PyUnicode_Concat( + PyObject *left, /* Left string */ + PyObject *right /* Right string */ + ); + +/* Split a string giving a list of Unicode strings. + + If sep is NULL, splitting will be done at all whitespace + substrings. Otherwise, splits occur at the given separator. + + At most maxsplit splits will be done. If negative, no limit is set. + + Separators are not included in the resulting list. + +*/ + +PyAPI_FUNC(PyObject*) PyUnicode_Split( + PyObject *s, /* String to split */ + PyObject *sep, /* String separator */ + Py_ssize_t maxsplit /* Maxsplit count */ + ); + +/* Dito, but split at line breaks. + + CRLF is considered to be one line break. Line breaks are not + included in the resulting list. */ + +PyAPI_FUNC(PyObject*) PyUnicode_Splitlines( + PyObject *s, /* String to split */ + int keepends /* If true, line end markers are included */ + ); + +/* Partition a string using a given separator. */ + +PyAPI_FUNC(PyObject*) PyUnicode_Partition( + PyObject *s, /* String to partition */ + PyObject *sep /* String separator */ + ); + +/* Partition a string using a given separator, searching from the end of the + string. */ + +PyAPI_FUNC(PyObject*) PyUnicode_RPartition( + PyObject *s, /* String to partition */ + PyObject *sep /* String separator */ + ); + +/* Split a string giving a list of Unicode strings. + + If sep is NULL, splitting will be done at all whitespace + substrings. Otherwise, splits occur at the given separator. + + At most maxsplit splits will be done. But unlike PyUnicode_Split + PyUnicode_RSplit splits from the end of the string. If negative, + no limit is set. + + Separators are not included in the resulting list. + +*/ + +PyAPI_FUNC(PyObject*) PyUnicode_RSplit( + PyObject *s, /* String to split */ + PyObject *sep, /* String separator */ + Py_ssize_t maxsplit /* Maxsplit count */ + ); + +/* Translate a string by applying a character mapping table to it and + return the resulting Unicode object. + + The mapping table must map Unicode ordinal integers to Unicode + ordinal integers or None (causing deletion of the character). + + Mapping tables may be dictionaries or sequences. Unmapped character + ordinals (ones which cause a LookupError) are left untouched and + are copied as-is. + +*/ + +PyAPI_FUNC(PyObject *) PyUnicode_Translate( + PyObject *str, /* String */ + PyObject *table, /* Translate table */ + const char *errors /* error handling */ + ); + +/* Join a sequence of strings using the given separator and return + the resulting Unicode string. */ + +PyAPI_FUNC(PyObject*) PyUnicode_Join( + PyObject *separator, /* Separator string */ + PyObject *seq /* Sequence object */ + ); + +/* Return 1 if substr matches str[start:end] at the given tail end, 0 + otherwise. */ + +PyAPI_FUNC(Py_ssize_t) PyUnicode_Tailmatch( + PyObject *str, /* String */ + PyObject *substr, /* Prefix or Suffix string */ + Py_ssize_t start, /* Start index */ + Py_ssize_t end, /* Stop index */ + int direction /* Tail end: -1 prefix, +1 suffix */ + ); + +/* Return the first position of substr in str[start:end] using the + given search direction or -1 if not found. -2 is returned in case + an error occurred and an exception is set. */ + +PyAPI_FUNC(Py_ssize_t) PyUnicode_Find( + PyObject *str, /* String */ + PyObject *substr, /* Substring to find */ + Py_ssize_t start, /* Start index */ + Py_ssize_t end, /* Stop index */ + int direction /* Find direction: +1 forward, -1 backward */ + ); + +/* Count the number of occurrences of substr in str[start:end]. */ + +PyAPI_FUNC(Py_ssize_t) PyUnicode_Count( + PyObject *str, /* String */ + PyObject *substr, /* Substring to count */ + Py_ssize_t start, /* Start index */ + Py_ssize_t end /* Stop index */ + ); + +/* Replace at most maxcount occurrences of substr in str with replstr + and return the resulting Unicode object. */ + +PyAPI_FUNC(PyObject *) PyUnicode_Replace( + PyObject *str, /* String */ + PyObject *substr, /* Substring to find */ + PyObject *replstr, /* Substring to replace */ + Py_ssize_t maxcount /* Max. number of replacements to apply; + -1 = all */ + ); + +/* Compare two strings and return -1, 0, 1 for less than, equal, + greater than resp. */ + +PyAPI_FUNC(int) PyUnicode_Compare( + PyObject *left, /* Left string */ + PyObject *right /* Right string */ + ); + +/* Rich compare two strings and return one of the following: + + - NULL in case an exception was raised + - Py_True or Py_False for successfuly comparisons + - Py_NotImplemented in case the type combination is unknown + + Note that Py_EQ and Py_NE comparisons can cause a UnicodeWarning in + case the conversion of the arguments to Unicode fails with a + UnicodeDecodeError. + + Possible values for op: + + Py_GT, Py_GE, Py_EQ, Py_NE, Py_LT, Py_LE + +*/ + +PyAPI_FUNC(PyObject *) PyUnicode_RichCompare( + PyObject *left, /* Left string */ + PyObject *right, /* Right string */ + int op /* Operation: Py_EQ, Py_NE, Py_GT, etc. */ + ); + +/* Apply a argument tuple or dictionary to a format string and return + the resulting Unicode string. */ + +PyAPI_FUNC(PyObject *) PyUnicode_Format( + PyObject *format, /* Format string */ + PyObject *args /* Argument tuple or dictionary */ + ); + +/* Checks whether element is contained in container and return 1/0 + accordingly. + + element has to coerce to an one element Unicode string. -1 is + returned in case of an error. */ + +PyAPI_FUNC(int) PyUnicode_Contains( + PyObject *container, /* Container string */ + PyObject *element /* Element string */ + ); + +/* Externally visible for str.strip(unicode) */ +PyAPI_FUNC(PyObject *) _PyUnicode_XStrip( + PyUnicodeObject *self, + int striptype, + PyObject *sepobj + ); + +/* === Characters Type APIs =============================================== */ + +/* Helper array used by Py_UNICODE_ISSPACE(). */ + +PyAPI_DATA(const unsigned char) _Py_ascii_whitespace[]; + +/* These should not be used directly. Use the Py_UNICODE_IS* and + Py_UNICODE_TO* macros instead. + + These APIs are implemented in Objects/unicodectype.c. + +*/ + +PyAPI_FUNC(int) _PyUnicode_IsLowercase( + Py_UNICODE ch /* Unicode character */ + ); + +PyAPI_FUNC(int) _PyUnicode_IsUppercase( + Py_UNICODE ch /* Unicode character */ + ); + +PyAPI_FUNC(int) _PyUnicode_IsTitlecase( + Py_UNICODE ch /* Unicode character */ + ); + +PyAPI_FUNC(int) _PyUnicode_IsWhitespace( + const Py_UNICODE ch /* Unicode character */ + ); + +PyAPI_FUNC(int) _PyUnicode_IsLinebreak( + const Py_UNICODE ch /* Unicode character */ + ); + +PyAPI_FUNC(Py_UNICODE) _PyUnicode_ToLowercase( + Py_UNICODE ch /* Unicode character */ + ); + +PyAPI_FUNC(Py_UNICODE) _PyUnicode_ToUppercase( + Py_UNICODE ch /* Unicode character */ + ); + +PyAPI_FUNC(Py_UNICODE) _PyUnicode_ToTitlecase( + Py_UNICODE ch /* Unicode character */ + ); + +PyAPI_FUNC(int) _PyUnicode_ToDecimalDigit( + Py_UNICODE ch /* Unicode character */ + ); + +PyAPI_FUNC(int) _PyUnicode_ToDigit( + Py_UNICODE ch /* Unicode character */ + ); + +PyAPI_FUNC(double) _PyUnicode_ToNumeric( + Py_UNICODE ch /* Unicode character */ + ); + +PyAPI_FUNC(int) _PyUnicode_IsDecimalDigit( + Py_UNICODE ch /* Unicode character */ + ); + +PyAPI_FUNC(int) _PyUnicode_IsDigit( + Py_UNICODE ch /* Unicode character */ + ); + +PyAPI_FUNC(int) _PyUnicode_IsNumeric( + Py_UNICODE ch /* Unicode character */ + ); + +PyAPI_FUNC(int) _PyUnicode_IsAlpha( + Py_UNICODE ch /* Unicode character */ + ); + +#ifdef __cplusplus +} +#endif +#endif /* Py_USING_UNICODE */ +#endif /* !Py_UNICODEOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/warnings.h b/AppPkg/Applications/Python/Python-2.7.10/Include/warnings.h new file mode 100644 index 0000000000..bf8f9636fd --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/warnings.h @@ -0,0 +1,23 @@ +#ifndef Py_WARNINGS_H +#define Py_WARNINGS_H +#ifdef __cplusplus +extern "C" { +#endif + +PyAPI_FUNC(void) _PyWarnings_Init(void); + +PyAPI_FUNC(int) PyErr_WarnEx(PyObject *, const char *, Py_ssize_t); +PyAPI_FUNC(int) PyErr_WarnExplicit(PyObject *, const char *, const char *, int, + const char *, PyObject *); + +#define PyErr_WarnPy3k(msg, stacklevel) \ + (Py_Py3kWarningFlag ? PyErr_WarnEx(PyExc_DeprecationWarning, msg, stacklevel) : 0) + +/* DEPRECATED: Use PyErr_WarnEx() instead. */ +#define PyErr_Warn(category, msg) PyErr_WarnEx(category, msg, 1) + +#ifdef __cplusplus +} +#endif +#endif /* !Py_WARNINGS_H */ + diff --git a/AppPkg/Applications/Python/Python-2.7.10/Include/weakrefobject.h b/AppPkg/Applications/Python/Python-2.7.10/Include/weakrefobject.h new file mode 100644 index 0000000000..49c23b1034 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Include/weakrefobject.h @@ -0,0 +1,82 @@ +/* Weak references objects for Python. */ + +#ifndef Py_WEAKREFOBJECT_H +#define Py_WEAKREFOBJECT_H +#ifdef __cplusplus +extern "C" { +#endif + + +typedef struct _PyWeakReference PyWeakReference; + +/* PyWeakReference is the base struct for the Python ReferenceType, ProxyType, + * and CallableProxyType. + */ +struct _PyWeakReference { + PyObject_HEAD + + /* The object to which this is a weak reference, or Py_None if none. + * Note that this is a stealth reference: wr_object's refcount is + * not incremented to reflect this pointer. + */ + PyObject *wr_object; + + /* A callable to invoke when wr_object dies, or NULL if none. */ + PyObject *wr_callback; + + /* A cache for wr_object's hash code. As usual for hashes, this is -1 + * if the hash code isn't known yet. + */ + long hash; + + /* If wr_object is weakly referenced, wr_object has a doubly-linked NULL- + * terminated list of weak references to it. These are the list pointers. + * If wr_object goes away, wr_object is set to Py_None, and these pointers + * have no meaning then. + */ + PyWeakReference *wr_prev; + PyWeakReference *wr_next; +}; + +PyAPI_DATA(PyTypeObject) _PyWeakref_RefType; +PyAPI_DATA(PyTypeObject) _PyWeakref_ProxyType; +PyAPI_DATA(PyTypeObject) _PyWeakref_CallableProxyType; + +#define PyWeakref_CheckRef(op) PyObject_TypeCheck(op, &_PyWeakref_RefType) +#define PyWeakref_CheckRefExact(op) \ + (Py_TYPE(op) == &_PyWeakref_RefType) +#define PyWeakref_CheckProxy(op) \ + ((Py_TYPE(op) == &_PyWeakref_ProxyType) || \ + (Py_TYPE(op) == &_PyWeakref_CallableProxyType)) + +#define PyWeakref_Check(op) \ + (PyWeakref_CheckRef(op) || PyWeakref_CheckProxy(op)) + + +PyAPI_FUNC(PyObject *) PyWeakref_NewRef(PyObject *ob, + PyObject *callback); +PyAPI_FUNC(PyObject *) PyWeakref_NewProxy(PyObject *ob, + PyObject *callback); +PyAPI_FUNC(PyObject *) PyWeakref_GetObject(PyObject *ref); + +PyAPI_FUNC(Py_ssize_t) _PyWeakref_GetWeakrefCount(PyWeakReference *head); + +PyAPI_FUNC(void) _PyWeakref_ClearRef(PyWeakReference *self); + +/* Explanation for the Py_REFCNT() check: when a weakref's target is part + of a long chain of deallocations which triggers the trashcan mechanism, + clearing the weakrefs can be delayed long after the target's refcount + has dropped to zero. In the meantime, code accessing the weakref will + be able to "see" the target object even though it is supposed to be + unreachable. See issue #16602. */ + +#define PyWeakref_GET_OBJECT(ref) \ + (Py_REFCNT(((PyWeakReference *)(ref))->wr_object) > 0 \ + ? ((PyWeakReference *)(ref))->wr_object \ + : Py_None) + + +#ifdef __cplusplus +} +#endif +#endif /* !Py_WEAKREFOBJECT_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Parser/acceler.c b/AppPkg/Applications/Python/Python-2.7.10/Parser/acceler.c new file mode 100644 index 0000000000..f6036d9739 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Parser/acceler.c @@ -0,0 +1,125 @@ + +/* Parser accelerator module */ + +/* The parser as originally conceived had disappointing performance. + This module does some precomputation that speeds up the selection + of a DFA based upon a token, turning a search through an array + into a simple indexing operation. The parser now cannot work + without the accelerators installed. Note that the accelerators + are installed dynamically when the parser is initialized, they + are not part of the static data structure written on graminit.[ch] + by the parser generator. */ + +#include "pgenheaders.h" +#include "grammar.h" +#include "node.h" +#include "token.h" +#include "parser.h" + +/* Forward references */ +static void fixdfa(grammar *, dfa *); +static void fixstate(grammar *, state *); + +void +PyGrammar_AddAccelerators(grammar *g) +{ + dfa *d; + int i; + d = g->g_dfa; + for (i = g->g_ndfas; --i >= 0; d++) + fixdfa(g, d); + g->g_accel = 1; +} + +void +PyGrammar_RemoveAccelerators(grammar *g) +{ + dfa *d; + int i; + g->g_accel = 0; + d = g->g_dfa; + for (i = g->g_ndfas; --i >= 0; d++) { + state *s; + int j; + s = d->d_state; + for (j = 0; j < d->d_nstates; j++, s++) { + if (s->s_accel) + PyObject_FREE(s->s_accel); + s->s_accel = NULL; + } + } +} + +static void +fixdfa(grammar *g, dfa *d) +{ + state *s; + int j; + s = d->d_state; + for (j = 0; j < d->d_nstates; j++, s++) + fixstate(g, s); +} + +static void +fixstate(grammar *g, state *s) +{ + arc *a; + int k; + int *accel; + int nl = g->g_ll.ll_nlabels; + s->s_accept = 0; + accel = (int *) PyObject_MALLOC(nl * sizeof(int)); + if (accel == NULL) { + fprintf(stderr, "no mem to build parser accelerators\n"); + exit(1); + } + for (k = 0; k < nl; k++) + accel[k] = -1; + a = s->s_arc; + for (k = s->s_narcs; --k >= 0; a++) { + int lbl = a->a_lbl; + label *l = &g->g_ll.ll_label[lbl]; + int type = l->lb_type; + if (a->a_arrow >= (1 << 7)) { + printf("XXX too many states!\n"); + continue; + } + if (ISNONTERMINAL(type)) { + dfa *d1 = PyGrammar_FindDFA(g, type); + int ibit; + if (type - NT_OFFSET >= (1 << 7)) { + printf("XXX too high nonterminal number!\n"); + continue; + } + for (ibit = 0; ibit < g->g_ll.ll_nlabels; ibit++) { + if (testbit(d1->d_first, ibit)) { + if (accel[ibit] != -1) + printf("XXX ambiguity!\n"); + accel[ibit] = a->a_arrow | (1 << 7) | + ((type - NT_OFFSET) << 8); + } + } + } + else if (lbl == EMPTY) + s->s_accept = 1; + else if (lbl >= 0 && lbl < nl) + accel[lbl] = a->a_arrow; + } + while (nl > 0 && accel[nl-1] == -1) + nl--; + for (k = 0; k < nl && accel[k] == -1;) + k++; + if (k < nl) { + int i; + s->s_accel = (int *) PyObject_MALLOC((nl-k) * sizeof(int)); + if (s->s_accel == NULL) { + fprintf(stderr, "no mem to add parser accelerators\n"); + exit(1); + } + s->s_lower = k; + s->s_upper = nl; + for (i = 0; k < nl; i++, k++) + s->s_accel[i] = accel[k]; + } + PyObject_FREE(accel); +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Parser/bitset.c b/AppPkg/Applications/Python/Python-2.7.10/Parser/bitset.c new file mode 100644 index 0000000000..3bf5da1dba --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Parser/bitset.c @@ -0,0 +1,66 @@ + +/* Bitset primitives used by the parser generator */ + +#include "pgenheaders.h" +#include "bitset.h" + +bitset +newbitset(int nbits) +{ + int nbytes = NBYTES(nbits); + bitset ss = (char *)PyObject_MALLOC(sizeof(BYTE) * nbytes); + + if (ss == NULL) + Py_FatalError("no mem for bitset"); + + ss += nbytes; + while (--nbytes >= 0) + *--ss = 0; + return ss; +} + +void +delbitset(bitset ss) +{ + PyObject_FREE(ss); +} + +int +addbit(bitset ss, int ibit) +{ + int ibyte = BIT2BYTE(ibit); + BYTE mask = BIT2MASK(ibit); + + if (ss[ibyte] & mask) + return 0; /* Bit already set */ + ss[ibyte] |= mask; + return 1; +} + +#if 0 /* Now a macro */ +int +testbit(bitset ss, int ibit) +{ + return (ss[BIT2BYTE(ibit)] & BIT2MASK(ibit)) != 0; +} +#endif + +int +samebitset(bitset ss1, bitset ss2, int nbits) +{ + int i; + + for (i = NBYTES(nbits); --i >= 0; ) + if (*ss1++ != *ss2++) + return 0; + return 1; +} + +void +mergebitset(bitset ss1, bitset ss2, int nbits) +{ + int i; + + for (i = NBYTES(nbits); --i >= 0; ) + *ss1++ |= *ss2++; +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Parser/firstsets.c b/AppPkg/Applications/Python/Python-2.7.10/Parser/firstsets.c new file mode 100644 index 0000000000..69faf8f09e --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Parser/firstsets.c @@ -0,0 +1,113 @@ + +/* Computation of FIRST stets */ + +#include "pgenheaders.h" +#include "grammar.h" +#include "token.h" + +extern int Py_DebugFlag; + +/* Forward */ +static void calcfirstset(grammar *, dfa *); + +void +addfirstsets(grammar *g) +{ + int i; + dfa *d; + + if (Py_DebugFlag) + printf("Adding FIRST sets ...\n"); + for (i = 0; i < g->g_ndfas; i++) { + d = &g->g_dfa[i]; + if (d->d_first == NULL) + calcfirstset(g, d); + } +} + +static void +calcfirstset(grammar *g, dfa *d) +{ + int i, j; + state *s; + arc *a; + int nsyms; + int *sym; + int nbits; + static bitset dummy; + bitset result; + int type; + dfa *d1; + label *l0; + + if (Py_DebugFlag) + printf("Calculate FIRST set for '%s'\n", d->d_name); + + if (dummy == NULL) + dummy = newbitset(1); + if (d->d_first == dummy) { + fprintf(stderr, "Left-recursion for '%s'\n", d->d_name); + return; + } + if (d->d_first != NULL) { + fprintf(stderr, "Re-calculating FIRST set for '%s' ???\n", + d->d_name); + } + d->d_first = dummy; + + l0 = g->g_ll.ll_label; + nbits = g->g_ll.ll_nlabels; + result = newbitset(nbits); + + sym = (int *)PyObject_MALLOC(sizeof(int)); + if (sym == NULL) + Py_FatalError("no mem for new sym in calcfirstset"); + nsyms = 1; + sym[0] = findlabel(&g->g_ll, d->d_type, (char *)NULL); + + s = &d->d_state[d->d_initial]; + for (i = 0; i < s->s_narcs; i++) { + a = &s->s_arc[i]; + for (j = 0; j < nsyms; j++) { + if (sym[j] == a->a_lbl) + break; + } + if (j >= nsyms) { /* New label */ + sym = (int *)PyObject_REALLOC(sym, + sizeof(int) * (nsyms + 1)); + if (sym == NULL) + Py_FatalError( + "no mem to resize sym in calcfirstset"); + sym[nsyms++] = a->a_lbl; + type = l0[a->a_lbl].lb_type; + if (ISNONTERMINAL(type)) { + d1 = PyGrammar_FindDFA(g, type); + if (d1->d_first == dummy) { + fprintf(stderr, + "Left-recursion below '%s'\n", + d->d_name); + } + else { + if (d1->d_first == NULL) + calcfirstset(g, d1); + mergebitset(result, + d1->d_first, nbits); + } + } + else if (ISTERMINAL(type)) { + addbit(result, a->a_lbl); + } + } + } + d->d_first = result; + if (Py_DebugFlag) { + printf("FIRST set for '%s': {", d->d_name); + for (i = 0; i < nbits; i++) { + if (testbit(result, i)) + printf(" %s", PyGrammar_LabelRepr(&l0[i])); + } + printf(" }\n"); + } + + PyObject_FREE(sym); +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Parser/grammar.c b/AppPkg/Applications/Python/Python-2.7.10/Parser/grammar.c new file mode 100644 index 0000000000..4cce422d1a --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Parser/grammar.c @@ -0,0 +1,254 @@ + +/* Grammar implementation */ + +#include "Python.h" +#include "pgenheaders.h" + +#include + +#include "token.h" +#include "grammar.h" + +#ifdef RISCOS +#include +#endif + +extern int Py_DebugFlag; + +grammar * +newgrammar(int start) +{ + grammar *g; + + g = (grammar *)PyObject_MALLOC(sizeof(grammar)); + if (g == NULL) + Py_FatalError("no mem for new grammar"); + g->g_ndfas = 0; + g->g_dfa = NULL; + g->g_start = start; + g->g_ll.ll_nlabels = 0; + g->g_ll.ll_label = NULL; + g->g_accel = 0; + return g; +} + +dfa * +adddfa(grammar *g, int type, char *name) +{ + dfa *d; + + g->g_dfa = (dfa *)PyObject_REALLOC(g->g_dfa, + sizeof(dfa) * (g->g_ndfas + 1)); + if (g->g_dfa == NULL) + Py_FatalError("no mem to resize dfa in adddfa"); + d = &g->g_dfa[g->g_ndfas++]; + d->d_type = type; + d->d_name = strdup(name); + d->d_nstates = 0; + d->d_state = NULL; + d->d_initial = -1; + d->d_first = NULL; + return d; /* Only use while fresh! */ +} + +int +addstate(dfa *d) +{ + state *s; + + d->d_state = (state *)PyObject_REALLOC(d->d_state, + sizeof(state) * (d->d_nstates + 1)); + if (d->d_state == NULL) + Py_FatalError("no mem to resize state in addstate"); + s = &d->d_state[d->d_nstates++]; + s->s_narcs = 0; + s->s_arc = NULL; + s->s_lower = 0; + s->s_upper = 0; + s->s_accel = NULL; + s->s_accept = 0; + return s - d->d_state; +} + +void +addarc(dfa *d, int from, int to, int lbl) +{ + state *s; + arc *a; + + assert(0 <= from && from < d->d_nstates); + assert(0 <= to && to < d->d_nstates); + + s = &d->d_state[from]; + s->s_arc = (arc *)PyObject_REALLOC(s->s_arc, sizeof(arc) * (s->s_narcs + 1)); + if (s->s_arc == NULL) + Py_FatalError("no mem to resize arc list in addarc"); + a = &s->s_arc[s->s_narcs++]; + a->a_lbl = lbl; + a->a_arrow = to; +} + +int +addlabel(labellist *ll, int type, char *str) +{ + int i; + label *lb; + + for (i = 0; i < ll->ll_nlabels; i++) { + if (ll->ll_label[i].lb_type == type && + strcmp(ll->ll_label[i].lb_str, str) == 0) + return i; + } + ll->ll_label = (label *)PyObject_REALLOC(ll->ll_label, + sizeof(label) * (ll->ll_nlabels + 1)); + if (ll->ll_label == NULL) + Py_FatalError("no mem to resize labellist in addlabel"); + lb = &ll->ll_label[ll->ll_nlabels++]; + lb->lb_type = type; + lb->lb_str = strdup(str); + if (Py_DebugFlag) + printf("Label @ %8p, %d: %s\n", ll, ll->ll_nlabels, + PyGrammar_LabelRepr(lb)); + return lb - ll->ll_label; +} + +/* Same, but rather dies than adds */ + +int +findlabel(labellist *ll, int type, char *str) +{ + int i; + + for (i = 0; i < ll->ll_nlabels; i++) { + if (ll->ll_label[i].lb_type == type /*&& + strcmp(ll->ll_label[i].lb_str, str) == 0*/) + return i; + } + fprintf(stderr, "Label %d/'%s' not found\n", type, str); + Py_FatalError("grammar.c:findlabel()"); + return 0; /* Make gcc -Wall happy */ +} + +/* Forward */ +static void translabel(grammar *, label *); + +void +translatelabels(grammar *g) +{ + int i; + +#ifdef Py_DEBUG + printf("Translating labels ...\n"); +#endif + /* Don't translate EMPTY */ + for (i = EMPTY+1; i < g->g_ll.ll_nlabels; i++) + translabel(g, &g->g_ll.ll_label[i]); +} + +static void +translabel(grammar *g, label *lb) +{ + int i; + + if (Py_DebugFlag) + printf("Translating label %s ...\n", PyGrammar_LabelRepr(lb)); + + if (lb->lb_type == NAME) { + for (i = 0; i < g->g_ndfas; i++) { + if (strcmp(lb->lb_str, g->g_dfa[i].d_name) == 0) { + if (Py_DebugFlag) + printf( + "Label %s is non-terminal %d.\n", + lb->lb_str, + g->g_dfa[i].d_type); + lb->lb_type = g->g_dfa[i].d_type; + free(lb->lb_str); + lb->lb_str = NULL; + return; + } + } + for (i = 0; i < (int)N_TOKENS; i++) { + if (strcmp(lb->lb_str, _PyParser_TokenNames[i]) == 0) { + if (Py_DebugFlag) + printf("Label %s is terminal %d.\n", + lb->lb_str, i); + lb->lb_type = i; + free(lb->lb_str); + lb->lb_str = NULL; + return; + } + } + printf("Can't translate NAME label '%s'\n", lb->lb_str); + return; + } + + if (lb->lb_type == STRING) { + if (isalpha(Py_CHARMASK(lb->lb_str[1])) || + lb->lb_str[1] == '_') { + char *p; + char *src; + char *dest; + size_t name_len; + if (Py_DebugFlag) + printf("Label %s is a keyword\n", lb->lb_str); + lb->lb_type = NAME; + src = lb->lb_str + 1; + p = strchr(src, '\''); + if (p) + name_len = p - src; + else + name_len = strlen(src); + dest = (char *)malloc(name_len + 1); + if (!dest) { + printf("Can't alloc dest '%s'\n", src); + return; + } + strncpy(dest, src, name_len); + dest[name_len] = '\0'; + free(lb->lb_str); + lb->lb_str = dest; + } + else if (lb->lb_str[2] == lb->lb_str[0]) { + int type = (int) PyToken_OneChar(lb->lb_str[1]); + if (type != OP) { + lb->lb_type = type; + free(lb->lb_str); + lb->lb_str = NULL; + } + else + printf("Unknown OP label %s\n", + lb->lb_str); + } + else if (lb->lb_str[2] && lb->lb_str[3] == lb->lb_str[0]) { + int type = (int) PyToken_TwoChars(lb->lb_str[1], + lb->lb_str[2]); + if (type != OP) { + lb->lb_type = type; + free(lb->lb_str); + lb->lb_str = NULL; + } + else + printf("Unknown OP label %s\n", + lb->lb_str); + } + else if (lb->lb_str[2] && lb->lb_str[3] && lb->lb_str[4] == lb->lb_str[0]) { + int type = (int) PyToken_ThreeChars(lb->lb_str[1], + lb->lb_str[2], + lb->lb_str[3]); + if (type != OP) { + lb->lb_type = type; + free(lb->lb_str); + lb->lb_str = NULL; + } + else + printf("Unknown OP label %s\n", + lb->lb_str); + } + else + printf("Can't translate STRING label %s\n", + lb->lb_str); + } + else + printf("Can't translate label '%s'\n", + PyGrammar_LabelRepr(lb)); +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Parser/grammar1.c b/AppPkg/Applications/Python/Python-2.7.10/Parser/grammar1.c new file mode 100644 index 0000000000..27db22f3f9 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Parser/grammar1.c @@ -0,0 +1,57 @@ + +/* Grammar subroutines needed by parser */ + +#include "Python.h" +#include "pgenheaders.h" +#include "grammar.h" +#include "token.h" + +/* Return the DFA for the given type */ + +dfa * +PyGrammar_FindDFA(grammar *g, register int type) +{ + register dfa *d; +#if 1 + /* Massive speed-up */ + d = &g->g_dfa[type - NT_OFFSET]; + assert(d->d_type == type); + return d; +#else + /* Old, slow version */ + register int i; + + for (i = g->g_ndfas, d = g->g_dfa; --i >= 0; d++) { + if (d->d_type == type) + return d; + } + assert(0); + /* NOTREACHED */ +#endif +} + +char * +PyGrammar_LabelRepr(label *lb) +{ + static char buf[100]; + + if (lb->lb_type == ENDMARKER) + return "EMPTY"; + else if (ISNONTERMINAL(lb->lb_type)) { + if (lb->lb_str == NULL) { + PyOS_snprintf(buf, sizeof(buf), "NT%d", lb->lb_type); + return buf; + } + else + return lb->lb_str; + } + else { + if (lb->lb_str == NULL) + return _PyParser_TokenNames[lb->lb_type]; + else { + PyOS_snprintf(buf, sizeof(buf), "%.32s(%.32s)", + _PyParser_TokenNames[lb->lb_type], lb->lb_str); + return buf; + } + } +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Parser/listnode.c b/AppPkg/Applications/Python/Python-2.7.10/Parser/listnode.c new file mode 100644 index 0000000000..8d59233599 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Parser/listnode.c @@ -0,0 +1,66 @@ + +/* List a node on a file */ + +#include "pgenheaders.h" +#include "token.h" +#include "node.h" + +/* Forward */ +static void list1node(FILE *, node *); +static void listnode(FILE *, node *); + +void +PyNode_ListTree(node *n) +{ + listnode(stdout, n); +} + +static int level, atbol; + +static void +listnode(FILE *fp, node *n) +{ + level = 0; + atbol = 1; + list1node(fp, n); +} + +static void +list1node(FILE *fp, node *n) +{ + if (n == 0) + return; + if (ISNONTERMINAL(TYPE(n))) { + int i; + for (i = 0; i < NCH(n); i++) + list1node(fp, CHILD(n, i)); + } + else if (ISTERMINAL(TYPE(n))) { + switch (TYPE(n)) { + case INDENT: + ++level; + break; + case DEDENT: + --level; + break; + default: + if (atbol) { + int i; + for (i = 0; i < level; ++i) + fprintf(fp, "\t"); + atbol = 0; + } + if (TYPE(n) == NEWLINE) { + if (STR(n) != NULL) + fprintf(fp, "%s", STR(n)); + fprintf(fp, "\n"); + atbol = 1; + } + else + fprintf(fp, "%s ", STR(n)); + break; + } + } + else + fprintf(fp, "? "); +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Parser/metagrammar.c b/AppPkg/Applications/Python/Python-2.7.10/Parser/metagrammar.c new file mode 100644 index 0000000000..299ccaa079 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Parser/metagrammar.c @@ -0,0 +1,159 @@ + +#include "pgenheaders.h" +#include "metagrammar.h" +#include "grammar.h" +#include "pgen.h" +static arc arcs_0_0[3] = { + {2, 0}, + {3, 0}, + {4, 1}, +}; +static arc arcs_0_1[1] = { + {0, 1}, +}; +static state states_0[2] = { + {3, arcs_0_0}, + {1, arcs_0_1}, +}; +static arc arcs_1_0[1] = { + {5, 1}, +}; +static arc arcs_1_1[1] = { + {6, 2}, +}; +static arc arcs_1_2[1] = { + {7, 3}, +}; +static arc arcs_1_3[1] = { + {3, 4}, +}; +static arc arcs_1_4[1] = { + {0, 4}, +}; +static state states_1[5] = { + {1, arcs_1_0}, + {1, arcs_1_1}, + {1, arcs_1_2}, + {1, arcs_1_3}, + {1, arcs_1_4}, +}; +static arc arcs_2_0[1] = { + {8, 1}, +}; +static arc arcs_2_1[2] = { + {9, 0}, + {0, 1}, +}; +static state states_2[2] = { + {1, arcs_2_0}, + {2, arcs_2_1}, +}; +static arc arcs_3_0[1] = { + {10, 1}, +}; +static arc arcs_3_1[2] = { + {10, 1}, + {0, 1}, +}; +static state states_3[2] = { + {1, arcs_3_0}, + {2, arcs_3_1}, +}; +static arc arcs_4_0[2] = { + {11, 1}, + {13, 2}, +}; +static arc arcs_4_1[1] = { + {7, 3}, +}; +static arc arcs_4_2[3] = { + {14, 4}, + {15, 4}, + {0, 2}, +}; +static arc arcs_4_3[1] = { + {12, 4}, +}; +static arc arcs_4_4[1] = { + {0, 4}, +}; +static state states_4[5] = { + {2, arcs_4_0}, + {1, arcs_4_1}, + {3, arcs_4_2}, + {1, arcs_4_3}, + {1, arcs_4_4}, +}; +static arc arcs_5_0[3] = { + {5, 1}, + {16, 1}, + {17, 2}, +}; +static arc arcs_5_1[1] = { + {0, 1}, +}; +static arc arcs_5_2[1] = { + {7, 3}, +}; +static arc arcs_5_3[1] = { + {18, 1}, +}; +static state states_5[4] = { + {3, arcs_5_0}, + {1, arcs_5_1}, + {1, arcs_5_2}, + {1, arcs_5_3}, +}; +static dfa dfas[6] = { + {256, "MSTART", 0, 2, states_0, + "\070\000\000"}, + {257, "RULE", 0, 5, states_1, + "\040\000\000"}, + {258, "RHS", 0, 2, states_2, + "\040\010\003"}, + {259, "ALT", 0, 2, states_3, + "\040\010\003"}, + {260, "ITEM", 0, 5, states_4, + "\040\010\003"}, + {261, "ATOM", 0, 4, states_5, + "\040\000\003"}, +}; +static label labels[19] = { + {0, "EMPTY"}, + {256, 0}, + {257, 0}, + {4, 0}, + {0, 0}, + {1, 0}, + {11, 0}, + {258, 0}, + {259, 0}, + {18, 0}, + {260, 0}, + {9, 0}, + {10, 0}, + {261, 0}, + {16, 0}, + {14, 0}, + {3, 0}, + {7, 0}, + {8, 0}, +}; +static grammar _PyParser_Grammar = { + 6, + dfas, + {19, labels}, + 256 +}; + +grammar * +meta_grammar(void) +{ + return &_PyParser_Grammar; +} + +grammar * +Py_meta_grammar(void) +{ + return meta_grammar(); +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Parser/myreadline.c b/AppPkg/Applications/Python/Python-2.7.10/Parser/myreadline.c new file mode 100644 index 0000000000..ca99e35ced --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Parser/myreadline.c @@ -0,0 +1,218 @@ + +/* Readline interface for tokenizer.c and [raw_]input() in bltinmodule.c. + By default, or when stdin is not a tty device, we have a super + simple my_readline function using fgets. + Optionally, we can use the GNU readline library. + my_readline() has a different return value from GNU readline(): + - NULL if an interrupt occurred or if an error occurred + - a malloc'ed empty string if EOF was read + - a malloc'ed string ending in \n normally +*/ + +#include "Python.h" +#ifdef MS_WINDOWS +#define WIN32_LEAN_AND_MEAN +#include "windows.h" +#endif /* MS_WINDOWS */ + +#ifdef __VMS +extern char* vms__StdioReadline(FILE *sys_stdin, FILE *sys_stdout, char *prompt); +#endif + + +PyThreadState* _PyOS_ReadlineTState; + +#ifdef WITH_THREAD +#include "pythread.h" +static PyThread_type_lock _PyOS_ReadlineLock = NULL; +#endif + +int (*PyOS_InputHook)(void) = NULL; + +#ifdef RISCOS +int Py_RISCOSWimpFlag; +#endif + +/* This function restarts a fgets() after an EINTR error occurred + except if PyOS_InterruptOccurred() returns true. */ + +static int +my_fgets(char *buf, int len, FILE *fp) +{ + char *p; +#ifdef MS_WINDOWS + int i; +#endif + + while (1) { + if (PyOS_InputHook != NULL) + (void)(PyOS_InputHook)(); + errno = 0; + clearerr(fp); + p = fgets(buf, len, fp); + if (p != NULL) + return 0; /* No error */ +#ifdef MS_WINDOWS + /* Ctrl-C anywhere on the line or Ctrl-Z if the only character + on a line will set ERROR_OPERATION_ABORTED. Under normal + circumstances Ctrl-C will also have caused the SIGINT handler + to fire. This signal fires in another thread and is not + guaranteed to have occurred before this point in the code. + + Therefore: check in a small loop to see if the trigger has + fired, in which case assume this is a Ctrl-C event. If it + hasn't fired within 10ms assume that this is a Ctrl-Z on its + own or that the signal isn't going to fire for some other + reason and drop through to check for EOF. + */ + if (GetLastError()==ERROR_OPERATION_ABORTED) { + for (i = 0; i < 10; i++) { + if (PyOS_InterruptOccurred()) + return 1; + Sleep(1); + } + } +#endif /* MS_WINDOWS */ + if (feof(fp)) { + clearerr(fp); + return -1; /* EOF */ + } +#ifdef EINTR + if (errno == EINTR) { + int s; +#ifdef WITH_THREAD + PyEval_RestoreThread(_PyOS_ReadlineTState); +#endif + s = PyErr_CheckSignals(); +#ifdef WITH_THREAD + PyEval_SaveThread(); +#endif + if (s < 0) + return 1; + /* try again */ + continue; + } +#endif + if (PyOS_InterruptOccurred()) { + return 1; /* Interrupt */ + } + return -2; /* Error */ + } + /* NOTREACHED */ +} + + +/* Readline implementation using fgets() */ + +char * +PyOS_StdioReadline(FILE *sys_stdin, FILE *sys_stdout, char *prompt) +{ + size_t n; + char *p; + n = 100; + if ((p = (char *)PyMem_MALLOC(n)) == NULL) + return NULL; + fflush(sys_stdout); +#ifndef RISCOS + if (prompt) + fprintf(stderr, "%s", prompt); +#else + if (prompt) { + if(Py_RISCOSWimpFlag) + fprintf(stderr, "\x0cr%s\x0c", prompt); + else + fprintf(stderr, "%s", prompt); + } +#endif + fflush(stderr); + switch (my_fgets(p, (int)n, sys_stdin)) { + case 0: /* Normal case */ + break; + case 1: /* Interrupt */ + PyMem_FREE(p); + return NULL; + case -1: /* EOF */ + case -2: /* Error */ + default: /* Shouldn't happen */ + *p = '\0'; + break; + } + n = strlen(p); + while (n > 0 && p[n-1] != '\n') { + size_t incr = n+2; + p = (char *)PyMem_REALLOC(p, n + incr); + if (p == NULL) + return NULL; + if (incr > INT_MAX) { + PyErr_SetString(PyExc_OverflowError, "input line too long"); + } + if (my_fgets(p+n, (int)incr, sys_stdin) != 0) + break; + n += strlen(p+n); + } + return (char *)PyMem_REALLOC(p, n+1); +} + + +/* By initializing this function pointer, systems embedding Python can + override the readline function. + + Note: Python expects in return a buffer allocated with PyMem_Malloc. */ + +char *(*PyOS_ReadlineFunctionPointer)(FILE *, FILE *, char *); + + +/* Interface used by tokenizer.c and bltinmodule.c */ + +char * +PyOS_Readline(FILE *sys_stdin, FILE *sys_stdout, char *prompt) +{ + char *rv; + + if (_PyOS_ReadlineTState == PyThreadState_GET()) { + PyErr_SetString(PyExc_RuntimeError, + "can't re-enter readline"); + return NULL; + } + + + if (PyOS_ReadlineFunctionPointer == NULL) { +#ifdef __VMS + PyOS_ReadlineFunctionPointer = vms__StdioReadline; +#else + PyOS_ReadlineFunctionPointer = PyOS_StdioReadline; +#endif + } + +#ifdef WITH_THREAD + if (_PyOS_ReadlineLock == NULL) { + _PyOS_ReadlineLock = PyThread_allocate_lock(); + } +#endif + + _PyOS_ReadlineTState = PyThreadState_GET(); + Py_BEGIN_ALLOW_THREADS +#ifdef WITH_THREAD + PyThread_acquire_lock(_PyOS_ReadlineLock, 1); +#endif + + /* This is needed to handle the unlikely case that the + * interpreter is in interactive mode *and* stdin/out are not + * a tty. This can happen, for example if python is run like + * this: python -i < test1.py + */ + if (!isatty (fileno (sys_stdin)) || !isatty (fileno (sys_stdout))) + rv = PyOS_StdioReadline (sys_stdin, sys_stdout, prompt); + else + rv = (*PyOS_ReadlineFunctionPointer)(sys_stdin, sys_stdout, + prompt); + Py_END_ALLOW_THREADS + +#ifdef WITH_THREAD + PyThread_release_lock(_PyOS_ReadlineLock); +#endif + + _PyOS_ReadlineTState = NULL; + + return rv; +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Parser/node.c b/AppPkg/Applications/Python/Python-2.7.10/Parser/node.c new file mode 100644 index 0000000000..4f1fbf8f23 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Parser/node.c @@ -0,0 +1,164 @@ +/* Parse tree node implementation */ + +#include "Python.h" +#include "node.h" +#include "errcode.h" + +node * +PyNode_New(int type) +{ + node *n = (node *) PyObject_MALLOC(1 * sizeof(node)); + if (n == NULL) + return NULL; + n->n_type = type; + n->n_str = NULL; + n->n_lineno = 0; + n->n_nchildren = 0; + n->n_child = NULL; + return n; +} + +/* See comments at XXXROUNDUP below. Returns -1 on overflow. */ +static int +fancy_roundup(int n) +{ + /* Round up to the closest power of 2 >= n. */ + int result = 256; + assert(n > 128); + while (result < n) { + result <<= 1; + if (result <= 0) + return -1; + } + return result; +} + +/* A gimmick to make massive numbers of reallocs quicker. The result is + * a number >= the input. In PyNode_AddChild, it's used like so, when + * we're about to add child number current_size + 1: + * + * if XXXROUNDUP(current_size) < XXXROUNDUP(current_size + 1): + * allocate space for XXXROUNDUP(current_size + 1) total children + * else: + * we already have enough space + * + * Since a node starts out empty, we must have + * + * XXXROUNDUP(0) < XXXROUNDUP(1) + * + * so that we allocate space for the first child. One-child nodes are very + * common (presumably that would change if we used a more abstract form + * of syntax tree), so to avoid wasting memory it's desirable that + * XXXROUNDUP(1) == 1. That in turn forces XXXROUNDUP(0) == 0. + * + * Else for 2 <= n <= 128, we round up to the closest multiple of 4. Why 4? + * Rounding up to a multiple of an exact power of 2 is very efficient, and + * most nodes with more than one child have <= 4 kids. + * + * Else we call fancy_roundup() to grow proportionately to n. We've got an + * extreme case then (like test_longexp.py), and on many platforms doing + * anything less than proportional growth leads to exorbitant runtime + * (e.g., MacPython), or extreme fragmentation of user address space (e.g., + * Win98). + * + * In a run of compileall across the 2.3a0 Lib directory, Andrew MacIntyre + * reported that, with this scheme, 89% of PyObject_REALLOC calls in + * PyNode_AddChild passed 1 for the size, and 9% passed 4. So this usually + * wastes very little memory, but is very effective at sidestepping + * platform-realloc disasters on vulnerable platforms. + * + * Note that this would be straightforward if a node stored its current + * capacity. The code is tricky to avoid that. + */ +#define XXXROUNDUP(n) ((n) <= 1 ? (n) : \ + (n) <= 128 ? (((n) + 3) & ~3) : \ + fancy_roundup(n)) + + +int +PyNode_AddChild(register node *n1, int type, char *str, int lineno, int col_offset) +{ + const int nch = n1->n_nchildren; + int current_capacity; + int required_capacity; + node *n; + + if (nch == INT_MAX || nch < 0) + return E_OVERFLOW; + + current_capacity = XXXROUNDUP(nch); + required_capacity = XXXROUNDUP(nch + 1); + if (current_capacity < 0 || required_capacity < 0) + return E_OVERFLOW; + if (current_capacity < required_capacity) { + if (required_capacity > PY_SIZE_MAX / sizeof(node)) { + return E_NOMEM; + } + n = n1->n_child; + n = (node *) PyObject_REALLOC(n, + required_capacity * sizeof(node)); + if (n == NULL) + return E_NOMEM; + n1->n_child = n; + } + + n = &n1->n_child[n1->n_nchildren++]; + n->n_type = type; + n->n_str = str; + n->n_lineno = lineno; + n->n_col_offset = col_offset; + n->n_nchildren = 0; + n->n_child = NULL; + return 0; +} + +/* Forward */ +static void freechildren(node *); +static Py_ssize_t sizeofchildren(node *n); + + +void +PyNode_Free(node *n) +{ + if (n != NULL) { + freechildren(n); + PyObject_FREE(n); + } +} + +Py_ssize_t +_PyNode_SizeOf(node *n) +{ + Py_ssize_t res = 0; + + if (n != NULL) + res = sizeof(node) + sizeofchildren(n); + return res; +} + +static void +freechildren(node *n) +{ + int i; + for (i = NCH(n); --i >= 0; ) + freechildren(CHILD(n, i)); + if (n->n_child != NULL) + PyObject_FREE(n->n_child); + if (STR(n) != NULL) + PyObject_FREE(STR(n)); +} + +static Py_ssize_t +sizeofchildren(node *n) +{ + Py_ssize_t res = 0; + int i; + for (i = NCH(n); --i >= 0; ) + res += sizeofchildren(CHILD(n, i)); + if (n->n_child != NULL) + /* allocated size of n->n_child array */ + res += XXXROUNDUP(NCH(n)) * sizeof(node); + if (STR(n) != NULL) + res += strlen(STR(n)) + 1; + return res; +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Parser/parser.c b/AppPkg/Applications/Python/Python-2.7.10/Parser/parser.c new file mode 100644 index 0000000000..d98dfaaca5 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Parser/parser.c @@ -0,0 +1,436 @@ + +/* Parser implementation */ + +/* For a description, see the comments at end of this file */ + +/* XXX To do: error recovery */ + +#include "Python.h" +#include "pgenheaders.h" +#include "token.h" +#include "grammar.h" +#include "node.h" +#include "parser.h" +#include "errcode.h" + + +#ifdef Py_DEBUG +extern int Py_DebugFlag; +#define D(x) if (!Py_DebugFlag); else x +#else +#define D(x) +#endif + + +/* STACK DATA TYPE */ + +static void s_reset(stack *); + +static void +s_reset(stack *s) +{ + s->s_top = &s->s_base[MAXSTACK]; +} + +#define s_empty(s) ((s)->s_top == &(s)->s_base[MAXSTACK]) + +static int +s_push(register stack *s, dfa *d, node *parent) +{ + register stackentry *top; + if (s->s_top == s->s_base) { + fprintf(stderr, "s_push: parser stack overflow\n"); + return E_NOMEM; + } + top = --s->s_top; + top->s_dfa = d; + top->s_parent = parent; + top->s_state = 0; + return 0; +} + +#ifdef Py_DEBUG + +static void +s_pop(register stack *s) +{ + if (s_empty(s)) + Py_FatalError("s_pop: parser stack underflow -- FATAL"); + s->s_top++; +} + +#else /* !Py_DEBUG */ + +#define s_pop(s) (s)->s_top++ + +#endif + + +/* PARSER CREATION */ + +parser_state * +PyParser_New(grammar *g, int start) +{ + parser_state *ps; + + if (!g->g_accel) + PyGrammar_AddAccelerators(g); + ps = (parser_state *)PyMem_MALLOC(sizeof(parser_state)); + if (ps == NULL) + return NULL; + ps->p_grammar = g; +#ifdef PY_PARSER_REQUIRES_FUTURE_KEYWORD + ps->p_flags = 0; +#endif + ps->p_tree = PyNode_New(start); + if (ps->p_tree == NULL) { + PyMem_FREE(ps); + return NULL; + } + s_reset(&ps->p_stack); + (void) s_push(&ps->p_stack, PyGrammar_FindDFA(g, start), ps->p_tree); + return ps; +} + +void +PyParser_Delete(parser_state *ps) +{ + /* NB If you want to save the parse tree, + you must set p_tree to NULL before calling delparser! */ + PyNode_Free(ps->p_tree); + PyMem_FREE(ps); +} + + +/* PARSER STACK OPERATIONS */ + +static int +shift(register stack *s, int type, char *str, int newstate, int lineno, int col_offset) +{ + int err; + assert(!s_empty(s)); + err = PyNode_AddChild(s->s_top->s_parent, type, str, lineno, col_offset); + if (err) + return err; + s->s_top->s_state = newstate; + return 0; +} + +static int +push(register stack *s, int type, dfa *d, int newstate, int lineno, int col_offset) +{ + int err; + register node *n; + n = s->s_top->s_parent; + assert(!s_empty(s)); + err = PyNode_AddChild(n, type, (char *)NULL, lineno, col_offset); + if (err) + return err; + s->s_top->s_state = newstate; + return s_push(s, d, CHILD(n, NCH(n)-1)); +} + + +/* PARSER PROPER */ + +static int +classify(parser_state *ps, int type, char *str) +{ + grammar *g = ps->p_grammar; + register int n = g->g_ll.ll_nlabels; + + if (type == NAME) { + register char *s = str; + register label *l = g->g_ll.ll_label; + register int i; + for (i = n; i > 0; i--, l++) { + if (l->lb_type != NAME || l->lb_str == NULL || + l->lb_str[0] != s[0] || + strcmp(l->lb_str, s) != 0) + continue; +#ifdef PY_PARSER_REQUIRES_FUTURE_KEYWORD + if (ps->p_flags & CO_FUTURE_PRINT_FUNCTION && + s[0] == 'p' && strcmp(s, "print") == 0) { + break; /* no longer a keyword */ + } +#endif + D(printf("It's a keyword\n")); + return n - i; + } + } + + { + register label *l = g->g_ll.ll_label; + register int i; + for (i = n; i > 0; i--, l++) { + if (l->lb_type == type && l->lb_str == NULL) { + D(printf("It's a token we know\n")); + return n - i; + } + } + } + + D(printf("Illegal token\n")); + return -1; +} + +#ifdef PY_PARSER_REQUIRES_FUTURE_KEYWORD +static void +future_hack(parser_state *ps) +{ + node *n = ps->p_stack.s_top->s_parent; + node *ch, *cch; + int i; + + /* from __future__ import ..., must have at least 4 children */ + n = CHILD(n, 0); + if (NCH(n) < 4) + return; + ch = CHILD(n, 0); + if (STR(ch) == NULL || strcmp(STR(ch), "from") != 0) + return; + ch = CHILD(n, 1); + if (NCH(ch) == 1 && STR(CHILD(ch, 0)) && + strcmp(STR(CHILD(ch, 0)), "__future__") != 0) + return; + ch = CHILD(n, 3); + /* ch can be a star, a parenthesis or import_as_names */ + if (TYPE(ch) == STAR) + return; + if (TYPE(ch) == LPAR) + ch = CHILD(n, 4); + + for (i = 0; i < NCH(ch); i += 2) { + cch = CHILD(ch, i); + if (NCH(cch) >= 1 && TYPE(CHILD(cch, 0)) == NAME) { + char *str_ch = STR(CHILD(cch, 0)); + if (strcmp(str_ch, FUTURE_WITH_STATEMENT) == 0) { + ps->p_flags |= CO_FUTURE_WITH_STATEMENT; + } else if (strcmp(str_ch, FUTURE_PRINT_FUNCTION) == 0) { + ps->p_flags |= CO_FUTURE_PRINT_FUNCTION; + } else if (strcmp(str_ch, FUTURE_UNICODE_LITERALS) == 0) { + ps->p_flags |= CO_FUTURE_UNICODE_LITERALS; + } + } + } +} +#endif /* future keyword */ + +int +PyParser_AddToken(register parser_state *ps, register int type, char *str, + int lineno, int col_offset, int *expected_ret) +{ + register int ilabel; + int err; + + D(printf("Token %s/'%s' ... ", _PyParser_TokenNames[type], str)); + + /* Find out which label this token is */ + ilabel = classify(ps, type, str); + if (ilabel < 0) + return E_SYNTAX; + + /* Loop until the token is shifted or an error occurred */ + for (;;) { + /* Fetch the current dfa and state */ + register dfa *d = ps->p_stack.s_top->s_dfa; + register state *s = &d->d_state[ps->p_stack.s_top->s_state]; + + D(printf(" DFA '%s', state %d:", + d->d_name, ps->p_stack.s_top->s_state)); + + /* Check accelerator */ + if (s->s_lower <= ilabel && ilabel < s->s_upper) { + register int x = s->s_accel[ilabel - s->s_lower]; + if (x != -1) { + if (x & (1<<7)) { + /* Push non-terminal */ + int nt = (x >> 8) + NT_OFFSET; + int arrow = x & ((1<<7)-1); + dfa *d1 = PyGrammar_FindDFA( + ps->p_grammar, nt); + if ((err = push(&ps->p_stack, nt, d1, + arrow, lineno, col_offset)) > 0) { + D(printf(" MemError: push\n")); + return err; + } + D(printf(" Push ...\n")); + continue; + } + + /* Shift the token */ + if ((err = shift(&ps->p_stack, type, str, + x, lineno, col_offset)) > 0) { + D(printf(" MemError: shift.\n")); + return err; + } + D(printf(" Shift.\n")); + /* Pop while we are in an accept-only state */ + while (s = &d->d_state + [ps->p_stack.s_top->s_state], + s->s_accept && s->s_narcs == 1) { + D(printf(" DFA '%s', state %d: " + "Direct pop.\n", + d->d_name, + ps->p_stack.s_top->s_state)); +#ifdef PY_PARSER_REQUIRES_FUTURE_KEYWORD + if (d->d_name[0] == 'i' && + strcmp(d->d_name, + "import_stmt") == 0) + future_hack(ps); +#endif + s_pop(&ps->p_stack); + if (s_empty(&ps->p_stack)) { + D(printf(" ACCEPT.\n")); + return E_DONE; + } + d = ps->p_stack.s_top->s_dfa; + } + return E_OK; + } + } + + if (s->s_accept) { +#ifdef PY_PARSER_REQUIRES_FUTURE_KEYWORD + if (d->d_name[0] == 'i' && + strcmp(d->d_name, "import_stmt") == 0) + future_hack(ps); +#endif + /* Pop this dfa and try again */ + s_pop(&ps->p_stack); + D(printf(" Pop ...\n")); + if (s_empty(&ps->p_stack)) { + D(printf(" Error: bottom of stack.\n")); + return E_SYNTAX; + } + continue; + } + + /* Stuck, report syntax error */ + D(printf(" Error.\n")); + if (expected_ret) { + if (s->s_lower == s->s_upper - 1) { + /* Only one possible expected token */ + *expected_ret = ps->p_grammar-> + g_ll.ll_label[s->s_lower].lb_type; + } + else + *expected_ret = -1; + } + return E_SYNTAX; + } +} + + +#ifdef Py_DEBUG + +/* DEBUG OUTPUT */ + +void +dumptree(grammar *g, node *n) +{ + int i; + + if (n == NULL) + printf("NIL"); + else { + label l; + l.lb_type = TYPE(n); + l.lb_str = STR(n); + printf("%s", PyGrammar_LabelRepr(&l)); + if (ISNONTERMINAL(TYPE(n))) { + printf("("); + for (i = 0; i < NCH(n); i++) { + if (i > 0) + printf(","); + dumptree(g, CHILD(n, i)); + } + printf(")"); + } + } +} + +void +showtree(grammar *g, node *n) +{ + int i; + + if (n == NULL) + return; + if (ISNONTERMINAL(TYPE(n))) { + for (i = 0; i < NCH(n); i++) + showtree(g, CHILD(n, i)); + } + else if (ISTERMINAL(TYPE(n))) { + printf("%s", _PyParser_TokenNames[TYPE(n)]); + if (TYPE(n) == NUMBER || TYPE(n) == NAME) + printf("(%s)", STR(n)); + printf(" "); + } + else + printf("? "); +} + +void +printtree(parser_state *ps) +{ + if (Py_DebugFlag) { + printf("Parse tree:\n"); + dumptree(ps->p_grammar, ps->p_tree); + printf("\n"); + printf("Tokens:\n"); + showtree(ps->p_grammar, ps->p_tree); + printf("\n"); + } + printf("Listing:\n"); + PyNode_ListTree(ps->p_tree); + printf("\n"); +} + +#endif /* Py_DEBUG */ + +/* + +Description +----------- + +The parser's interface is different than usual: the function addtoken() +must be called for each token in the input. This makes it possible to +turn it into an incremental parsing system later. The parsing system +constructs a parse tree as it goes. + +A parsing rule is represented as a Deterministic Finite-state Automaton +(DFA). A node in a DFA represents a state of the parser; an arc represents +a transition. Transitions are either labeled with terminal symbols or +with non-terminals. When the parser decides to follow an arc labeled +with a non-terminal, it is invoked recursively with the DFA representing +the parsing rule for that as its initial state; when that DFA accepts, +the parser that invoked it continues. The parse tree constructed by the +recursively called parser is inserted as a child in the current parse tree. + +The DFA's can be constructed automatically from a more conventional +language description. An extended LL(1) grammar (ELL(1)) is suitable. +Certain restrictions make the parser's life easier: rules that can produce +the empty string should be outlawed (there are other ways to put loops +or optional parts in the language). To avoid the need to construct +FIRST sets, we can require that all but the last alternative of a rule +(really: arc going out of a DFA's state) must begin with a terminal +symbol. + +As an example, consider this grammar: + +expr: term (OP term)* +term: CONSTANT | '(' expr ')' + +The DFA corresponding to the rule for expr is: + +------->.---term-->.-------> + ^ | + | | + \----OP----/ + +The parse tree generated for the input a+b is: + +(expr: (term: (NAME: a)), (OP: +), (term: (NAME: b))) + +*/ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Parser/parser.h b/AppPkg/Applications/Python/Python-2.7.10/Parser/parser.h new file mode 100644 index 0000000000..bc09396769 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Parser/parser.h @@ -0,0 +1,42 @@ +#ifndef Py_PARSER_H +#define Py_PARSER_H +#ifdef __cplusplus +extern "C" { +#endif + + +/* Parser interface */ + +#define MAXSTACK 1500 + +typedef struct { + int s_state; /* State in current DFA */ + dfa *s_dfa; /* Current DFA */ + struct _node *s_parent; /* Where to add next node */ +} stackentry; + +typedef struct { + stackentry *s_top; /* Top entry */ + stackentry s_base[MAXSTACK];/* Array of stack entries */ + /* NB The stack grows down */ +} stack; + +typedef struct { + stack p_stack; /* Stack of parser states */ + grammar *p_grammar; /* Grammar to use */ + node *p_tree; /* Top of parse tree */ +#ifdef PY_PARSER_REQUIRES_FUTURE_KEYWORD + unsigned long p_flags; /* see co_flags in Include/code.h */ +#endif +} parser_state; + +parser_state *PyParser_New(grammar *g, int start); +void PyParser_Delete(parser_state *ps); +int PyParser_AddToken(parser_state *ps, int type, char *str, int lineno, int col_offset, + int *expected_ret); +void PyGrammar_AddAccelerators(grammar *g); + +#ifdef __cplusplus +} +#endif +#endif /* !Py_PARSER_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Parser/parsetok.c b/AppPkg/Applications/Python/Python-2.7.10/Parser/parsetok.c new file mode 100644 index 0000000000..ac1eeb6776 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Parser/parsetok.c @@ -0,0 +1,282 @@ + +/* Parser-tokenizer link implementation */ + +#include "pgenheaders.h" +#include "tokenizer.h" +#include "node.h" +#include "grammar.h" +#include "parser.h" +#include "parsetok.h" +#include "errcode.h" +#include "graminit.h" + +int Py_TabcheckFlag; + + +/* Forward */ +static node *parsetok(struct tok_state *, grammar *, int, perrdetail *, int *); +static void initerr(perrdetail *err_ret, const char* filename); + +/* Parse input coming from a string. Return error code, print some errors. */ +node * +PyParser_ParseString(const char *s, grammar *g, int start, perrdetail *err_ret) +{ + return PyParser_ParseStringFlagsFilename(s, NULL, g, start, err_ret, 0); +} + +node * +PyParser_ParseStringFlags(const char *s, grammar *g, int start, + perrdetail *err_ret, int flags) +{ + return PyParser_ParseStringFlagsFilename(s, NULL, + g, start, err_ret, flags); +} + +node * +PyParser_ParseStringFlagsFilename(const char *s, const char *filename, + grammar *g, int start, + perrdetail *err_ret, int flags) +{ + int iflags = flags; + return PyParser_ParseStringFlagsFilenameEx(s, filename, g, start, + err_ret, &iflags); +} + +node * +PyParser_ParseStringFlagsFilenameEx(const char *s, const char *filename, + grammar *g, int start, + perrdetail *err_ret, int *flags) +{ + struct tok_state *tok; + + initerr(err_ret, filename); + + if ((tok = PyTokenizer_FromString(s, start == file_input)) == NULL) { + err_ret->error = PyErr_Occurred() ? E_DECODE : E_NOMEM; + return NULL; + } + + tok->filename = filename ? filename : ""; + if (Py_TabcheckFlag || Py_VerboseFlag) { + tok->altwarning = (tok->filename != NULL); + if (Py_TabcheckFlag >= 2) + tok->alterror++; + } + + return parsetok(tok, g, start, err_ret, flags); +} + +/* Parse input coming from a file. Return error code, print some errors. */ + +node * +PyParser_ParseFile(FILE *fp, const char *filename, grammar *g, int start, + char *ps1, char *ps2, perrdetail *err_ret) +{ + return PyParser_ParseFileFlags(fp, filename, g, start, ps1, ps2, + err_ret, 0); +} + +node * +PyParser_ParseFileFlags(FILE *fp, const char *filename, grammar *g, int start, + char *ps1, char *ps2, perrdetail *err_ret, int flags) +{ + int iflags = flags; + return PyParser_ParseFileFlagsEx(fp, filename, g, start, ps1, ps2, err_ret, &iflags); +} + +node * +PyParser_ParseFileFlagsEx(FILE *fp, const char *filename, grammar *g, int start, + char *ps1, char *ps2, perrdetail *err_ret, int *flags) +{ + struct tok_state *tok; + + initerr(err_ret, filename); + + if ((tok = PyTokenizer_FromFile(fp, ps1, ps2)) == NULL) { + err_ret->error = E_NOMEM; + return NULL; + } + tok->filename = filename; + if (Py_TabcheckFlag || Py_VerboseFlag) { + tok->altwarning = (filename != NULL); + if (Py_TabcheckFlag >= 2) + tok->alterror++; + } + + return parsetok(tok, g, start, err_ret, flags); +} + +#if 0 +static char with_msg[] = +"%s:%d: Warning: 'with' will become a reserved keyword in Python 2.6\n"; + +static char as_msg[] = +"%s:%d: Warning: 'as' will become a reserved keyword in Python 2.6\n"; + +static void +warn(const char *msg, const char *filename, int lineno) +{ + if (filename == NULL) + filename = ""; + PySys_WriteStderr(msg, filename, lineno); +} +#endif + +/* Parse input coming from the given tokenizer structure. + Return error code. */ + +static node * +parsetok(struct tok_state *tok, grammar *g, int start, perrdetail *err_ret, + int *flags) +{ + parser_state *ps; + node *n; + int started = 0; + + if ((ps = PyParser_New(g, start)) == NULL) { + fprintf(stderr, "no mem for new parser\n"); + err_ret->error = E_NOMEM; + PyTokenizer_Free(tok); + return NULL; + } +#ifdef PY_PARSER_REQUIRES_FUTURE_KEYWORD + if (*flags & PyPARSE_PRINT_IS_FUNCTION) { + ps->p_flags |= CO_FUTURE_PRINT_FUNCTION; + } + if (*flags & PyPARSE_UNICODE_LITERALS) { + ps->p_flags |= CO_FUTURE_UNICODE_LITERALS; + } + +#endif + + for (;;) { + char *a, *b; + int type; + size_t len; + char *str; + int col_offset; + + type = PyTokenizer_Get(tok, &a, &b); + if (type == ERRORTOKEN) { + err_ret->error = tok->done; + break; + } + if (type == ENDMARKER && started) { + type = NEWLINE; /* Add an extra newline */ + started = 0; + /* Add the right number of dedent tokens, + except if a certain flag is given -- + codeop.py uses this. */ + if (tok->indent && + !(*flags & PyPARSE_DONT_IMPLY_DEDENT)) + { + tok->pendin = -tok->indent; + tok->indent = 0; + } + } + else + started = 1; + len = b - a; /* XXX this may compute NULL - NULL */ + str = (char *) PyObject_MALLOC(len + 1); + if (str == NULL) { + fprintf(stderr, "no mem for next token\n"); + err_ret->error = E_NOMEM; + break; + } + if (len > 0) + strncpy(str, a, len); + str[len] = '\0'; + +#ifdef PY_PARSER_REQUIRES_FUTURE_KEYWORD +#endif + if (a >= tok->line_start) + col_offset = a - tok->line_start; + else + col_offset = -1; + + if ((err_ret->error = + PyParser_AddToken(ps, (int)type, str, tok->lineno, col_offset, + &(err_ret->expected))) != E_OK) { + if (err_ret->error != E_DONE) { + PyObject_FREE(str); + err_ret->token = type; + } + break; + } + } + + if (err_ret->error == E_DONE) { + n = ps->p_tree; + ps->p_tree = NULL; + } + else + n = NULL; + +#ifdef PY_PARSER_REQUIRES_FUTURE_KEYWORD + *flags = ps->p_flags; +#endif + PyParser_Delete(ps); + + if (n == NULL) { + if (tok->lineno <= 1 && tok->done == E_EOF) + err_ret->error = E_EOF; + err_ret->lineno = tok->lineno; + if (tok->buf != NULL) { + char *text = NULL; + size_t len; + assert(tok->cur - tok->buf < INT_MAX); + err_ret->offset = (int)(tok->cur - tok->buf); + len = tok->inp - tok->buf; +#ifdef Py_USING_UNICODE + text = PyTokenizer_RestoreEncoding(tok, len, &err_ret->offset); + +#endif + if (text == NULL) { + text = (char *) PyObject_MALLOC(len + 1); + if (text != NULL) { + if (len > 0) + strncpy(text, tok->buf, len); + text[len] = '\0'; + } + } + err_ret->text = text; + } + } else if (tok->encoding != NULL) { + /* 'nodes->n_str' uses PyObject_*, while 'tok->encoding' was + * allocated using PyMem_ + */ + node* r = PyNode_New(encoding_decl); + if (r) + r->n_str = PyObject_MALLOC(strlen(tok->encoding)+1); + if (!r || !r->n_str) { + err_ret->error = E_NOMEM; + if (r) + PyObject_FREE(r); + n = NULL; + goto done; + } + strcpy(r->n_str, tok->encoding); + PyMem_FREE(tok->encoding); + tok->encoding = NULL; + r->n_nchildren = 1; + r->n_child = n; + n = r; + } + +done: + PyTokenizer_Free(tok); + + return n; +} + +static void +initerr(perrdetail *err_ret, const char *filename) +{ + err_ret->error = E_OK; + err_ret->filename = filename; + err_ret->lineno = 0; + err_ret->offset = 0; + err_ret->text = NULL; + err_ret->token = -1; + err_ret->expected = -1; +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Parser/tokenizer.c b/AppPkg/Applications/Python/Python-2.7.10/Parser/tokenizer.c new file mode 100644 index 0000000000..086dc56741 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Parser/tokenizer.c @@ -0,0 +1,1755 @@ + +/* Tokenizer implementation */ + +#include "Python.h" +#include "pgenheaders.h" + +#include +#include + +#include "tokenizer.h" +#include "errcode.h" + +#ifndef PGEN +#include "unicodeobject.h" +#include "stringobject.h" +#include "fileobject.h" +#include "codecs.h" +#include "abstract.h" +#include "pydebug.h" +#endif /* PGEN */ + +extern char *PyOS_Readline(FILE *, FILE *, char *); +/* Return malloc'ed string including trailing \n; + empty malloc'ed string for EOF; + NULL if interrupted */ + +/* Don't ever change this -- it would break the portability of Python code */ +#define TABSIZE 8 + +/* Forward */ +static struct tok_state *tok_new(void); +static int tok_nextc(struct tok_state *tok); +static void tok_backup(struct tok_state *tok, int c); + +/* Token names */ + +char *_PyParser_TokenNames[] = { + "ENDMARKER", + "NAME", + "NUMBER", + "STRING", + "NEWLINE", + "INDENT", + "DEDENT", + "LPAR", + "RPAR", + "LSQB", + "RSQB", + "COLON", + "COMMA", + "SEMI", + "PLUS", + "MINUS", + "STAR", + "SLASH", + "VBAR", + "AMPER", + "LESS", + "GREATER", + "EQUAL", + "DOT", + "PERCENT", + "BACKQUOTE", + "LBRACE", + "RBRACE", + "EQEQUAL", + "NOTEQUAL", + "LESSEQUAL", + "GREATEREQUAL", + "TILDE", + "CIRCUMFLEX", + "LEFTSHIFT", + "RIGHTSHIFT", + "DOUBLESTAR", + "PLUSEQUAL", + "MINEQUAL", + "STAREQUAL", + "SLASHEQUAL", + "PERCENTEQUAL", + "AMPEREQUAL", + "VBAREQUAL", + "CIRCUMFLEXEQUAL", + "LEFTSHIFTEQUAL", + "RIGHTSHIFTEQUAL", + "DOUBLESTAREQUAL", + "DOUBLESLASH", + "DOUBLESLASHEQUAL", + "AT", + /* This table must match the #defines in token.h! */ + "OP", + "", + "" +}; + +/* Create and initialize a new tok_state structure */ + +static struct tok_state * +tok_new(void) +{ + struct tok_state *tok = (struct tok_state *)PyMem_MALLOC( + sizeof(struct tok_state)); + if (tok == NULL) + return NULL; + tok->buf = tok->cur = tok->end = tok->inp = tok->start = NULL; + tok->done = E_OK; + tok->fp = NULL; + tok->input = NULL; + tok->tabsize = TABSIZE; + tok->indent = 0; + tok->indstack[0] = 0; + tok->atbol = 1; + tok->pendin = 0; + tok->prompt = tok->nextprompt = NULL; + tok->lineno = 0; + tok->level = 0; + tok->filename = NULL; + tok->altwarning = 0; + tok->alterror = 0; + tok->alttabsize = 1; + tok->altindstack[0] = 0; + tok->decoding_state = 0; + tok->decoding_erred = 0; + tok->read_coding_spec = 0; + tok->encoding = NULL; + tok->cont_line = 0; +#ifndef PGEN + tok->decoding_readline = NULL; + tok->decoding_buffer = NULL; +#endif + return tok; +} + +static char * +new_string(const char *s, Py_ssize_t len) +{ + char* result = (char *)PyMem_MALLOC(len + 1); + if (result != NULL) { + memcpy(result, s, len); + result[len] = '\0'; + } + return result; +} + +#ifdef PGEN + +static char * +decoding_fgets(char *s, int size, struct tok_state *tok) +{ + return fgets(s, size, tok->fp); +} + +static int +decoding_feof(struct tok_state *tok) +{ + return feof(tok->fp); +} + +static char * +decode_str(const char *str, int exec_input, struct tok_state *tok) +{ + return new_string(str, strlen(str)); +} + +#else /* PGEN */ + +static char * +error_ret(struct tok_state *tok) /* XXX */ +{ + tok->decoding_erred = 1; + if (tok->fp != NULL && tok->buf != NULL) /* see PyTokenizer_Free */ + PyMem_FREE(tok->buf); + tok->buf = NULL; + return NULL; /* as if it were EOF */ +} + + +static char * +get_normal_name(char *s) /* for utf-8 and latin-1 */ +{ + char buf[13]; + int i; + for (i = 0; i < 12; i++) { + int c = s[i]; + if (c == '\0') + break; + else if (c == '_') + buf[i] = '-'; + else + buf[i] = tolower(c); + } + buf[i] = '\0'; + if (strcmp(buf, "utf-8") == 0 || + strncmp(buf, "utf-8-", 6) == 0) + return "utf-8"; + else if (strcmp(buf, "latin-1") == 0 || + strcmp(buf, "iso-8859-1") == 0 || + strcmp(buf, "iso-latin-1") == 0 || + strncmp(buf, "latin-1-", 8) == 0 || + strncmp(buf, "iso-8859-1-", 11) == 0 || + strncmp(buf, "iso-latin-1-", 12) == 0) + return "iso-8859-1"; + else + return s; +} + +/* Return the coding spec in S, or NULL if none is found. */ + +static char * +get_coding_spec(const char *s, Py_ssize_t size) +{ + Py_ssize_t i; + /* Coding spec must be in a comment, and that comment must be + * the only statement on the source code line. */ + for (i = 0; i < size - 6; i++) { + if (s[i] == '#') + break; + if (s[i] != ' ' && s[i] != '\t' && s[i] != '\014') + return NULL; + } + for (; i < size - 6; i++) { /* XXX inefficient search */ + const char* t = s + i; + if (strncmp(t, "coding", 6) == 0) { + const char* begin = NULL; + t += 6; + if (t[0] != ':' && t[0] != '=') + continue; + do { + t++; + } while (t[0] == '\x20' || t[0] == '\t'); + + begin = t; + while (Py_ISALNUM(t[0]) || + t[0] == '-' || t[0] == '_' || t[0] == '.') + t++; + + if (begin < t) { + char* r = new_string(begin, t - begin); + char* q = get_normal_name(r); + if (r != q) { + PyMem_FREE(r); + r = new_string(q, strlen(q)); + } + return r; + } + } + } + return NULL; +} + +/* Check whether the line contains a coding spec. If it does, + invoke the set_readline function for the new encoding. + This function receives the tok_state and the new encoding. + Return 1 on success, 0 on failure. */ + +static int +check_coding_spec(const char* line, Py_ssize_t size, struct tok_state *tok, + int set_readline(struct tok_state *, const char *)) +{ + char * cs; + int r = 1; + + if (tok->cont_line) { + /* It's a continuation line, so it can't be a coding spec. */ + tok->read_coding_spec = 1; + return 1; + } + cs = get_coding_spec(line, size); + if (!cs) { + Py_ssize_t i; + for (i = 0; i < size; i++) { + if (line[i] == '#' || line[i] == '\n' || line[i] == '\r') + break; + if (line[i] != ' ' && line[i] != '\t' && line[i] != '\014') { + /* Stop checking coding spec after a line containing + * anything except a comment. */ + tok->read_coding_spec = 1; + break; + } + } + } else { + tok->read_coding_spec = 1; + if (tok->encoding == NULL) { + assert(tok->decoding_state == 1); /* raw */ + if (strcmp(cs, "utf-8") == 0 || + strcmp(cs, "iso-8859-1") == 0) { + tok->encoding = cs; + } else { +#ifdef Py_USING_UNICODE + r = set_readline(tok, cs); + if (r) { + tok->encoding = cs; + tok->decoding_state = -1; + } + else { + PyErr_Format(PyExc_SyntaxError, + "encoding problem: %s", cs); + PyMem_FREE(cs); + } +#else + /* Without Unicode support, we cannot + process the coding spec. Since there + won't be any Unicode literals, that + won't matter. */ + PyMem_FREE(cs); +#endif + } + } else { /* then, compare cs with BOM */ + r = (strcmp(tok->encoding, cs) == 0); + if (!r) + PyErr_Format(PyExc_SyntaxError, + "encoding problem: %s with BOM", cs); + PyMem_FREE(cs); + } + } + return r; +} + +/* See whether the file starts with a BOM. If it does, + invoke the set_readline function with the new encoding. + Return 1 on success, 0 on failure. */ + +static int +check_bom(int get_char(struct tok_state *), + void unget_char(int, struct tok_state *), + int set_readline(struct tok_state *, const char *), + struct tok_state *tok) +{ + int ch1, ch2, ch3; + ch1 = get_char(tok); + tok->decoding_state = 1; + if (ch1 == EOF) { + return 1; + } else if (ch1 == 0xEF) { + ch2 = get_char(tok); + if (ch2 != 0xBB) { + unget_char(ch2, tok); + unget_char(ch1, tok); + return 1; + } + ch3 = get_char(tok); + if (ch3 != 0xBF) { + unget_char(ch3, tok); + unget_char(ch2, tok); + unget_char(ch1, tok); + return 1; + } +#if 0 + /* Disable support for UTF-16 BOMs until a decision + is made whether this needs to be supported. */ + } else if (ch1 == 0xFE) { + ch2 = get_char(tok); + if (ch2 != 0xFF) { + unget_char(ch2, tok); + unget_char(ch1, tok); + return 1; + } + if (!set_readline(tok, "utf-16-be")) + return 0; + tok->decoding_state = -1; + } else if (ch1 == 0xFF) { + ch2 = get_char(tok); + if (ch2 != 0xFE) { + unget_char(ch2, tok); + unget_char(ch1, tok); + return 1; + } + if (!set_readline(tok, "utf-16-le")) + return 0; + tok->decoding_state = -1; +#endif + } else { + unget_char(ch1, tok); + return 1; + } + if (tok->encoding != NULL) + PyMem_FREE(tok->encoding); + tok->encoding = new_string("utf-8", 5); /* resulting is in utf-8 */ + return 1; +} + +/* Read a line of text from TOK into S, using the stream in TOK. + Return NULL on failure, else S. + + On entry, tok->decoding_buffer will be one of: + 1) NULL: need to call tok->decoding_readline to get a new line + 2) PyUnicodeObject *: decoding_feof has called tok->decoding_readline and + stored the result in tok->decoding_buffer + 3) PyStringObject *: previous call to fp_readl did not have enough room + (in the s buffer) to copy entire contents of the line read + by tok->decoding_readline. tok->decoding_buffer has the overflow. + In this case, fp_readl is called in a loop (with an expanded buffer) + until the buffer ends with a '\n' (or until the end of the file is + reached): see tok_nextc and its calls to decoding_fgets. +*/ + +static char * +fp_readl(char *s, int size, struct tok_state *tok) +{ +#ifndef Py_USING_UNICODE + /* In a non-Unicode built, this should never be called. */ + Py_FatalError("fp_readl should not be called in this build."); + return NULL; /* Keep compiler happy (not reachable) */ +#else + PyObject* utf8 = NULL; + PyObject* buf = tok->decoding_buffer; + char *str; + Py_ssize_t utf8len; + + /* Ask for one less byte so we can terminate it */ + assert(size > 0); + size--; + + if (buf == NULL) { + buf = PyObject_CallObject(tok->decoding_readline, NULL); + if (buf == NULL) + return error_ret(tok); + if (!PyUnicode_Check(buf)) { + Py_DECREF(buf); + PyErr_SetString(PyExc_SyntaxError, + "codec did not return a unicode object"); + return error_ret(tok); + } + } else { + tok->decoding_buffer = NULL; + if (PyString_CheckExact(buf)) + utf8 = buf; + } + if (utf8 == NULL) { + utf8 = PyUnicode_AsUTF8String(buf); + Py_DECREF(buf); + if (utf8 == NULL) + return error_ret(tok); + } + str = PyString_AsString(utf8); + utf8len = PyString_GET_SIZE(utf8); + if (utf8len > size) { + tok->decoding_buffer = PyString_FromStringAndSize(str+size, utf8len-size); + if (tok->decoding_buffer == NULL) { + Py_DECREF(utf8); + return error_ret(tok); + } + utf8len = size; + } + memcpy(s, str, utf8len); + s[utf8len] = '\0'; + Py_DECREF(utf8); + if (utf8len == 0) + return NULL; /* EOF */ + return s; +#endif +} + +/* Set the readline function for TOK to a StreamReader's + readline function. The StreamReader is named ENC. + + This function is called from check_bom and check_coding_spec. + + ENC is usually identical to the future value of tok->encoding, + except for the (currently unsupported) case of UTF-16. + + Return 1 on success, 0 on failure. */ + +static int +fp_setreadl(struct tok_state *tok, const char* enc) +{ + PyObject *reader, *stream, *readline; + + /* XXX: constify filename argument. */ + stream = PyFile_FromFile(tok->fp, (char*)tok->filename, "rb", NULL); + if (stream == NULL) + return 0; + + reader = PyCodec_StreamReader(enc, stream, NULL); + Py_DECREF(stream); + if (reader == NULL) + return 0; + + readline = PyObject_GetAttrString(reader, "readline"); + Py_DECREF(reader); + if (readline == NULL) + return 0; + + tok->decoding_readline = readline; + return 1; +} + +/* Fetch the next byte from TOK. */ + +static int fp_getc(struct tok_state *tok) { + return getc(tok->fp); +} + +/* Unfetch the last byte back into TOK. */ + +static void fp_ungetc(int c, struct tok_state *tok) { + ungetc(c, tok->fp); +} + +/* Read a line of input from TOK. Determine encoding + if necessary. */ + +static char * +decoding_fgets(char *s, int size, struct tok_state *tok) +{ + char *line = NULL; + int badchar = 0; + for (;;) { + if (tok->decoding_state < 0) { + /* We already have a codec associated with + this input. */ + line = fp_readl(s, size, tok); + break; + } else if (tok->decoding_state > 0) { + /* We want a 'raw' read. */ + line = Py_UniversalNewlineFgets(s, size, + tok->fp, NULL); + break; + } else { + /* We have not yet determined the encoding. + If an encoding is found, use the file-pointer + reader functions from now on. */ + if (!check_bom(fp_getc, fp_ungetc, fp_setreadl, tok)) + return error_ret(tok); + assert(tok->decoding_state != 0); + } + } + if (line != NULL && tok->lineno < 2 && !tok->read_coding_spec) { + if (!check_coding_spec(line, strlen(line), tok, fp_setreadl)) { + return error_ret(tok); + } + } +#ifndef PGEN + /* The default encoding is ASCII, so make sure we don't have any + non-ASCII bytes in it. */ + if (line && !tok->encoding) { + unsigned char *c; + for (c = (unsigned char *)line; *c; c++) + if (*c > 127) { + badchar = *c; + break; + } + } + if (badchar) { + char buf[500]; + /* Need to add 1 to the line number, since this line + has not been counted, yet. */ + sprintf(buf, + "Non-ASCII character '\\x%.2x' " + "in file %.200s on line %i, " + "but no encoding declared; " + "see http://python.org/dev/peps/pep-0263/ for details", + badchar, tok->filename, tok->lineno + 1); + PyErr_SetString(PyExc_SyntaxError, buf); + return error_ret(tok); + } +#endif + return line; +} + +static int +decoding_feof(struct tok_state *tok) +{ + if (tok->decoding_state >= 0) { + return feof(tok->fp); + } else { + PyObject* buf = tok->decoding_buffer; + if (buf == NULL) { + buf = PyObject_CallObject(tok->decoding_readline, NULL); + if (buf == NULL) { + error_ret(tok); + return 1; + } else { + tok->decoding_buffer = buf; + } + } + return PyObject_Length(buf) == 0; + } +} + +/* Fetch a byte from TOK, using the string buffer. */ + +static int +buf_getc(struct tok_state *tok) { + return Py_CHARMASK(*tok->str++); +} + +/* Unfetch a byte from TOK, using the string buffer. */ + +static void +buf_ungetc(int c, struct tok_state *tok) { + tok->str--; + assert(Py_CHARMASK(*tok->str) == c); /* tok->cur may point to read-only segment */ +} + +/* Set the readline function for TOK to ENC. For the string-based + tokenizer, this means to just record the encoding. */ + +static int +buf_setreadl(struct tok_state *tok, const char* enc) { + tok->enc = enc; + return 1; +} + +/* Return a UTF-8 encoding Python string object from the + C byte string STR, which is encoded with ENC. */ + +#ifdef Py_USING_UNICODE +static PyObject * +translate_into_utf8(const char* str, const char* enc) { + PyObject *utf8; + PyObject* buf = PyUnicode_Decode(str, strlen(str), enc, NULL); + if (buf == NULL) + return NULL; + utf8 = PyUnicode_AsUTF8String(buf); + Py_DECREF(buf); + return utf8; +} +#endif + + +static char * +translate_newlines(const char *s, int exec_input, struct tok_state *tok) { + int skip_next_lf = 0, needed_length = strlen(s) + 2, final_length; + char *buf, *current; + char c = '\0'; + buf = PyMem_MALLOC(needed_length); + if (buf == NULL) { + tok->done = E_NOMEM; + return NULL; + } + for (current = buf; *s; s++, current++) { + c = *s; + if (skip_next_lf) { + skip_next_lf = 0; + if (c == '\n') { + c = *++s; + if (!c) + break; + } + } + if (c == '\r') { + skip_next_lf = 1; + c = '\n'; + } + *current = c; + } + /* If this is exec input, add a newline to the end of the string if + there isn't one already. */ + if (exec_input && c != '\n') { + *current = '\n'; + current++; + } + *current = '\0'; + final_length = current - buf + 1; + if (final_length < needed_length && final_length) + /* should never fail */ + buf = PyMem_REALLOC(buf, final_length); + return buf; +} + +/* Decode a byte string STR for use as the buffer of TOK. + Look for encoding declarations inside STR, and record them + inside TOK. */ + +static const char * +decode_str(const char *input, int single, struct tok_state *tok) +{ + PyObject* utf8 = NULL; + const char *str; + const char *s; + const char *newl[2] = {NULL, NULL}; + int lineno = 0; + tok->input = str = translate_newlines(input, single, tok); + if (str == NULL) + return NULL; + tok->enc = NULL; + tok->str = str; + if (!check_bom(buf_getc, buf_ungetc, buf_setreadl, tok)) + return error_ret(tok); + str = tok->str; /* string after BOM if any */ + assert(str); +#ifdef Py_USING_UNICODE + if (tok->enc != NULL) { + utf8 = translate_into_utf8(str, tok->enc); + if (utf8 == NULL) + return error_ret(tok); + str = PyString_AsString(utf8); + } +#endif + for (s = str;; s++) { + if (*s == '\0') break; + else if (*s == '\n') { + assert(lineno < 2); + newl[lineno] = s; + lineno++; + if (lineno == 2) break; + } + } + tok->enc = NULL; + /* need to check line 1 and 2 separately since check_coding_spec + assumes a single line as input */ + if (newl[0]) { + if (!check_coding_spec(str, newl[0] - str, tok, buf_setreadl)) + return error_ret(tok); + if (tok->enc == NULL && !tok->read_coding_spec && newl[1]) { + if (!check_coding_spec(newl[0]+1, newl[1] - newl[0], + tok, buf_setreadl)) + return error_ret(tok); + } + } +#ifdef Py_USING_UNICODE + if (tok->enc != NULL) { + assert(utf8 == NULL); + utf8 = translate_into_utf8(str, tok->enc); + if (utf8 == NULL) + return error_ret(tok); + str = PyString_AsString(utf8); + } +#endif + assert(tok->decoding_buffer == NULL); + tok->decoding_buffer = utf8; /* CAUTION */ + return str; +} + +#endif /* PGEN */ + +/* Set up tokenizer for string */ + +struct tok_state * +PyTokenizer_FromString(const char *str, int exec_input) +{ + struct tok_state *tok = tok_new(); + if (tok == NULL) + return NULL; + str = (char *)decode_str(str, exec_input, tok); + if (str == NULL) { + PyTokenizer_Free(tok); + return NULL; + } + + /* XXX: constify members. */ + tok->buf = tok->cur = tok->end = tok->inp = (char*)str; + return tok; +} + + +/* Set up tokenizer for file */ + +struct tok_state * +PyTokenizer_FromFile(FILE *fp, char *ps1, char *ps2) +{ + struct tok_state *tok = tok_new(); + if (tok == NULL) + return NULL; + if ((tok->buf = (char *)PyMem_MALLOC(BUFSIZ)) == NULL) { + PyTokenizer_Free(tok); + return NULL; + } + tok->cur = tok->inp = tok->buf; + tok->end = tok->buf + BUFSIZ; + tok->fp = fp; + tok->prompt = ps1; + tok->nextprompt = ps2; + return tok; +} + + +/* Free a tok_state structure */ + +void +PyTokenizer_Free(struct tok_state *tok) +{ + if (tok->encoding != NULL) + PyMem_FREE(tok->encoding); +#ifndef PGEN + Py_XDECREF(tok->decoding_readline); + Py_XDECREF(tok->decoding_buffer); +#endif + if (tok->fp != NULL && tok->buf != NULL) + PyMem_FREE(tok->buf); + if (tok->input) + PyMem_FREE((char *)tok->input); + PyMem_FREE(tok); +} + +#if !defined(PGEN) && defined(Py_USING_UNICODE) +static int +tok_stdin_decode(struct tok_state *tok, char **inp) +{ + PyObject *enc, *sysstdin, *decoded, *utf8; + const char *encoding; + char *converted; + + if (PySys_GetFile((char *)"stdin", NULL) != stdin) + return 0; + sysstdin = PySys_GetObject("stdin"); + if (sysstdin == NULL || !PyFile_Check(sysstdin)) + return 0; + + enc = ((PyFileObject *)sysstdin)->f_encoding; + if (enc == NULL || !PyString_Check(enc)) + return 0; + Py_INCREF(enc); + + encoding = PyString_AsString(enc); + decoded = PyUnicode_Decode(*inp, strlen(*inp), encoding, NULL); + if (decoded == NULL) + goto error_clear; + + utf8 = PyUnicode_AsEncodedString(decoded, "utf-8", NULL); + Py_DECREF(decoded); + if (utf8 == NULL) + goto error_clear; + + assert(PyString_Check(utf8)); + converted = new_string(PyString_AS_STRING(utf8), + PyString_GET_SIZE(utf8)); + Py_DECREF(utf8); + if (converted == NULL) + goto error_nomem; + + PyMem_FREE(*inp); + *inp = converted; + if (tok->encoding != NULL) + PyMem_FREE(tok->encoding); + tok->encoding = new_string(encoding, strlen(encoding)); + if (tok->encoding == NULL) + goto error_nomem; + + Py_DECREF(enc); + return 0; + +error_nomem: + Py_DECREF(enc); + tok->done = E_NOMEM; + return -1; + +error_clear: + Py_DECREF(enc); + if (!PyErr_ExceptionMatches(PyExc_UnicodeDecodeError)) { + tok->done = E_ERROR; + return -1; + } + /* Fallback to iso-8859-1: for backward compatibility */ + PyErr_Clear(); + return 0; +} +#endif + +/* Get next char, updating state; error code goes into tok->done */ + +static int +tok_nextc(register struct tok_state *tok) +{ + for (;;) { + if (tok->cur != tok->inp) { + return Py_CHARMASK(*tok->cur++); /* Fast path */ + } + if (tok->done != E_OK) + return EOF; + if (tok->fp == NULL) { + char *end = strchr(tok->inp, '\n'); + if (end != NULL) + end++; + else { + end = strchr(tok->inp, '\0'); + if (end == tok->inp) { + tok->done = E_EOF; + return EOF; + } + } + if (tok->start == NULL) + tok->buf = tok->cur; + tok->line_start = tok->cur; + tok->lineno++; + tok->inp = end; + return Py_CHARMASK(*tok->cur++); + } + if (tok->prompt != NULL) { + char *newtok = PyOS_Readline(stdin, stdout, tok->prompt); + if (tok->nextprompt != NULL) + tok->prompt = tok->nextprompt; + if (newtok == NULL) + tok->done = E_INTR; + else if (*newtok == '\0') { + PyMem_FREE(newtok); + tok->done = E_EOF; + } +#if !defined(PGEN) && defined(Py_USING_UNICODE) + else if (tok_stdin_decode(tok, &newtok) != 0) + PyMem_FREE(newtok); +#endif + else if (tok->start != NULL) { + size_t start = tok->start - tok->buf; + size_t oldlen = tok->cur - tok->buf; + size_t newlen = oldlen + strlen(newtok); + char *buf = tok->buf; + buf = (char *)PyMem_REALLOC(buf, newlen+1); + tok->lineno++; + if (buf == NULL) { + PyMem_FREE(tok->buf); + tok->buf = NULL; + PyMem_FREE(newtok); + tok->done = E_NOMEM; + return EOF; + } + tok->buf = buf; + tok->cur = tok->buf + oldlen; + tok->line_start = tok->cur; + strcpy(tok->buf + oldlen, newtok); + PyMem_FREE(newtok); + tok->inp = tok->buf + newlen; + tok->end = tok->inp + 1; + tok->start = tok->buf + start; + } + else { + tok->lineno++; + if (tok->buf != NULL) + PyMem_FREE(tok->buf); + tok->buf = newtok; + tok->line_start = tok->buf; + tok->cur = tok->buf; + tok->line_start = tok->buf; + tok->inp = strchr(tok->buf, '\0'); + tok->end = tok->inp + 1; + } + } + else { + int done = 0; + Py_ssize_t cur = 0; + char *pt; + if (tok->start == NULL) { + if (tok->buf == NULL) { + tok->buf = (char *) + PyMem_MALLOC(BUFSIZ); + if (tok->buf == NULL) { + tok->done = E_NOMEM; + return EOF; + } + tok->end = tok->buf + BUFSIZ; + } + if (decoding_fgets(tok->buf, (int)(tok->end - tok->buf), + tok) == NULL) { + tok->done = E_EOF; + done = 1; + } + else { + tok->done = E_OK; + tok->inp = strchr(tok->buf, '\0'); + done = tok->inp[-1] == '\n'; + } + } + else { + cur = tok->cur - tok->buf; + if (decoding_feof(tok)) { + tok->done = E_EOF; + done = 1; + } + else + tok->done = E_OK; + } + tok->lineno++; + /* Read until '\n' or EOF */ + while (!done) { + Py_ssize_t curstart = tok->start == NULL ? -1 : + tok->start - tok->buf; + Py_ssize_t curvalid = tok->inp - tok->buf; + Py_ssize_t newsize = curvalid + BUFSIZ; + char *newbuf = tok->buf; + newbuf = (char *)PyMem_REALLOC(newbuf, + newsize); + if (newbuf == NULL) { + tok->done = E_NOMEM; + tok->cur = tok->inp; + return EOF; + } + tok->buf = newbuf; + tok->inp = tok->buf + curvalid; + tok->end = tok->buf + newsize; + tok->start = curstart < 0 ? NULL : + tok->buf + curstart; + if (decoding_fgets(tok->inp, + (int)(tok->end - tok->inp), + tok) == NULL) { + /* Break out early on decoding + errors, as tok->buf will be NULL + */ + if (tok->decoding_erred) + return EOF; + /* Last line does not end in \n, + fake one */ + strcpy(tok->inp, "\n"); + } + tok->inp = strchr(tok->inp, '\0'); + done = tok->inp[-1] == '\n'; + } + if (tok->buf != NULL) { + tok->cur = tok->buf + cur; + tok->line_start = tok->cur; + /* replace "\r\n" with "\n" */ + /* For Mac leave the \r, giving a syntax error */ + pt = tok->inp - 2; + if (pt >= tok->buf && *pt == '\r') { + *pt++ = '\n'; + *pt = '\0'; + tok->inp = pt; + } + } + } + if (tok->done != E_OK) { + if (tok->prompt != NULL) + PySys_WriteStderr("\n"); + tok->cur = tok->inp; + return EOF; + } + } + /*NOTREACHED*/ +} + + +/* Back-up one character */ + +static void +tok_backup(register struct tok_state *tok, register int c) +{ + if (c != EOF) { + if (--tok->cur < tok->buf) + Py_FatalError("tok_backup: beginning of buffer"); + if (*tok->cur != c) + *tok->cur = c; + } +} + + +/* Return the token corresponding to a single character */ + +int +PyToken_OneChar(int c) +{ + switch (c) { + case '(': return LPAR; + case ')': return RPAR; + case '[': return LSQB; + case ']': return RSQB; + case ':': return COLON; + case ',': return COMMA; + case ';': return SEMI; + case '+': return PLUS; + case '-': return MINUS; + case '*': return STAR; + case '/': return SLASH; + case '|': return VBAR; + case '&': return AMPER; + case '<': return LESS; + case '>': return GREATER; + case '=': return EQUAL; + case '.': return DOT; + case '%': return PERCENT; + case '`': return BACKQUOTE; + case '{': return LBRACE; + case '}': return RBRACE; + case '^': return CIRCUMFLEX; + case '~': return TILDE; + case '@': return AT; + default: return OP; + } +} + + +int +PyToken_TwoChars(int c1, int c2) +{ + switch (c1) { + case '=': + switch (c2) { + case '=': return EQEQUAL; + } + break; + case '!': + switch (c2) { + case '=': return NOTEQUAL; + } + break; + case '<': + switch (c2) { + case '>': return NOTEQUAL; + case '=': return LESSEQUAL; + case '<': return LEFTSHIFT; + } + break; + case '>': + switch (c2) { + case '=': return GREATEREQUAL; + case '>': return RIGHTSHIFT; + } + break; + case '+': + switch (c2) { + case '=': return PLUSEQUAL; + } + break; + case '-': + switch (c2) { + case '=': return MINEQUAL; + } + break; + case '*': + switch (c2) { + case '*': return DOUBLESTAR; + case '=': return STAREQUAL; + } + break; + case '/': + switch (c2) { + case '/': return DOUBLESLASH; + case '=': return SLASHEQUAL; + } + break; + case '|': + switch (c2) { + case '=': return VBAREQUAL; + } + break; + case '%': + switch (c2) { + case '=': return PERCENTEQUAL; + } + break; + case '&': + switch (c2) { + case '=': return AMPEREQUAL; + } + break; + case '^': + switch (c2) { + case '=': return CIRCUMFLEXEQUAL; + } + break; + } + return OP; +} + +int +PyToken_ThreeChars(int c1, int c2, int c3) +{ + switch (c1) { + case '<': + switch (c2) { + case '<': + switch (c3) { + case '=': + return LEFTSHIFTEQUAL; + } + break; + } + break; + case '>': + switch (c2) { + case '>': + switch (c3) { + case '=': + return RIGHTSHIFTEQUAL; + } + break; + } + break; + case '*': + switch (c2) { + case '*': + switch (c3) { + case '=': + return DOUBLESTAREQUAL; + } + break; + } + break; + case '/': + switch (c2) { + case '/': + switch (c3) { + case '=': + return DOUBLESLASHEQUAL; + } + break; + } + break; + } + return OP; +} + +static int +indenterror(struct tok_state *tok) +{ + if (tok->alterror) { + tok->done = E_TABSPACE; + tok->cur = tok->inp; + return 1; + } + if (tok->altwarning) { + PySys_WriteStderr("%s: inconsistent use of tabs and spaces " + "in indentation\n", tok->filename); + tok->altwarning = 0; + } + return 0; +} + +/* Get next token, after space stripping etc. */ + +static int +tok_get(register struct tok_state *tok, char **p_start, char **p_end) +{ + register int c; + int blankline; + + *p_start = *p_end = NULL; + nextline: + tok->start = NULL; + blankline = 0; + + /* Get indentation level */ + if (tok->atbol) { + register int col = 0; + register int altcol = 0; + tok->atbol = 0; + for (;;) { + c = tok_nextc(tok); + if (c == ' ') + col++, altcol++; + else if (c == '\t') { + col = (col/tok->tabsize + 1) * tok->tabsize; + altcol = (altcol/tok->alttabsize + 1) + * tok->alttabsize; + } + else if (c == '\014') /* Control-L (formfeed) */ + col = altcol = 0; /* For Emacs users */ + else + break; + } + tok_backup(tok, c); + if (c == '#' || c == '\n') { + /* Lines with only whitespace and/or comments + shouldn't affect the indentation and are + not passed to the parser as NEWLINE tokens, + except *totally* empty lines in interactive + mode, which signal the end of a command group. */ + if (col == 0 && c == '\n' && tok->prompt != NULL) + blankline = 0; /* Let it through */ + else + blankline = 1; /* Ignore completely */ + /* We can't jump back right here since we still + may need to skip to the end of a comment */ + } + if (!blankline && tok->level == 0) { + if (col == tok->indstack[tok->indent]) { + /* No change */ + if (altcol != tok->altindstack[tok->indent]) { + if (indenterror(tok)) + return ERRORTOKEN; + } + } + else if (col > tok->indstack[tok->indent]) { + /* Indent -- always one */ + if (tok->indent+1 >= MAXINDENT) { + tok->done = E_TOODEEP; + tok->cur = tok->inp; + return ERRORTOKEN; + } + if (altcol <= tok->altindstack[tok->indent]) { + if (indenterror(tok)) + return ERRORTOKEN; + } + tok->pendin++; + tok->indstack[++tok->indent] = col; + tok->altindstack[tok->indent] = altcol; + } + else /* col < tok->indstack[tok->indent] */ { + /* Dedent -- any number, must be consistent */ + while (tok->indent > 0 && + col < tok->indstack[tok->indent]) { + tok->pendin--; + tok->indent--; + } + if (col != tok->indstack[tok->indent]) { + tok->done = E_DEDENT; + tok->cur = tok->inp; + return ERRORTOKEN; + } + if (altcol != tok->altindstack[tok->indent]) { + if (indenterror(tok)) + return ERRORTOKEN; + } + } + } + } + + tok->start = tok->cur; + + /* Return pending indents/dedents */ + if (tok->pendin != 0) { + if (tok->pendin < 0) { + tok->pendin++; + return DEDENT; + } + else { + tok->pendin--; + return INDENT; + } + } + + again: + tok->start = NULL; + /* Skip spaces */ + do { + c = tok_nextc(tok); + } while (c == ' ' || c == '\t' || c == '\014'); + + /* Set start of current token */ + tok->start = tok->cur - 1; + + /* Skip comment, while looking for tab-setting magic */ + if (c == '#') { + static char *tabforms[] = { + "tab-width:", /* Emacs */ + ":tabstop=", /* vim, full form */ + ":ts=", /* vim, abbreviated form */ + "set tabsize=", /* will vi never die? */ + /* more templates can be added here to support other editors */ + }; + char cbuf[80]; + char *tp, **cp; + tp = cbuf; + do { + *tp++ = c = tok_nextc(tok); + } while (c != EOF && c != '\n' && + (size_t)(tp - cbuf + 1) < sizeof(cbuf)); + *tp = '\0'; + for (cp = tabforms; + cp < tabforms + sizeof(tabforms)/sizeof(tabforms[0]); + cp++) { + if ((tp = strstr(cbuf, *cp))) { + int newsize = atoi(tp + strlen(*cp)); + + if (newsize >= 1 && newsize <= 40) { + tok->tabsize = newsize; + if (Py_VerboseFlag) + PySys_WriteStderr( + "Tab size set to %d\n", + newsize); + } + } + } + while (c != EOF && c != '\n') + c = tok_nextc(tok); + } + + /* Check for EOF and errors now */ + if (c == EOF) { + return tok->done == E_EOF ? ENDMARKER : ERRORTOKEN; + } + + /* Identifier (most frequent token!) */ + if (Py_ISALPHA(c) || c == '_') { + /* Process r"", u"" and ur"" */ + switch (c) { + case 'b': + case 'B': + c = tok_nextc(tok); + if (c == 'r' || c == 'R') + c = tok_nextc(tok); + if (c == '"' || c == '\'') + goto letter_quote; + break; + case 'r': + case 'R': + c = tok_nextc(tok); + if (c == '"' || c == '\'') + goto letter_quote; + break; + case 'u': + case 'U': + c = tok_nextc(tok); + if (c == 'r' || c == 'R') + c = tok_nextc(tok); + if (c == '"' || c == '\'') + goto letter_quote; + break; + } + while (c != EOF && (Py_ISALNUM(c) || c == '_')) { + c = tok_nextc(tok); + } + tok_backup(tok, c); + *p_start = tok->start; + *p_end = tok->cur; + return NAME; + } + + /* Newline */ + if (c == '\n') { + tok->atbol = 1; + if (blankline || tok->level > 0) + goto nextline; + *p_start = tok->start; + *p_end = tok->cur - 1; /* Leave '\n' out of the string */ + tok->cont_line = 0; + return NEWLINE; + } + + /* Period or number starting with period? */ + if (c == '.') { + c = tok_nextc(tok); + if (isdigit(c)) { + goto fraction; + } + else { + tok_backup(tok, c); + *p_start = tok->start; + *p_end = tok->cur; + return DOT; + } + } + + /* Number */ + if (isdigit(c)) { + if (c == '0') { + /* Hex, octal or binary -- maybe. */ + c = tok_nextc(tok); + if (c == '.') + goto fraction; +#ifndef WITHOUT_COMPLEX + if (c == 'j' || c == 'J') + goto imaginary; +#endif + if (c == 'x' || c == 'X') { + + /* Hex */ + c = tok_nextc(tok); + if (!isxdigit(c)) { + tok->done = E_TOKEN; + tok_backup(tok, c); + return ERRORTOKEN; + } + do { + c = tok_nextc(tok); + } while (isxdigit(c)); + } + else if (c == 'o' || c == 'O') { + /* Octal */ + c = tok_nextc(tok); + if (c < '0' || c >= '8') { + tok->done = E_TOKEN; + tok_backup(tok, c); + return ERRORTOKEN; + } + do { + c = tok_nextc(tok); + } while ('0' <= c && c < '8'); + } + else if (c == 'b' || c == 'B') { + /* Binary */ + c = tok_nextc(tok); + if (c != '0' && c != '1') { + tok->done = E_TOKEN; + tok_backup(tok, c); + return ERRORTOKEN; + } + do { + c = tok_nextc(tok); + } while (c == '0' || c == '1'); + } + else { + int found_decimal = 0; + /* Octal; c is first char of it */ + /* There's no 'isoctdigit' macro, sigh */ + while ('0' <= c && c < '8') { + c = tok_nextc(tok); + } + if (isdigit(c)) { + found_decimal = 1; + do { + c = tok_nextc(tok); + } while (isdigit(c)); + } + if (c == '.') + goto fraction; + else if (c == 'e' || c == 'E') + goto exponent; +#ifndef WITHOUT_COMPLEX + else if (c == 'j' || c == 'J') + goto imaginary; +#endif + else if (found_decimal) { + tok->done = E_TOKEN; + tok_backup(tok, c); + return ERRORTOKEN; + } + } + if (c == 'l' || c == 'L') + c = tok_nextc(tok); + } + else { + /* Decimal */ + do { + c = tok_nextc(tok); + } while (isdigit(c)); + if (c == 'l' || c == 'L') + c = tok_nextc(tok); + else { + /* Accept floating point numbers. */ + if (c == '.') { + fraction: + /* Fraction */ + do { + c = tok_nextc(tok); + } while (isdigit(c)); + } + if (c == 'e' || c == 'E') { + int e; + exponent: + e = c; + /* Exponent part */ + c = tok_nextc(tok); + if (c == '+' || c == '-') { + c = tok_nextc(tok); + if (!isdigit(c)) { + tok->done = E_TOKEN; + tok_backup(tok, c); + return ERRORTOKEN; + } + } else if (!isdigit(c)) { + tok_backup(tok, c); + tok_backup(tok, e); + *p_start = tok->start; + *p_end = tok->cur; + return NUMBER; + } + do { + c = tok_nextc(tok); + } while (isdigit(c)); + } +#ifndef WITHOUT_COMPLEX + if (c == 'j' || c == 'J') + /* Imaginary part */ + imaginary: + c = tok_nextc(tok); +#endif + } + } + tok_backup(tok, c); + *p_start = tok->start; + *p_end = tok->cur; + return NUMBER; + } + + letter_quote: + /* String */ + if (c == '\'' || c == '"') { + Py_ssize_t quote2 = tok->cur - tok->start + 1; + int quote = c; + int triple = 0; + int tripcount = 0; + for (;;) { + c = tok_nextc(tok); + if (c == '\n') { + if (!triple) { + tok->done = E_EOLS; + tok_backup(tok, c); + return ERRORTOKEN; + } + tripcount = 0; + tok->cont_line = 1; /* multiline string. */ + } + else if (c == EOF) { + if (triple) + tok->done = E_EOFS; + else + tok->done = E_EOLS; + tok->cur = tok->inp; + return ERRORTOKEN; + } + else if (c == quote) { + tripcount++; + if (tok->cur - tok->start == quote2) { + c = tok_nextc(tok); + if (c == quote) { + triple = 1; + tripcount = 0; + continue; + } + tok_backup(tok, c); + } + if (!triple || tripcount == 3) + break; + } + else if (c == '\\') { + tripcount = 0; + c = tok_nextc(tok); + if (c == EOF) { + tok->done = E_EOLS; + tok->cur = tok->inp; + return ERRORTOKEN; + } + } + else + tripcount = 0; + } + *p_start = tok->start; + *p_end = tok->cur; + return STRING; + } + + /* Line continuation */ + if (c == '\\') { + c = tok_nextc(tok); + if (c != '\n') { + tok->done = E_LINECONT; + tok->cur = tok->inp; + return ERRORTOKEN; + } + tok->cont_line = 1; + goto again; /* Read next line */ + } + + /* Check for two-character token */ + { + int c2 = tok_nextc(tok); + int token = PyToken_TwoChars(c, c2); +#ifndef PGEN + if (Py_Py3kWarningFlag && token == NOTEQUAL && c == '<') { + if (PyErr_WarnExplicit(PyExc_DeprecationWarning, + "<> not supported in 3.x; use !=", + tok->filename, tok->lineno, + NULL, NULL)) { + return ERRORTOKEN; + } + } +#endif + if (token != OP) { + int c3 = tok_nextc(tok); + int token3 = PyToken_ThreeChars(c, c2, c3); + if (token3 != OP) { + token = token3; + } else { + tok_backup(tok, c3); + } + *p_start = tok->start; + *p_end = tok->cur; + return token; + } + tok_backup(tok, c2); + } + + /* Keep track of parentheses nesting level */ + switch (c) { + case '(': + case '[': + case '{': + tok->level++; + break; + case ')': + case ']': + case '}': + tok->level--; + break; + } + + /* Punctuation character */ + *p_start = tok->start; + *p_end = tok->cur; + return PyToken_OneChar(c); +} + +int +PyTokenizer_Get(struct tok_state *tok, char **p_start, char **p_end) +{ + int result = tok_get(tok, p_start, p_end); + if (tok->decoding_erred) { + result = ERRORTOKEN; + tok->done = E_DECODE; + } + return result; +} + +/* This function is only called from parsetok. However, it cannot live + there, as it must be empty for PGEN, and we can check for PGEN only + in this file. */ + +#if defined(PGEN) || !defined(Py_USING_UNICODE) +char* +PyTokenizer_RestoreEncoding(struct tok_state* tok, int len, int* offset) +{ + return NULL; +} +#else +#ifdef Py_USING_UNICODE +static PyObject * +dec_utf8(const char *enc, const char *text, size_t len) { + PyObject *ret = NULL; + PyObject *unicode_text = PyUnicode_DecodeUTF8(text, len, "replace"); + if (unicode_text) { + ret = PyUnicode_AsEncodedString(unicode_text, enc, "replace"); + Py_DECREF(unicode_text); + } + if (!ret) { + PyErr_Clear(); + } + return ret; +} +char * +PyTokenizer_RestoreEncoding(struct tok_state* tok, int len, int *offset) +{ + char *text = NULL; + if (tok->encoding) { + /* convert source to original encondig */ + PyObject *lineobj = dec_utf8(tok->encoding, tok->buf, len); + if (lineobj != NULL) { + int linelen = PyString_Size(lineobj); + const char *line = PyString_AsString(lineobj); + text = PyObject_MALLOC(linelen + 1); + if (text != NULL && line != NULL) { + if (linelen) + strncpy(text, line, linelen); + text[linelen] = '\0'; + } + Py_DECREF(lineobj); + + /* adjust error offset */ + if (*offset > 1) { + PyObject *offsetobj = dec_utf8(tok->encoding, + tok->buf, *offset-1); + if (offsetobj) { + *offset = PyString_Size(offsetobj) + 1; + Py_DECREF(offsetobj); + } + } + + } + } + return text; + +} +#endif /* defined(Py_USING_UNICODE) */ +#endif + + +#ifdef Py_DEBUG + +void +tok_dump(int type, char *start, char *end) +{ + printf("%s", _PyParser_TokenNames[type]); + if (type == NAME || type == NUMBER || type == STRING || type == OP) + printf("(%.*s)", (int)(end - start), start); +} + +#endif diff --git a/AppPkg/Applications/Python/Python-2.7.10/Parser/tokenizer.h b/AppPkg/Applications/Python/Python-2.7.10/Parser/tokenizer.h new file mode 100644 index 0000000000..3de3280d05 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Parser/tokenizer.h @@ -0,0 +1,70 @@ +#ifndef Py_TOKENIZER_H +#define Py_TOKENIZER_H +#ifdef __cplusplus +extern "C" { +#endif + +#include "object.h" + +/* Tokenizer interface */ + +#include "token.h" /* For token types */ + +#define MAXINDENT 100 /* Max indentation level */ + +/* Tokenizer state */ +struct tok_state { + /* Input state; buf <= cur <= inp <= end */ + /* NB an entire line is held in the buffer */ + char *buf; /* Input buffer, or NULL; malloc'ed if fp != NULL */ + char *cur; /* Next character in buffer */ + char *inp; /* End of data in buffer */ + char *end; /* End of input buffer if buf != NULL */ + char *start; /* Start of current token if not NULL */ + int done; /* E_OK normally, E_EOF at EOF, otherwise error code */ + /* NB If done != E_OK, cur must be == inp!!! */ + FILE *fp; /* Rest of input; NULL if tokenizing a string */ + int tabsize; /* Tab spacing */ + int indent; /* Current indentation index */ + int indstack[MAXINDENT]; /* Stack of indents */ + int atbol; /* Nonzero if at begin of new line */ + int pendin; /* Pending indents (if > 0) or dedents (if < 0) */ + char *prompt, *nextprompt; /* For interactive prompting */ + int lineno; /* Current line number */ + int level; /* () [] {} Parentheses nesting level */ + /* Used to allow free continuations inside them */ + /* Stuff for checking on different tab sizes */ + const char *filename; /* For error messages */ + int altwarning; /* Issue warning if alternate tabs don't match */ + int alterror; /* Issue error if alternate tabs don't match */ + int alttabsize; /* Alternate tab spacing */ + int altindstack[MAXINDENT]; /* Stack of alternate indents */ + /* Stuff for PEP 0263 */ + int decoding_state; /* -1:decoding, 0:init, 1:raw */ + int decoding_erred; /* whether erred in decoding */ + int read_coding_spec; /* whether 'coding:...' has been read */ + char *encoding; + int cont_line; /* whether we are in a continuation line. */ + const char* line_start; /* pointer to start of current line */ +#ifndef PGEN + PyObject *decoding_readline; /* codecs.open(...).readline */ + PyObject *decoding_buffer; +#endif + const char* enc; + const char* str; + const char* input; /* Tokenizer's newline translated copy of the string. */ +}; + +extern struct tok_state *PyTokenizer_FromString(const char *, int); +extern struct tok_state *PyTokenizer_FromFile(FILE *, char *, char *); +extern void PyTokenizer_Free(struct tok_state *); +extern int PyTokenizer_Get(struct tok_state *, char **, char **); +#if defined(PGEN) || defined(Py_USING_UNICODE) +extern char * PyTokenizer_RestoreEncoding(struct tok_state* tok, + int len, int *offset); +#endif + +#ifdef __cplusplus +} +#endif +#endif /* !Py_TOKENIZER_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/Python-ast.c b/AppPkg/Applications/Python/Python-2.7.10/Python/Python-ast.c new file mode 100644 index 0000000000..ab4009a942 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/Python-ast.c @@ -0,0 +1,6788 @@ +/* File automatically generated by Parser/asdl_c.py. */ + + +/* + __version__ 82160. + + This module must be committed separately after each AST grammar change; + The __version__ number is set to the revision number of the commit + containing the grammar change. +*/ + +#include "Python.h" +#include "Python-ast.h" + +static PyTypeObject AST_type; +static PyTypeObject *mod_type; +static PyObject* ast2obj_mod(void*); +static PyTypeObject *Module_type; +static char *Module_fields[]={ + "body", +}; +static PyTypeObject *Interactive_type; +static char *Interactive_fields[]={ + "body", +}; +static PyTypeObject *Expression_type; +static char *Expression_fields[]={ + "body", +}; +static PyTypeObject *Suite_type; +static char *Suite_fields[]={ + "body", +}; +static PyTypeObject *stmt_type; +static char *stmt_attributes[] = { + "lineno", + "col_offset", +}; +static PyObject* ast2obj_stmt(void*); +static PyTypeObject *FunctionDef_type; +static char *FunctionDef_fields[]={ + "name", + "args", + "body", + "decorator_list", +}; +static PyTypeObject *ClassDef_type; +static char *ClassDef_fields[]={ + "name", + "bases", + "body", + "decorator_list", +}; +static PyTypeObject *Return_type; +static char *Return_fields[]={ + "value", +}; +static PyTypeObject *Delete_type; +static char *Delete_fields[]={ + "targets", +}; +static PyTypeObject *Assign_type; +static char *Assign_fields[]={ + "targets", + "value", +}; +static PyTypeObject *AugAssign_type; +static char *AugAssign_fields[]={ + "target", + "op", + "value", +}; +static PyTypeObject *Print_type; +static char *Print_fields[]={ + "dest", + "values", + "nl", +}; +static PyTypeObject *For_type; +static char *For_fields[]={ + "target", + "iter", + "body", + "orelse", +}; +static PyTypeObject *While_type; +static char *While_fields[]={ + "test", + "body", + "orelse", +}; +static PyTypeObject *If_type; +static char *If_fields[]={ + "test", + "body", + "orelse", +}; +static PyTypeObject *With_type; +static char *With_fields[]={ + "context_expr", + "optional_vars", + "body", +}; +static PyTypeObject *Raise_type; +static char *Raise_fields[]={ + "type", + "inst", + "tback", +}; +static PyTypeObject *TryExcept_type; +static char *TryExcept_fields[]={ + "body", + "handlers", + "orelse", +}; +static PyTypeObject *TryFinally_type; +static char *TryFinally_fields[]={ + "body", + "finalbody", +}; +static PyTypeObject *Assert_type; +static char *Assert_fields[]={ + "test", + "msg", +}; +static PyTypeObject *Import_type; +static char *Import_fields[]={ + "names", +}; +static PyTypeObject *ImportFrom_type; +static char *ImportFrom_fields[]={ + "module", + "names", + "level", +}; +static PyTypeObject *Exec_type; +static char *Exec_fields[]={ + "body", + "globals", + "locals", +}; +static PyTypeObject *Global_type; +static char *Global_fields[]={ + "names", +}; +static PyTypeObject *Expr_type; +static char *Expr_fields[]={ + "value", +}; +static PyTypeObject *Pass_type; +static PyTypeObject *Break_type; +static PyTypeObject *Continue_type; +static PyTypeObject *expr_type; +static char *expr_attributes[] = { + "lineno", + "col_offset", +}; +static PyObject* ast2obj_expr(void*); +static PyTypeObject *BoolOp_type; +static char *BoolOp_fields[]={ + "op", + "values", +}; +static PyTypeObject *BinOp_type; +static char *BinOp_fields[]={ + "left", + "op", + "right", +}; +static PyTypeObject *UnaryOp_type; +static char *UnaryOp_fields[]={ + "op", + "operand", +}; +static PyTypeObject *Lambda_type; +static char *Lambda_fields[]={ + "args", + "body", +}; +static PyTypeObject *IfExp_type; +static char *IfExp_fields[]={ + "test", + "body", + "orelse", +}; +static PyTypeObject *Dict_type; +static char *Dict_fields[]={ + "keys", + "values", +}; +static PyTypeObject *Set_type; +static char *Set_fields[]={ + "elts", +}; +static PyTypeObject *ListComp_type; +static char *ListComp_fields[]={ + "elt", + "generators", +}; +static PyTypeObject *SetComp_type; +static char *SetComp_fields[]={ + "elt", + "generators", +}; +static PyTypeObject *DictComp_type; +static char *DictComp_fields[]={ + "key", + "value", + "generators", +}; +static PyTypeObject *GeneratorExp_type; +static char *GeneratorExp_fields[]={ + "elt", + "generators", +}; +static PyTypeObject *Yield_type; +static char *Yield_fields[]={ + "value", +}; +static PyTypeObject *Compare_type; +static char *Compare_fields[]={ + "left", + "ops", + "comparators", +}; +static PyTypeObject *Call_type; +static char *Call_fields[]={ + "func", + "args", + "keywords", + "starargs", + "kwargs", +}; +static PyTypeObject *Repr_type; +static char *Repr_fields[]={ + "value", +}; +static PyTypeObject *Num_type; +static char *Num_fields[]={ + "n", +}; +static PyTypeObject *Str_type; +static char *Str_fields[]={ + "s", +}; +static PyTypeObject *Attribute_type; +static char *Attribute_fields[]={ + "value", + "attr", + "ctx", +}; +static PyTypeObject *Subscript_type; +static char *Subscript_fields[]={ + "value", + "slice", + "ctx", +}; +static PyTypeObject *Name_type; +static char *Name_fields[]={ + "id", + "ctx", +}; +static PyTypeObject *List_type; +static char *List_fields[]={ + "elts", + "ctx", +}; +static PyTypeObject *Tuple_type; +static char *Tuple_fields[]={ + "elts", + "ctx", +}; +static PyTypeObject *expr_context_type; +static PyObject *Load_singleton, *Store_singleton, *Del_singleton, +*AugLoad_singleton, *AugStore_singleton, *Param_singleton; +static PyObject* ast2obj_expr_context(expr_context_ty); +static PyTypeObject *Load_type; +static PyTypeObject *Store_type; +static PyTypeObject *Del_type; +static PyTypeObject *AugLoad_type; +static PyTypeObject *AugStore_type; +static PyTypeObject *Param_type; +static PyTypeObject *slice_type; +static PyObject* ast2obj_slice(void*); +static PyTypeObject *Ellipsis_type; +static PyTypeObject *Slice_type; +static char *Slice_fields[]={ + "lower", + "upper", + "step", +}; +static PyTypeObject *ExtSlice_type; +static char *ExtSlice_fields[]={ + "dims", +}; +static PyTypeObject *Index_type; +static char *Index_fields[]={ + "value", +}; +static PyTypeObject *boolop_type; +static PyObject *And_singleton, *Or_singleton; +static PyObject* ast2obj_boolop(boolop_ty); +static PyTypeObject *And_type; +static PyTypeObject *Or_type; +static PyTypeObject *operator_type; +static PyObject *Add_singleton, *Sub_singleton, *Mult_singleton, +*Div_singleton, *Mod_singleton, *Pow_singleton, *LShift_singleton, +*RShift_singleton, *BitOr_singleton, *BitXor_singleton, *BitAnd_singleton, +*FloorDiv_singleton; +static PyObject* ast2obj_operator(operator_ty); +static PyTypeObject *Add_type; +static PyTypeObject *Sub_type; +static PyTypeObject *Mult_type; +static PyTypeObject *Div_type; +static PyTypeObject *Mod_type; +static PyTypeObject *Pow_type; +static PyTypeObject *LShift_type; +static PyTypeObject *RShift_type; +static PyTypeObject *BitOr_type; +static PyTypeObject *BitXor_type; +static PyTypeObject *BitAnd_type; +static PyTypeObject *FloorDiv_type; +static PyTypeObject *unaryop_type; +static PyObject *Invert_singleton, *Not_singleton, *UAdd_singleton, +*USub_singleton; +static PyObject* ast2obj_unaryop(unaryop_ty); +static PyTypeObject *Invert_type; +static PyTypeObject *Not_type; +static PyTypeObject *UAdd_type; +static PyTypeObject *USub_type; +static PyTypeObject *cmpop_type; +static PyObject *Eq_singleton, *NotEq_singleton, *Lt_singleton, *LtE_singleton, +*Gt_singleton, *GtE_singleton, *Is_singleton, *IsNot_singleton, *In_singleton, +*NotIn_singleton; +static PyObject* ast2obj_cmpop(cmpop_ty); +static PyTypeObject *Eq_type; +static PyTypeObject *NotEq_type; +static PyTypeObject *Lt_type; +static PyTypeObject *LtE_type; +static PyTypeObject *Gt_type; +static PyTypeObject *GtE_type; +static PyTypeObject *Is_type; +static PyTypeObject *IsNot_type; +static PyTypeObject *In_type; +static PyTypeObject *NotIn_type; +static PyTypeObject *comprehension_type; +static PyObject* ast2obj_comprehension(void*); +static char *comprehension_fields[]={ + "target", + "iter", + "ifs", +}; +static PyTypeObject *excepthandler_type; +static char *excepthandler_attributes[] = { + "lineno", + "col_offset", +}; +static PyObject* ast2obj_excepthandler(void*); +static PyTypeObject *ExceptHandler_type; +static char *ExceptHandler_fields[]={ + "type", + "name", + "body", +}; +static PyTypeObject *arguments_type; +static PyObject* ast2obj_arguments(void*); +static char *arguments_fields[]={ + "args", + "vararg", + "kwarg", + "defaults", +}; +static PyTypeObject *keyword_type; +static PyObject* ast2obj_keyword(void*); +static char *keyword_fields[]={ + "arg", + "value", +}; +static PyTypeObject *alias_type; +static PyObject* ast2obj_alias(void*); +static char *alias_fields[]={ + "name", + "asname", +}; + + +static int +ast_type_init(PyObject *self, PyObject *args, PyObject *kw) +{ + Py_ssize_t i, numfields = 0; + int res = -1; + PyObject *key, *value, *fields; + fields = PyObject_GetAttrString((PyObject*)Py_TYPE(self), "_fields"); + if (!fields) + PyErr_Clear(); + if (fields) { + numfields = PySequence_Size(fields); + if (numfields == -1) + goto cleanup; + } + res = 0; /* if no error occurs, this stays 0 to the end */ + if (PyTuple_GET_SIZE(args) > 0) { + if (numfields != PyTuple_GET_SIZE(args)) { + PyErr_Format(PyExc_TypeError, "%.400s constructor takes %s" + "%zd positional argument%s", + Py_TYPE(self)->tp_name, + numfields == 0 ? "" : "either 0 or ", + numfields, numfields == 1 ? "" : "s"); + res = -1; + goto cleanup; + } + for (i = 0; i < PyTuple_GET_SIZE(args); i++) { + /* cannot be reached when fields is NULL */ + PyObject *name = PySequence_GetItem(fields, i); + if (!name) { + res = -1; + goto cleanup; + } + res = PyObject_SetAttr(self, name, PyTuple_GET_ITEM(args, i)); + Py_DECREF(name); + if (res < 0) + goto cleanup; + } + } + if (kw) { + i = 0; /* needed by PyDict_Next */ + while (PyDict_Next(kw, &i, &key, &value)) { + res = PyObject_SetAttr(self, key, value); + if (res < 0) + goto cleanup; + } + } + cleanup: + Py_XDECREF(fields); + return res; +} + +/* Pickling support */ +static PyObject * +ast_type_reduce(PyObject *self, PyObject *unused) +{ + PyObject *res; + PyObject *dict = PyObject_GetAttrString(self, "__dict__"); + if (dict == NULL) { + if (PyErr_ExceptionMatches(PyExc_AttributeError)) + PyErr_Clear(); + else + return NULL; + } + if (dict) { + res = Py_BuildValue("O()O", Py_TYPE(self), dict); + Py_DECREF(dict); + return res; + } + return Py_BuildValue("O()", Py_TYPE(self)); +} + +static PyMethodDef ast_type_methods[] = { + {"__reduce__", ast_type_reduce, METH_NOARGS, NULL}, + {NULL} +}; + +static PyTypeObject AST_type = { + PyVarObject_HEAD_INIT(&PyType_Type, 0) + "_ast.AST", + sizeof(PyObject), + 0, + 0, /* tp_dealloc */ + 0, /* tp_print */ + 0, /* tp_getattr */ + 0, /* tp_setattr */ + 0, /* tp_compare */ + 0, /* tp_repr */ + 0, /* tp_as_number */ + 0, /* tp_as_sequence */ + 0, /* tp_as_mapping */ + 0, /* tp_hash */ + 0, /* tp_call */ + 0, /* tp_str */ + PyObject_GenericGetAttr, /* tp_getattro */ + PyObject_GenericSetAttr, /* tp_setattro */ + 0, /* tp_as_buffer */ + Py_TPFLAGS_DEFAULT | Py_TPFLAGS_BASETYPE, /* tp_flags */ + 0, /* tp_doc */ + 0, /* tp_traverse */ + 0, /* tp_clear */ + 0, /* tp_richcompare */ + 0, /* tp_weaklistoffset */ + 0, /* tp_iter */ + 0, /* tp_iternext */ + ast_type_methods, /* tp_methods */ + 0, /* tp_members */ + 0, /* tp_getset */ + 0, /* tp_base */ + 0, /* tp_dict */ + 0, /* tp_descr_get */ + 0, /* tp_descr_set */ + 0, /* tp_dictoffset */ + (initproc)ast_type_init, /* tp_init */ + PyType_GenericAlloc, /* tp_alloc */ + PyType_GenericNew, /* tp_new */ + PyObject_Del, /* tp_free */ +}; + + +static PyTypeObject* make_type(char *type, PyTypeObject* base, char**fields, int num_fields) +{ + PyObject *fnames, *result; + int i; + fnames = PyTuple_New(num_fields); + if (!fnames) return NULL; + for (i = 0; i < num_fields; i++) { + PyObject *field = PyString_FromString(fields[i]); + if (!field) { + Py_DECREF(fnames); + return NULL; + } + PyTuple_SET_ITEM(fnames, i, field); + } + result = PyObject_CallFunction((PyObject*)&PyType_Type, "s(O){sOss}", + type, base, "_fields", fnames, "__module__", "_ast"); + Py_DECREF(fnames); + return (PyTypeObject*)result; +} + +static int add_attributes(PyTypeObject* type, char**attrs, int num_fields) +{ + int i, result; + PyObject *s, *l = PyTuple_New(num_fields); + if (!l) + return 0; + for (i = 0; i < num_fields; i++) { + s = PyString_FromString(attrs[i]); + if (!s) { + Py_DECREF(l); + return 0; + } + PyTuple_SET_ITEM(l, i, s); + } + result = PyObject_SetAttrString((PyObject*)type, "_attributes", l) >= 0; + Py_DECREF(l); + return result; +} + +/* Conversion AST -> Python */ + +static PyObject* ast2obj_list(asdl_seq *seq, PyObject* (*func)(void*)) +{ + int i, n = asdl_seq_LEN(seq); + PyObject *result = PyList_New(n); + PyObject *value; + if (!result) + return NULL; + for (i = 0; i < n; i++) { + value = func(asdl_seq_GET(seq, i)); + if (!value) { + Py_DECREF(result); + return NULL; + } + PyList_SET_ITEM(result, i, value); + } + return result; +} + +static PyObject* ast2obj_object(void *o) +{ + if (!o) + o = Py_None; + Py_INCREF((PyObject*)o); + return (PyObject*)o; +} +#define ast2obj_identifier ast2obj_object +#define ast2obj_string ast2obj_object +static PyObject* ast2obj_bool(bool b) +{ + return PyBool_FromLong(b); +} + +static PyObject* ast2obj_int(long b) +{ + return PyInt_FromLong(b); +} + +/* Conversion Python -> AST */ + +static int obj2ast_object(PyObject* obj, PyObject** out, PyArena* arena) +{ + if (obj == Py_None) + obj = NULL; + if (obj) + PyArena_AddPyObject(arena, obj); + Py_XINCREF(obj); + *out = obj; + return 0; +} + +static int obj2ast_identifier(PyObject* obj, PyObject** out, PyArena* arena) +{ + if (!PyString_CheckExact(obj) && obj != Py_None) { + PyErr_Format(PyExc_TypeError, + "AST identifier must be of type str"); + return 1; + } + return obj2ast_object(obj, out, arena); +} + +static int obj2ast_string(PyObject* obj, PyObject** out, PyArena* arena) +{ + if (!PyString_CheckExact(obj) && !PyUnicode_CheckExact(obj)) { + PyErr_SetString(PyExc_TypeError, + "AST string must be of type str or unicode"); + return 1; + } + return obj2ast_object(obj, out, arena); +} + +static int obj2ast_int(PyObject* obj, int* out, PyArena* arena) +{ + int i; + if (!PyInt_Check(obj) && !PyLong_Check(obj)) { + PyObject *s = PyObject_Repr(obj); + if (s == NULL) return 1; + PyErr_Format(PyExc_ValueError, "invalid integer value: %.400s", + PyString_AS_STRING(s)); + Py_DECREF(s); + return 1; + } + + i = (int)PyLong_AsLong(obj); + if (i == -1 && PyErr_Occurred()) + return 1; + *out = i; + return 0; +} + +static int obj2ast_bool(PyObject* obj, bool* out, PyArena* arena) +{ + if (!PyBool_Check(obj)) { + PyObject *s = PyObject_Repr(obj); + if (s == NULL) return 1; + PyErr_Format(PyExc_ValueError, "invalid boolean value: %.400s", + PyString_AS_STRING(s)); + Py_DECREF(s); + return 1; + } + + *out = (obj == Py_True); + return 0; +} + +static int add_ast_fields(void) +{ + PyObject *empty_tuple, *d; + if (PyType_Ready(&AST_type) < 0) + return -1; + d = AST_type.tp_dict; + empty_tuple = PyTuple_New(0); + if (!empty_tuple || + PyDict_SetItemString(d, "_fields", empty_tuple) < 0 || + PyDict_SetItemString(d, "_attributes", empty_tuple) < 0) { + Py_XDECREF(empty_tuple); + return -1; + } + Py_DECREF(empty_tuple); + return 0; +} + + +static int init_types(void) +{ + static int initialized; + if (initialized) return 1; + if (add_ast_fields() < 0) return 0; + mod_type = make_type("mod", &AST_type, NULL, 0); + if (!mod_type) return 0; + if (!add_attributes(mod_type, NULL, 0)) return 0; + Module_type = make_type("Module", mod_type, Module_fields, 1); + if (!Module_type) return 0; + Interactive_type = make_type("Interactive", mod_type, + Interactive_fields, 1); + if (!Interactive_type) return 0; + Expression_type = make_type("Expression", mod_type, Expression_fields, + 1); + if (!Expression_type) return 0; + Suite_type = make_type("Suite", mod_type, Suite_fields, 1); + if (!Suite_type) return 0; + stmt_type = make_type("stmt", &AST_type, NULL, 0); + if (!stmt_type) return 0; + if (!add_attributes(stmt_type, stmt_attributes, 2)) return 0; + FunctionDef_type = make_type("FunctionDef", stmt_type, + FunctionDef_fields, 4); + if (!FunctionDef_type) return 0; + ClassDef_type = make_type("ClassDef", stmt_type, ClassDef_fields, 4); + if (!ClassDef_type) return 0; + Return_type = make_type("Return", stmt_type, Return_fields, 1); + if (!Return_type) return 0; + Delete_type = make_type("Delete", stmt_type, Delete_fields, 1); + if (!Delete_type) return 0; + Assign_type = make_type("Assign", stmt_type, Assign_fields, 2); + if (!Assign_type) return 0; + AugAssign_type = make_type("AugAssign", stmt_type, AugAssign_fields, 3); + if (!AugAssign_type) return 0; + Print_type = make_type("Print", stmt_type, Print_fields, 3); + if (!Print_type) return 0; + For_type = make_type("For", stmt_type, For_fields, 4); + if (!For_type) return 0; + While_type = make_type("While", stmt_type, While_fields, 3); + if (!While_type) return 0; + If_type = make_type("If", stmt_type, If_fields, 3); + if (!If_type) return 0; + With_type = make_type("With", stmt_type, With_fields, 3); + if (!With_type) return 0; + Raise_type = make_type("Raise", stmt_type, Raise_fields, 3); + if (!Raise_type) return 0; + TryExcept_type = make_type("TryExcept", stmt_type, TryExcept_fields, 3); + if (!TryExcept_type) return 0; + TryFinally_type = make_type("TryFinally", stmt_type, TryFinally_fields, + 2); + if (!TryFinally_type) return 0; + Assert_type = make_type("Assert", stmt_type, Assert_fields, 2); + if (!Assert_type) return 0; + Import_type = make_type("Import", stmt_type, Import_fields, 1); + if (!Import_type) return 0; + ImportFrom_type = make_type("ImportFrom", stmt_type, ImportFrom_fields, + 3); + if (!ImportFrom_type) return 0; + Exec_type = make_type("Exec", stmt_type, Exec_fields, 3); + if (!Exec_type) return 0; + Global_type = make_type("Global", stmt_type, Global_fields, 1); + if (!Global_type) return 0; + Expr_type = make_type("Expr", stmt_type, Expr_fields, 1); + if (!Expr_type) return 0; + Pass_type = make_type("Pass", stmt_type, NULL, 0); + if (!Pass_type) return 0; + Break_type = make_type("Break", stmt_type, NULL, 0); + if (!Break_type) return 0; + Continue_type = make_type("Continue", stmt_type, NULL, 0); + if (!Continue_type) return 0; + expr_type = make_type("expr", &AST_type, NULL, 0); + if (!expr_type) return 0; + if (!add_attributes(expr_type, expr_attributes, 2)) return 0; + BoolOp_type = make_type("BoolOp", expr_type, BoolOp_fields, 2); + if (!BoolOp_type) return 0; + BinOp_type = make_type("BinOp", expr_type, BinOp_fields, 3); + if (!BinOp_type) return 0; + UnaryOp_type = make_type("UnaryOp", expr_type, UnaryOp_fields, 2); + if (!UnaryOp_type) return 0; + Lambda_type = make_type("Lambda", expr_type, Lambda_fields, 2); + if (!Lambda_type) return 0; + IfExp_type = make_type("IfExp", expr_type, IfExp_fields, 3); + if (!IfExp_type) return 0; + Dict_type = make_type("Dict", expr_type, Dict_fields, 2); + if (!Dict_type) return 0; + Set_type = make_type("Set", expr_type, Set_fields, 1); + if (!Set_type) return 0; + ListComp_type = make_type("ListComp", expr_type, ListComp_fields, 2); + if (!ListComp_type) return 0; + SetComp_type = make_type("SetComp", expr_type, SetComp_fields, 2); + if (!SetComp_type) return 0; + DictComp_type = make_type("DictComp", expr_type, DictComp_fields, 3); + if (!DictComp_type) return 0; + GeneratorExp_type = make_type("GeneratorExp", expr_type, + GeneratorExp_fields, 2); + if (!GeneratorExp_type) return 0; + Yield_type = make_type("Yield", expr_type, Yield_fields, 1); + if (!Yield_type) return 0; + Compare_type = make_type("Compare", expr_type, Compare_fields, 3); + if (!Compare_type) return 0; + Call_type = make_type("Call", expr_type, Call_fields, 5); + if (!Call_type) return 0; + Repr_type = make_type("Repr", expr_type, Repr_fields, 1); + if (!Repr_type) return 0; + Num_type = make_type("Num", expr_type, Num_fields, 1); + if (!Num_type) return 0; + Str_type = make_type("Str", expr_type, Str_fields, 1); + if (!Str_type) return 0; + Attribute_type = make_type("Attribute", expr_type, Attribute_fields, 3); + if (!Attribute_type) return 0; + Subscript_type = make_type("Subscript", expr_type, Subscript_fields, 3); + if (!Subscript_type) return 0; + Name_type = make_type("Name", expr_type, Name_fields, 2); + if (!Name_type) return 0; + List_type = make_type("List", expr_type, List_fields, 2); + if (!List_type) return 0; + Tuple_type = make_type("Tuple", expr_type, Tuple_fields, 2); + if (!Tuple_type) return 0; + expr_context_type = make_type("expr_context", &AST_type, NULL, 0); + if (!expr_context_type) return 0; + if (!add_attributes(expr_context_type, NULL, 0)) return 0; + Load_type = make_type("Load", expr_context_type, NULL, 0); + if (!Load_type) return 0; + Load_singleton = PyType_GenericNew(Load_type, NULL, NULL); + if (!Load_singleton) return 0; + Store_type = make_type("Store", expr_context_type, NULL, 0); + if (!Store_type) return 0; + Store_singleton = PyType_GenericNew(Store_type, NULL, NULL); + if (!Store_singleton) return 0; + Del_type = make_type("Del", expr_context_type, NULL, 0); + if (!Del_type) return 0; + Del_singleton = PyType_GenericNew(Del_type, NULL, NULL); + if (!Del_singleton) return 0; + AugLoad_type = make_type("AugLoad", expr_context_type, NULL, 0); + if (!AugLoad_type) return 0; + AugLoad_singleton = PyType_GenericNew(AugLoad_type, NULL, NULL); + if (!AugLoad_singleton) return 0; + AugStore_type = make_type("AugStore", expr_context_type, NULL, 0); + if (!AugStore_type) return 0; + AugStore_singleton = PyType_GenericNew(AugStore_type, NULL, NULL); + if (!AugStore_singleton) return 0; + Param_type = make_type("Param", expr_context_type, NULL, 0); + if (!Param_type) return 0; + Param_singleton = PyType_GenericNew(Param_type, NULL, NULL); + if (!Param_singleton) return 0; + slice_type = make_type("slice", &AST_type, NULL, 0); + if (!slice_type) return 0; + if (!add_attributes(slice_type, NULL, 0)) return 0; + Ellipsis_type = make_type("Ellipsis", slice_type, NULL, 0); + if (!Ellipsis_type) return 0; + Slice_type = make_type("Slice", slice_type, Slice_fields, 3); + if (!Slice_type) return 0; + ExtSlice_type = make_type("ExtSlice", slice_type, ExtSlice_fields, 1); + if (!ExtSlice_type) return 0; + Index_type = make_type("Index", slice_type, Index_fields, 1); + if (!Index_type) return 0; + boolop_type = make_type("boolop", &AST_type, NULL, 0); + if (!boolop_type) return 0; + if (!add_attributes(boolop_type, NULL, 0)) return 0; + And_type = make_type("And", boolop_type, NULL, 0); + if (!And_type) return 0; + And_singleton = PyType_GenericNew(And_type, NULL, NULL); + if (!And_singleton) return 0; + Or_type = make_type("Or", boolop_type, NULL, 0); + if (!Or_type) return 0; + Or_singleton = PyType_GenericNew(Or_type, NULL, NULL); + if (!Or_singleton) return 0; + operator_type = make_type("operator", &AST_type, NULL, 0); + if (!operator_type) return 0; + if (!add_attributes(operator_type, NULL, 0)) return 0; + Add_type = make_type("Add", operator_type, NULL, 0); + if (!Add_type) return 0; + Add_singleton = PyType_GenericNew(Add_type, NULL, NULL); + if (!Add_singleton) return 0; + Sub_type = make_type("Sub", operator_type, NULL, 0); + if (!Sub_type) return 0; + Sub_singleton = PyType_GenericNew(Sub_type, NULL, NULL); + if (!Sub_singleton) return 0; + Mult_type = make_type("Mult", operator_type, NULL, 0); + if (!Mult_type) return 0; + Mult_singleton = PyType_GenericNew(Mult_type, NULL, NULL); + if (!Mult_singleton) return 0; + Div_type = make_type("Div", operator_type, NULL, 0); + if (!Div_type) return 0; + Div_singleton = PyType_GenericNew(Div_type, NULL, NULL); + if (!Div_singleton) return 0; + Mod_type = make_type("Mod", operator_type, NULL, 0); + if (!Mod_type) return 0; + Mod_singleton = PyType_GenericNew(Mod_type, NULL, NULL); + if (!Mod_singleton) return 0; + Pow_type = make_type("Pow", operator_type, NULL, 0); + if (!Pow_type) return 0; + Pow_singleton = PyType_GenericNew(Pow_type, NULL, NULL); + if (!Pow_singleton) return 0; + LShift_type = make_type("LShift", operator_type, NULL, 0); + if (!LShift_type) return 0; + LShift_singleton = PyType_GenericNew(LShift_type, NULL, NULL); + if (!LShift_singleton) return 0; + RShift_type = make_type("RShift", operator_type, NULL, 0); + if (!RShift_type) return 0; + RShift_singleton = PyType_GenericNew(RShift_type, NULL, NULL); + if (!RShift_singleton) return 0; + BitOr_type = make_type("BitOr", operator_type, NULL, 0); + if (!BitOr_type) return 0; + BitOr_singleton = PyType_GenericNew(BitOr_type, NULL, NULL); + if (!BitOr_singleton) return 0; + BitXor_type = make_type("BitXor", operator_type, NULL, 0); + if (!BitXor_type) return 0; + BitXor_singleton = PyType_GenericNew(BitXor_type, NULL, NULL); + if (!BitXor_singleton) return 0; + BitAnd_type = make_type("BitAnd", operator_type, NULL, 0); + if (!BitAnd_type) return 0; + BitAnd_singleton = PyType_GenericNew(BitAnd_type, NULL, NULL); + if (!BitAnd_singleton) return 0; + FloorDiv_type = make_type("FloorDiv", operator_type, NULL, 0); + if (!FloorDiv_type) return 0; + FloorDiv_singleton = PyType_GenericNew(FloorDiv_type, NULL, NULL); + if (!FloorDiv_singleton) return 0; + unaryop_type = make_type("unaryop", &AST_type, NULL, 0); + if (!unaryop_type) return 0; + if (!add_attributes(unaryop_type, NULL, 0)) return 0; + Invert_type = make_type("Invert", unaryop_type, NULL, 0); + if (!Invert_type) return 0; + Invert_singleton = PyType_GenericNew(Invert_type, NULL, NULL); + if (!Invert_singleton) return 0; + Not_type = make_type("Not", unaryop_type, NULL, 0); + if (!Not_type) return 0; + Not_singleton = PyType_GenericNew(Not_type, NULL, NULL); + if (!Not_singleton) return 0; + UAdd_type = make_type("UAdd", unaryop_type, NULL, 0); + if (!UAdd_type) return 0; + UAdd_singleton = PyType_GenericNew(UAdd_type, NULL, NULL); + if (!UAdd_singleton) return 0; + USub_type = make_type("USub", unaryop_type, NULL, 0); + if (!USub_type) return 0; + USub_singleton = PyType_GenericNew(USub_type, NULL, NULL); + if (!USub_singleton) return 0; + cmpop_type = make_type("cmpop", &AST_type, NULL, 0); + if (!cmpop_type) return 0; + if (!add_attributes(cmpop_type, NULL, 0)) return 0; + Eq_type = make_type("Eq", cmpop_type, NULL, 0); + if (!Eq_type) return 0; + Eq_singleton = PyType_GenericNew(Eq_type, NULL, NULL); + if (!Eq_singleton) return 0; + NotEq_type = make_type("NotEq", cmpop_type, NULL, 0); + if (!NotEq_type) return 0; + NotEq_singleton = PyType_GenericNew(NotEq_type, NULL, NULL); + if (!NotEq_singleton) return 0; + Lt_type = make_type("Lt", cmpop_type, NULL, 0); + if (!Lt_type) return 0; + Lt_singleton = PyType_GenericNew(Lt_type, NULL, NULL); + if (!Lt_singleton) return 0; + LtE_type = make_type("LtE", cmpop_type, NULL, 0); + if (!LtE_type) return 0; + LtE_singleton = PyType_GenericNew(LtE_type, NULL, NULL); + if (!LtE_singleton) return 0; + Gt_type = make_type("Gt", cmpop_type, NULL, 0); + if (!Gt_type) return 0; + Gt_singleton = PyType_GenericNew(Gt_type, NULL, NULL); + if (!Gt_singleton) return 0; + GtE_type = make_type("GtE", cmpop_type, NULL, 0); + if (!GtE_type) return 0; + GtE_singleton = PyType_GenericNew(GtE_type, NULL, NULL); + if (!GtE_singleton) return 0; + Is_type = make_type("Is", cmpop_type, NULL, 0); + if (!Is_type) return 0; + Is_singleton = PyType_GenericNew(Is_type, NULL, NULL); + if (!Is_singleton) return 0; + IsNot_type = make_type("IsNot", cmpop_type, NULL, 0); + if (!IsNot_type) return 0; + IsNot_singleton = PyType_GenericNew(IsNot_type, NULL, NULL); + if (!IsNot_singleton) return 0; + In_type = make_type("In", cmpop_type, NULL, 0); + if (!In_type) return 0; + In_singleton = PyType_GenericNew(In_type, NULL, NULL); + if (!In_singleton) return 0; + NotIn_type = make_type("NotIn", cmpop_type, NULL, 0); + if (!NotIn_type) return 0; + NotIn_singleton = PyType_GenericNew(NotIn_type, NULL, NULL); + if (!NotIn_singleton) return 0; + comprehension_type = make_type("comprehension", &AST_type, + comprehension_fields, 3); + if (!comprehension_type) return 0; + excepthandler_type = make_type("excepthandler", &AST_type, NULL, 0); + if (!excepthandler_type) return 0; + if (!add_attributes(excepthandler_type, excepthandler_attributes, 2)) + return 0; + ExceptHandler_type = make_type("ExceptHandler", excepthandler_type, + ExceptHandler_fields, 3); + if (!ExceptHandler_type) return 0; + arguments_type = make_type("arguments", &AST_type, arguments_fields, 4); + if (!arguments_type) return 0; + keyword_type = make_type("keyword", &AST_type, keyword_fields, 2); + if (!keyword_type) return 0; + alias_type = make_type("alias", &AST_type, alias_fields, 2); + if (!alias_type) return 0; + initialized = 1; + return 1; +} + +static int obj2ast_mod(PyObject* obj, mod_ty* out, PyArena* arena); +static int obj2ast_stmt(PyObject* obj, stmt_ty* out, PyArena* arena); +static int obj2ast_expr(PyObject* obj, expr_ty* out, PyArena* arena); +static int obj2ast_expr_context(PyObject* obj, expr_context_ty* out, PyArena* + arena); +static int obj2ast_slice(PyObject* obj, slice_ty* out, PyArena* arena); +static int obj2ast_boolop(PyObject* obj, boolop_ty* out, PyArena* arena); +static int obj2ast_operator(PyObject* obj, operator_ty* out, PyArena* arena); +static int obj2ast_unaryop(PyObject* obj, unaryop_ty* out, PyArena* arena); +static int obj2ast_cmpop(PyObject* obj, cmpop_ty* out, PyArena* arena); +static int obj2ast_comprehension(PyObject* obj, comprehension_ty* out, PyArena* + arena); +static int obj2ast_excepthandler(PyObject* obj, excepthandler_ty* out, PyArena* + arena); +static int obj2ast_arguments(PyObject* obj, arguments_ty* out, PyArena* arena); +static int obj2ast_keyword(PyObject* obj, keyword_ty* out, PyArena* arena); +static int obj2ast_alias(PyObject* obj, alias_ty* out, PyArena* arena); + +mod_ty +Module(asdl_seq * body, PyArena *arena) +{ + mod_ty p; + p = (mod_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Module_kind; + p->v.Module.body = body; + return p; +} + +mod_ty +Interactive(asdl_seq * body, PyArena *arena) +{ + mod_ty p; + p = (mod_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Interactive_kind; + p->v.Interactive.body = body; + return p; +} + +mod_ty +Expression(expr_ty body, PyArena *arena) +{ + mod_ty p; + if (!body) { + PyErr_SetString(PyExc_ValueError, + "field body is required for Expression"); + return NULL; + } + p = (mod_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Expression_kind; + p->v.Expression.body = body; + return p; +} + +mod_ty +Suite(asdl_seq * body, PyArena *arena) +{ + mod_ty p; + p = (mod_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Suite_kind; + p->v.Suite.body = body; + return p; +} + +stmt_ty +FunctionDef(identifier name, arguments_ty args, asdl_seq * body, asdl_seq * + decorator_list, int lineno, int col_offset, PyArena *arena) +{ + stmt_ty p; + if (!name) { + PyErr_SetString(PyExc_ValueError, + "field name is required for FunctionDef"); + return NULL; + } + if (!args) { + PyErr_SetString(PyExc_ValueError, + "field args is required for FunctionDef"); + return NULL; + } + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = FunctionDef_kind; + p->v.FunctionDef.name = name; + p->v.FunctionDef.args = args; + p->v.FunctionDef.body = body; + p->v.FunctionDef.decorator_list = decorator_list; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +ClassDef(identifier name, asdl_seq * bases, asdl_seq * body, asdl_seq * + decorator_list, int lineno, int col_offset, PyArena *arena) +{ + stmt_ty p; + if (!name) { + PyErr_SetString(PyExc_ValueError, + "field name is required for ClassDef"); + return NULL; + } + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = ClassDef_kind; + p->v.ClassDef.name = name; + p->v.ClassDef.bases = bases; + p->v.ClassDef.body = body; + p->v.ClassDef.decorator_list = decorator_list; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +Return(expr_ty value, int lineno, int col_offset, PyArena *arena) +{ + stmt_ty p; + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Return_kind; + p->v.Return.value = value; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +Delete(asdl_seq * targets, int lineno, int col_offset, PyArena *arena) +{ + stmt_ty p; + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Delete_kind; + p->v.Delete.targets = targets; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +Assign(asdl_seq * targets, expr_ty value, int lineno, int col_offset, PyArena + *arena) +{ + stmt_ty p; + if (!value) { + PyErr_SetString(PyExc_ValueError, + "field value is required for Assign"); + return NULL; + } + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Assign_kind; + p->v.Assign.targets = targets; + p->v.Assign.value = value; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +AugAssign(expr_ty target, operator_ty op, expr_ty value, int lineno, int + col_offset, PyArena *arena) +{ + stmt_ty p; + if (!target) { + PyErr_SetString(PyExc_ValueError, + "field target is required for AugAssign"); + return NULL; + } + if (!op) { + PyErr_SetString(PyExc_ValueError, + "field op is required for AugAssign"); + return NULL; + } + if (!value) { + PyErr_SetString(PyExc_ValueError, + "field value is required for AugAssign"); + return NULL; + } + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = AugAssign_kind; + p->v.AugAssign.target = target; + p->v.AugAssign.op = op; + p->v.AugAssign.value = value; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +Print(expr_ty dest, asdl_seq * values, bool nl, int lineno, int col_offset, + PyArena *arena) +{ + stmt_ty p; + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Print_kind; + p->v.Print.dest = dest; + p->v.Print.values = values; + p->v.Print.nl = nl; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +For(expr_ty target, expr_ty iter, asdl_seq * body, asdl_seq * orelse, int + lineno, int col_offset, PyArena *arena) +{ + stmt_ty p; + if (!target) { + PyErr_SetString(PyExc_ValueError, + "field target is required for For"); + return NULL; + } + if (!iter) { + PyErr_SetString(PyExc_ValueError, + "field iter is required for For"); + return NULL; + } + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = For_kind; + p->v.For.target = target; + p->v.For.iter = iter; + p->v.For.body = body; + p->v.For.orelse = orelse; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +While(expr_ty test, asdl_seq * body, asdl_seq * orelse, int lineno, int + col_offset, PyArena *arena) +{ + stmt_ty p; + if (!test) { + PyErr_SetString(PyExc_ValueError, + "field test is required for While"); + return NULL; + } + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = While_kind; + p->v.While.test = test; + p->v.While.body = body; + p->v.While.orelse = orelse; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +If(expr_ty test, asdl_seq * body, asdl_seq * orelse, int lineno, int + col_offset, PyArena *arena) +{ + stmt_ty p; + if (!test) { + PyErr_SetString(PyExc_ValueError, + "field test is required for If"); + return NULL; + } + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = If_kind; + p->v.If.test = test; + p->v.If.body = body; + p->v.If.orelse = orelse; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +With(expr_ty context_expr, expr_ty optional_vars, asdl_seq * body, int lineno, + int col_offset, PyArena *arena) +{ + stmt_ty p; + if (!context_expr) { + PyErr_SetString(PyExc_ValueError, + "field context_expr is required for With"); + return NULL; + } + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = With_kind; + p->v.With.context_expr = context_expr; + p->v.With.optional_vars = optional_vars; + p->v.With.body = body; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +Raise(expr_ty type, expr_ty inst, expr_ty tback, int lineno, int col_offset, + PyArena *arena) +{ + stmt_ty p; + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Raise_kind; + p->v.Raise.type = type; + p->v.Raise.inst = inst; + p->v.Raise.tback = tback; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +TryExcept(asdl_seq * body, asdl_seq * handlers, asdl_seq * orelse, int lineno, + int col_offset, PyArena *arena) +{ + stmt_ty p; + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = TryExcept_kind; + p->v.TryExcept.body = body; + p->v.TryExcept.handlers = handlers; + p->v.TryExcept.orelse = orelse; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +TryFinally(asdl_seq * body, asdl_seq * finalbody, int lineno, int col_offset, + PyArena *arena) +{ + stmt_ty p; + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = TryFinally_kind; + p->v.TryFinally.body = body; + p->v.TryFinally.finalbody = finalbody; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +Assert(expr_ty test, expr_ty msg, int lineno, int col_offset, PyArena *arena) +{ + stmt_ty p; + if (!test) { + PyErr_SetString(PyExc_ValueError, + "field test is required for Assert"); + return NULL; + } + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Assert_kind; + p->v.Assert.test = test; + p->v.Assert.msg = msg; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +Import(asdl_seq * names, int lineno, int col_offset, PyArena *arena) +{ + stmt_ty p; + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Import_kind; + p->v.Import.names = names; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +ImportFrom(identifier module, asdl_seq * names, int level, int lineno, int + col_offset, PyArena *arena) +{ + stmt_ty p; + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = ImportFrom_kind; + p->v.ImportFrom.module = module; + p->v.ImportFrom.names = names; + p->v.ImportFrom.level = level; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +Exec(expr_ty body, expr_ty globals, expr_ty locals, int lineno, int col_offset, + PyArena *arena) +{ + stmt_ty p; + if (!body) { + PyErr_SetString(PyExc_ValueError, + "field body is required for Exec"); + return NULL; + } + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Exec_kind; + p->v.Exec.body = body; + p->v.Exec.globals = globals; + p->v.Exec.locals = locals; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +Global(asdl_seq * names, int lineno, int col_offset, PyArena *arena) +{ + stmt_ty p; + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Global_kind; + p->v.Global.names = names; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +Expr(expr_ty value, int lineno, int col_offset, PyArena *arena) +{ + stmt_ty p; + if (!value) { + PyErr_SetString(PyExc_ValueError, + "field value is required for Expr"); + return NULL; + } + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Expr_kind; + p->v.Expr.value = value; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +Pass(int lineno, int col_offset, PyArena *arena) +{ + stmt_ty p; + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Pass_kind; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +Break(int lineno, int col_offset, PyArena *arena) +{ + stmt_ty p; + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Break_kind; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +stmt_ty +Continue(int lineno, int col_offset, PyArena *arena) +{ + stmt_ty p; + p = (stmt_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Continue_kind; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +BoolOp(boolop_ty op, asdl_seq * values, int lineno, int col_offset, PyArena + *arena) +{ + expr_ty p; + if (!op) { + PyErr_SetString(PyExc_ValueError, + "field op is required for BoolOp"); + return NULL; + } + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = BoolOp_kind; + p->v.BoolOp.op = op; + p->v.BoolOp.values = values; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +BinOp(expr_ty left, operator_ty op, expr_ty right, int lineno, int col_offset, + PyArena *arena) +{ + expr_ty p; + if (!left) { + PyErr_SetString(PyExc_ValueError, + "field left is required for BinOp"); + return NULL; + } + if (!op) { + PyErr_SetString(PyExc_ValueError, + "field op is required for BinOp"); + return NULL; + } + if (!right) { + PyErr_SetString(PyExc_ValueError, + "field right is required for BinOp"); + return NULL; + } + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = BinOp_kind; + p->v.BinOp.left = left; + p->v.BinOp.op = op; + p->v.BinOp.right = right; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +UnaryOp(unaryop_ty op, expr_ty operand, int lineno, int col_offset, PyArena + *arena) +{ + expr_ty p; + if (!op) { + PyErr_SetString(PyExc_ValueError, + "field op is required for UnaryOp"); + return NULL; + } + if (!operand) { + PyErr_SetString(PyExc_ValueError, + "field operand is required for UnaryOp"); + return NULL; + } + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = UnaryOp_kind; + p->v.UnaryOp.op = op; + p->v.UnaryOp.operand = operand; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +Lambda(arguments_ty args, expr_ty body, int lineno, int col_offset, PyArena + *arena) +{ + expr_ty p; + if (!args) { + PyErr_SetString(PyExc_ValueError, + "field args is required for Lambda"); + return NULL; + } + if (!body) { + PyErr_SetString(PyExc_ValueError, + "field body is required for Lambda"); + return NULL; + } + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Lambda_kind; + p->v.Lambda.args = args; + p->v.Lambda.body = body; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +IfExp(expr_ty test, expr_ty body, expr_ty orelse, int lineno, int col_offset, + PyArena *arena) +{ + expr_ty p; + if (!test) { + PyErr_SetString(PyExc_ValueError, + "field test is required for IfExp"); + return NULL; + } + if (!body) { + PyErr_SetString(PyExc_ValueError, + "field body is required for IfExp"); + return NULL; + } + if (!orelse) { + PyErr_SetString(PyExc_ValueError, + "field orelse is required for IfExp"); + return NULL; + } + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = IfExp_kind; + p->v.IfExp.test = test; + p->v.IfExp.body = body; + p->v.IfExp.orelse = orelse; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +Dict(asdl_seq * keys, asdl_seq * values, int lineno, int col_offset, PyArena + *arena) +{ + expr_ty p; + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Dict_kind; + p->v.Dict.keys = keys; + p->v.Dict.values = values; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +Set(asdl_seq * elts, int lineno, int col_offset, PyArena *arena) +{ + expr_ty p; + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Set_kind; + p->v.Set.elts = elts; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +ListComp(expr_ty elt, asdl_seq * generators, int lineno, int col_offset, + PyArena *arena) +{ + expr_ty p; + if (!elt) { + PyErr_SetString(PyExc_ValueError, + "field elt is required for ListComp"); + return NULL; + } + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = ListComp_kind; + p->v.ListComp.elt = elt; + p->v.ListComp.generators = generators; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +SetComp(expr_ty elt, asdl_seq * generators, int lineno, int col_offset, PyArena + *arena) +{ + expr_ty p; + if (!elt) { + PyErr_SetString(PyExc_ValueError, + "field elt is required for SetComp"); + return NULL; + } + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = SetComp_kind; + p->v.SetComp.elt = elt; + p->v.SetComp.generators = generators; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +DictComp(expr_ty key, expr_ty value, asdl_seq * generators, int lineno, int + col_offset, PyArena *arena) +{ + expr_ty p; + if (!key) { + PyErr_SetString(PyExc_ValueError, + "field key is required for DictComp"); + return NULL; + } + if (!value) { + PyErr_SetString(PyExc_ValueError, + "field value is required for DictComp"); + return NULL; + } + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = DictComp_kind; + p->v.DictComp.key = key; + p->v.DictComp.value = value; + p->v.DictComp.generators = generators; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +GeneratorExp(expr_ty elt, asdl_seq * generators, int lineno, int col_offset, + PyArena *arena) +{ + expr_ty p; + if (!elt) { + PyErr_SetString(PyExc_ValueError, + "field elt is required for GeneratorExp"); + return NULL; + } + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = GeneratorExp_kind; + p->v.GeneratorExp.elt = elt; + p->v.GeneratorExp.generators = generators; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +Yield(expr_ty value, int lineno, int col_offset, PyArena *arena) +{ + expr_ty p; + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Yield_kind; + p->v.Yield.value = value; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +Compare(expr_ty left, asdl_int_seq * ops, asdl_seq * comparators, int lineno, + int col_offset, PyArena *arena) +{ + expr_ty p; + if (!left) { + PyErr_SetString(PyExc_ValueError, + "field left is required for Compare"); + return NULL; + } + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Compare_kind; + p->v.Compare.left = left; + p->v.Compare.ops = ops; + p->v.Compare.comparators = comparators; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +Call(expr_ty func, asdl_seq * args, asdl_seq * keywords, expr_ty starargs, + expr_ty kwargs, int lineno, int col_offset, PyArena *arena) +{ + expr_ty p; + if (!func) { + PyErr_SetString(PyExc_ValueError, + "field func is required for Call"); + return NULL; + } + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Call_kind; + p->v.Call.func = func; + p->v.Call.args = args; + p->v.Call.keywords = keywords; + p->v.Call.starargs = starargs; + p->v.Call.kwargs = kwargs; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +Repr(expr_ty value, int lineno, int col_offset, PyArena *arena) +{ + expr_ty p; + if (!value) { + PyErr_SetString(PyExc_ValueError, + "field value is required for Repr"); + return NULL; + } + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Repr_kind; + p->v.Repr.value = value; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +Num(object n, int lineno, int col_offset, PyArena *arena) +{ + expr_ty p; + if (!n) { + PyErr_SetString(PyExc_ValueError, + "field n is required for Num"); + return NULL; + } + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Num_kind; + p->v.Num.n = n; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +Str(string s, int lineno, int col_offset, PyArena *arena) +{ + expr_ty p; + if (!s) { + PyErr_SetString(PyExc_ValueError, + "field s is required for Str"); + return NULL; + } + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Str_kind; + p->v.Str.s = s; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +Attribute(expr_ty value, identifier attr, expr_context_ty ctx, int lineno, int + col_offset, PyArena *arena) +{ + expr_ty p; + if (!value) { + PyErr_SetString(PyExc_ValueError, + "field value is required for Attribute"); + return NULL; + } + if (!attr) { + PyErr_SetString(PyExc_ValueError, + "field attr is required for Attribute"); + return NULL; + } + if (!ctx) { + PyErr_SetString(PyExc_ValueError, + "field ctx is required for Attribute"); + return NULL; + } + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Attribute_kind; + p->v.Attribute.value = value; + p->v.Attribute.attr = attr; + p->v.Attribute.ctx = ctx; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +Subscript(expr_ty value, slice_ty slice, expr_context_ty ctx, int lineno, int + col_offset, PyArena *arena) +{ + expr_ty p; + if (!value) { + PyErr_SetString(PyExc_ValueError, + "field value is required for Subscript"); + return NULL; + } + if (!slice) { + PyErr_SetString(PyExc_ValueError, + "field slice is required for Subscript"); + return NULL; + } + if (!ctx) { + PyErr_SetString(PyExc_ValueError, + "field ctx is required for Subscript"); + return NULL; + } + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Subscript_kind; + p->v.Subscript.value = value; + p->v.Subscript.slice = slice; + p->v.Subscript.ctx = ctx; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +Name(identifier id, expr_context_ty ctx, int lineno, int col_offset, PyArena + *arena) +{ + expr_ty p; + if (!id) { + PyErr_SetString(PyExc_ValueError, + "field id is required for Name"); + return NULL; + } + if (!ctx) { + PyErr_SetString(PyExc_ValueError, + "field ctx is required for Name"); + return NULL; + } + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Name_kind; + p->v.Name.id = id; + p->v.Name.ctx = ctx; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +List(asdl_seq * elts, expr_context_ty ctx, int lineno, int col_offset, PyArena + *arena) +{ + expr_ty p; + if (!ctx) { + PyErr_SetString(PyExc_ValueError, + "field ctx is required for List"); + return NULL; + } + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = List_kind; + p->v.List.elts = elts; + p->v.List.ctx = ctx; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +expr_ty +Tuple(asdl_seq * elts, expr_context_ty ctx, int lineno, int col_offset, PyArena + *arena) +{ + expr_ty p; + if (!ctx) { + PyErr_SetString(PyExc_ValueError, + "field ctx is required for Tuple"); + return NULL; + } + p = (expr_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Tuple_kind; + p->v.Tuple.elts = elts; + p->v.Tuple.ctx = ctx; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +slice_ty +Ellipsis(PyArena *arena) +{ + slice_ty p; + p = (slice_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Ellipsis_kind; + return p; +} + +slice_ty +Slice(expr_ty lower, expr_ty upper, expr_ty step, PyArena *arena) +{ + slice_ty p; + p = (slice_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Slice_kind; + p->v.Slice.lower = lower; + p->v.Slice.upper = upper; + p->v.Slice.step = step; + return p; +} + +slice_ty +ExtSlice(asdl_seq * dims, PyArena *arena) +{ + slice_ty p; + p = (slice_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = ExtSlice_kind; + p->v.ExtSlice.dims = dims; + return p; +} + +slice_ty +Index(expr_ty value, PyArena *arena) +{ + slice_ty p; + if (!value) { + PyErr_SetString(PyExc_ValueError, + "field value is required for Index"); + return NULL; + } + p = (slice_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = Index_kind; + p->v.Index.value = value; + return p; +} + +comprehension_ty +comprehension(expr_ty target, expr_ty iter, asdl_seq * ifs, PyArena *arena) +{ + comprehension_ty p; + if (!target) { + PyErr_SetString(PyExc_ValueError, + "field target is required for comprehension"); + return NULL; + } + if (!iter) { + PyErr_SetString(PyExc_ValueError, + "field iter is required for comprehension"); + return NULL; + } + p = (comprehension_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->target = target; + p->iter = iter; + p->ifs = ifs; + return p; +} + +excepthandler_ty +ExceptHandler(expr_ty type, expr_ty name, asdl_seq * body, int lineno, int + col_offset, PyArena *arena) +{ + excepthandler_ty p; + p = (excepthandler_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->kind = ExceptHandler_kind; + p->v.ExceptHandler.type = type; + p->v.ExceptHandler.name = name; + p->v.ExceptHandler.body = body; + p->lineno = lineno; + p->col_offset = col_offset; + return p; +} + +arguments_ty +arguments(asdl_seq * args, identifier vararg, identifier kwarg, asdl_seq * + defaults, PyArena *arena) +{ + arguments_ty p; + p = (arguments_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->args = args; + p->vararg = vararg; + p->kwarg = kwarg; + p->defaults = defaults; + return p; +} + +keyword_ty +keyword(identifier arg, expr_ty value, PyArena *arena) +{ + keyword_ty p; + if (!arg) { + PyErr_SetString(PyExc_ValueError, + "field arg is required for keyword"); + return NULL; + } + if (!value) { + PyErr_SetString(PyExc_ValueError, + "field value is required for keyword"); + return NULL; + } + p = (keyword_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->arg = arg; + p->value = value; + return p; +} + +alias_ty +alias(identifier name, identifier asname, PyArena *arena) +{ + alias_ty p; + if (!name) { + PyErr_SetString(PyExc_ValueError, + "field name is required for alias"); + return NULL; + } + p = (alias_ty)PyArena_Malloc(arena, sizeof(*p)); + if (!p) + return NULL; + p->name = name; + p->asname = asname; + return p; +} + + +PyObject* +ast2obj_mod(void* _o) +{ + mod_ty o = (mod_ty)_o; + PyObject *result = NULL, *value = NULL; + if (!o) { + Py_INCREF(Py_None); + return Py_None; + } + + switch (o->kind) { + case Module_kind: + result = PyType_GenericNew(Module_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_list(o->v.Module.body, ast2obj_stmt); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "body", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Interactive_kind: + result = PyType_GenericNew(Interactive_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_list(o->v.Interactive.body, ast2obj_stmt); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "body", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Expression_kind: + result = PyType_GenericNew(Expression_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.Expression.body); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "body", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Suite_kind: + result = PyType_GenericNew(Suite_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_list(o->v.Suite.body, ast2obj_stmt); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "body", value) == -1) + goto failed; + Py_DECREF(value); + break; + } + return result; +failed: + Py_XDECREF(value); + Py_XDECREF(result); + return NULL; +} + +PyObject* +ast2obj_stmt(void* _o) +{ + stmt_ty o = (stmt_ty)_o; + PyObject *result = NULL, *value = NULL; + if (!o) { + Py_INCREF(Py_None); + return Py_None; + } + + switch (o->kind) { + case FunctionDef_kind: + result = PyType_GenericNew(FunctionDef_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_identifier(o->v.FunctionDef.name); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "name", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_arguments(o->v.FunctionDef.args); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "args", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.FunctionDef.body, ast2obj_stmt); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "body", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.FunctionDef.decorator_list, + ast2obj_expr); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "decorator_list", value) == + -1) + goto failed; + Py_DECREF(value); + break; + case ClassDef_kind: + result = PyType_GenericNew(ClassDef_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_identifier(o->v.ClassDef.name); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "name", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.ClassDef.bases, ast2obj_expr); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "bases", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.ClassDef.body, ast2obj_stmt); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "body", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.ClassDef.decorator_list, + ast2obj_expr); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "decorator_list", value) == + -1) + goto failed; + Py_DECREF(value); + break; + case Return_kind: + result = PyType_GenericNew(Return_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.Return.value); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "value", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Delete_kind: + result = PyType_GenericNew(Delete_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_list(o->v.Delete.targets, ast2obj_expr); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "targets", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Assign_kind: + result = PyType_GenericNew(Assign_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_list(o->v.Assign.targets, ast2obj_expr); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "targets", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->v.Assign.value); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "value", value) == -1) + goto failed; + Py_DECREF(value); + break; + case AugAssign_kind: + result = PyType_GenericNew(AugAssign_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.AugAssign.target); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "target", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_operator(o->v.AugAssign.op); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "op", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->v.AugAssign.value); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "value", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Print_kind: + result = PyType_GenericNew(Print_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.Print.dest); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "dest", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.Print.values, ast2obj_expr); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "values", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_bool(o->v.Print.nl); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "nl", value) == -1) + goto failed; + Py_DECREF(value); + break; + case For_kind: + result = PyType_GenericNew(For_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.For.target); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "target", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->v.For.iter); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "iter", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.For.body, ast2obj_stmt); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "body", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.For.orelse, ast2obj_stmt); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "orelse", value) == -1) + goto failed; + Py_DECREF(value); + break; + case While_kind: + result = PyType_GenericNew(While_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.While.test); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "test", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.While.body, ast2obj_stmt); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "body", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.While.orelse, ast2obj_stmt); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "orelse", value) == -1) + goto failed; + Py_DECREF(value); + break; + case If_kind: + result = PyType_GenericNew(If_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.If.test); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "test", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.If.body, ast2obj_stmt); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "body", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.If.orelse, ast2obj_stmt); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "orelse", value) == -1) + goto failed; + Py_DECREF(value); + break; + case With_kind: + result = PyType_GenericNew(With_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.With.context_expr); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "context_expr", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->v.With.optional_vars); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "optional_vars", value) == + -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.With.body, ast2obj_stmt); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "body", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Raise_kind: + result = PyType_GenericNew(Raise_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.Raise.type); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "type", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->v.Raise.inst); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "inst", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->v.Raise.tback); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "tback", value) == -1) + goto failed; + Py_DECREF(value); + break; + case TryExcept_kind: + result = PyType_GenericNew(TryExcept_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_list(o->v.TryExcept.body, ast2obj_stmt); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "body", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.TryExcept.handlers, + ast2obj_excepthandler); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "handlers", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.TryExcept.orelse, ast2obj_stmt); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "orelse", value) == -1) + goto failed; + Py_DECREF(value); + break; + case TryFinally_kind: + result = PyType_GenericNew(TryFinally_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_list(o->v.TryFinally.body, ast2obj_stmt); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "body", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.TryFinally.finalbody, ast2obj_stmt); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "finalbody", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Assert_kind: + result = PyType_GenericNew(Assert_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.Assert.test); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "test", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->v.Assert.msg); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "msg", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Import_kind: + result = PyType_GenericNew(Import_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_list(o->v.Import.names, ast2obj_alias); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "names", value) == -1) + goto failed; + Py_DECREF(value); + break; + case ImportFrom_kind: + result = PyType_GenericNew(ImportFrom_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_identifier(o->v.ImportFrom.module); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "module", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.ImportFrom.names, ast2obj_alias); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "names", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_int(o->v.ImportFrom.level); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "level", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Exec_kind: + result = PyType_GenericNew(Exec_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.Exec.body); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "body", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->v.Exec.globals); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "globals", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->v.Exec.locals); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "locals", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Global_kind: + result = PyType_GenericNew(Global_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_list(o->v.Global.names, ast2obj_identifier); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "names", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Expr_kind: + result = PyType_GenericNew(Expr_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.Expr.value); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "value", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Pass_kind: + result = PyType_GenericNew(Pass_type, NULL, NULL); + if (!result) goto failed; + break; + case Break_kind: + result = PyType_GenericNew(Break_type, NULL, NULL); + if (!result) goto failed; + break; + case Continue_kind: + result = PyType_GenericNew(Continue_type, NULL, NULL); + if (!result) goto failed; + break; + } + value = ast2obj_int(o->lineno); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "lineno", value) < 0) + goto failed; + Py_DECREF(value); + value = ast2obj_int(o->col_offset); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "col_offset", value) < 0) + goto failed; + Py_DECREF(value); + return result; +failed: + Py_XDECREF(value); + Py_XDECREF(result); + return NULL; +} + +PyObject* +ast2obj_expr(void* _o) +{ + expr_ty o = (expr_ty)_o; + PyObject *result = NULL, *value = NULL; + if (!o) { + Py_INCREF(Py_None); + return Py_None; + } + + switch (o->kind) { + case BoolOp_kind: + result = PyType_GenericNew(BoolOp_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_boolop(o->v.BoolOp.op); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "op", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.BoolOp.values, ast2obj_expr); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "values", value) == -1) + goto failed; + Py_DECREF(value); + break; + case BinOp_kind: + result = PyType_GenericNew(BinOp_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.BinOp.left); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "left", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_operator(o->v.BinOp.op); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "op", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->v.BinOp.right); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "right", value) == -1) + goto failed; + Py_DECREF(value); + break; + case UnaryOp_kind: + result = PyType_GenericNew(UnaryOp_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_unaryop(o->v.UnaryOp.op); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "op", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->v.UnaryOp.operand); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "operand", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Lambda_kind: + result = PyType_GenericNew(Lambda_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_arguments(o->v.Lambda.args); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "args", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->v.Lambda.body); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "body", value) == -1) + goto failed; + Py_DECREF(value); + break; + case IfExp_kind: + result = PyType_GenericNew(IfExp_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.IfExp.test); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "test", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->v.IfExp.body); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "body", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->v.IfExp.orelse); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "orelse", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Dict_kind: + result = PyType_GenericNew(Dict_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_list(o->v.Dict.keys, ast2obj_expr); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "keys", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.Dict.values, ast2obj_expr); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "values", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Set_kind: + result = PyType_GenericNew(Set_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_list(o->v.Set.elts, ast2obj_expr); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "elts", value) == -1) + goto failed; + Py_DECREF(value); + break; + case ListComp_kind: + result = PyType_GenericNew(ListComp_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.ListComp.elt); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "elt", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.ListComp.generators, + ast2obj_comprehension); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "generators", value) == -1) + goto failed; + Py_DECREF(value); + break; + case SetComp_kind: + result = PyType_GenericNew(SetComp_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.SetComp.elt); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "elt", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.SetComp.generators, + ast2obj_comprehension); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "generators", value) == -1) + goto failed; + Py_DECREF(value); + break; + case DictComp_kind: + result = PyType_GenericNew(DictComp_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.DictComp.key); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "key", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->v.DictComp.value); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "value", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.DictComp.generators, + ast2obj_comprehension); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "generators", value) == -1) + goto failed; + Py_DECREF(value); + break; + case GeneratorExp_kind: + result = PyType_GenericNew(GeneratorExp_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.GeneratorExp.elt); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "elt", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.GeneratorExp.generators, + ast2obj_comprehension); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "generators", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Yield_kind: + result = PyType_GenericNew(Yield_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.Yield.value); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "value", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Compare_kind: + result = PyType_GenericNew(Compare_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.Compare.left); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "left", value) == -1) + goto failed; + Py_DECREF(value); + { + int i, n = asdl_seq_LEN(o->v.Compare.ops); + value = PyList_New(n); + if (!value) goto failed; + for(i = 0; i < n; i++) + PyList_SET_ITEM(value, i, ast2obj_cmpop((cmpop_ty)asdl_seq_GET(o->v.Compare.ops, i))); + } + if (!value) goto failed; + if (PyObject_SetAttrString(result, "ops", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.Compare.comparators, ast2obj_expr); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "comparators", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Call_kind: + result = PyType_GenericNew(Call_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.Call.func); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "func", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.Call.args, ast2obj_expr); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "args", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.Call.keywords, ast2obj_keyword); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "keywords", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->v.Call.starargs); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "starargs", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->v.Call.kwargs); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "kwargs", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Repr_kind: + result = PyType_GenericNew(Repr_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.Repr.value); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "value", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Num_kind: + result = PyType_GenericNew(Num_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_object(o->v.Num.n); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "n", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Str_kind: + result = PyType_GenericNew(Str_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_string(o->v.Str.s); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "s", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Attribute_kind: + result = PyType_GenericNew(Attribute_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.Attribute.value); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "value", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_identifier(o->v.Attribute.attr); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "attr", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr_context(o->v.Attribute.ctx); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "ctx", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Subscript_kind: + result = PyType_GenericNew(Subscript_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.Subscript.value); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "value", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_slice(o->v.Subscript.slice); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "slice", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr_context(o->v.Subscript.ctx); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "ctx", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Name_kind: + result = PyType_GenericNew(Name_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_identifier(o->v.Name.id); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "id", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr_context(o->v.Name.ctx); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "ctx", value) == -1) + goto failed; + Py_DECREF(value); + break; + case List_kind: + result = PyType_GenericNew(List_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_list(o->v.List.elts, ast2obj_expr); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "elts", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr_context(o->v.List.ctx); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "ctx", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Tuple_kind: + result = PyType_GenericNew(Tuple_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_list(o->v.Tuple.elts, ast2obj_expr); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "elts", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr_context(o->v.Tuple.ctx); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "ctx", value) == -1) + goto failed; + Py_DECREF(value); + break; + } + value = ast2obj_int(o->lineno); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "lineno", value) < 0) + goto failed; + Py_DECREF(value); + value = ast2obj_int(o->col_offset); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "col_offset", value) < 0) + goto failed; + Py_DECREF(value); + return result; +failed: + Py_XDECREF(value); + Py_XDECREF(result); + return NULL; +} + +PyObject* ast2obj_expr_context(expr_context_ty o) +{ + switch(o) { + case Load: + Py_INCREF(Load_singleton); + return Load_singleton; + case Store: + Py_INCREF(Store_singleton); + return Store_singleton; + case Del: + Py_INCREF(Del_singleton); + return Del_singleton; + case AugLoad: + Py_INCREF(AugLoad_singleton); + return AugLoad_singleton; + case AugStore: + Py_INCREF(AugStore_singleton); + return AugStore_singleton; + case Param: + Py_INCREF(Param_singleton); + return Param_singleton; + default: + /* should never happen, but just in case ... */ + PyErr_Format(PyExc_SystemError, "unknown expr_context found"); + return NULL; + } +} +PyObject* +ast2obj_slice(void* _o) +{ + slice_ty o = (slice_ty)_o; + PyObject *result = NULL, *value = NULL; + if (!o) { + Py_INCREF(Py_None); + return Py_None; + } + + switch (o->kind) { + case Ellipsis_kind: + result = PyType_GenericNew(Ellipsis_type, NULL, NULL); + if (!result) goto failed; + break; + case Slice_kind: + result = PyType_GenericNew(Slice_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.Slice.lower); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "lower", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->v.Slice.upper); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "upper", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->v.Slice.step); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "step", value) == -1) + goto failed; + Py_DECREF(value); + break; + case ExtSlice_kind: + result = PyType_GenericNew(ExtSlice_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_list(o->v.ExtSlice.dims, ast2obj_slice); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "dims", value) == -1) + goto failed; + Py_DECREF(value); + break; + case Index_kind: + result = PyType_GenericNew(Index_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.Index.value); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "value", value) == -1) + goto failed; + Py_DECREF(value); + break; + } + return result; +failed: + Py_XDECREF(value); + Py_XDECREF(result); + return NULL; +} + +PyObject* ast2obj_boolop(boolop_ty o) +{ + switch(o) { + case And: + Py_INCREF(And_singleton); + return And_singleton; + case Or: + Py_INCREF(Or_singleton); + return Or_singleton; + default: + /* should never happen, but just in case ... */ + PyErr_Format(PyExc_SystemError, "unknown boolop found"); + return NULL; + } +} +PyObject* ast2obj_operator(operator_ty o) +{ + switch(o) { + case Add: + Py_INCREF(Add_singleton); + return Add_singleton; + case Sub: + Py_INCREF(Sub_singleton); + return Sub_singleton; + case Mult: + Py_INCREF(Mult_singleton); + return Mult_singleton; + case Div: + Py_INCREF(Div_singleton); + return Div_singleton; + case Mod: + Py_INCREF(Mod_singleton); + return Mod_singleton; + case Pow: + Py_INCREF(Pow_singleton); + return Pow_singleton; + case LShift: + Py_INCREF(LShift_singleton); + return LShift_singleton; + case RShift: + Py_INCREF(RShift_singleton); + return RShift_singleton; + case BitOr: + Py_INCREF(BitOr_singleton); + return BitOr_singleton; + case BitXor: + Py_INCREF(BitXor_singleton); + return BitXor_singleton; + case BitAnd: + Py_INCREF(BitAnd_singleton); + return BitAnd_singleton; + case FloorDiv: + Py_INCREF(FloorDiv_singleton); + return FloorDiv_singleton; + default: + /* should never happen, but just in case ... */ + PyErr_Format(PyExc_SystemError, "unknown operator found"); + return NULL; + } +} +PyObject* ast2obj_unaryop(unaryop_ty o) +{ + switch(o) { + case Invert: + Py_INCREF(Invert_singleton); + return Invert_singleton; + case Not: + Py_INCREF(Not_singleton); + return Not_singleton; + case UAdd: + Py_INCREF(UAdd_singleton); + return UAdd_singleton; + case USub: + Py_INCREF(USub_singleton); + return USub_singleton; + default: + /* should never happen, but just in case ... */ + PyErr_Format(PyExc_SystemError, "unknown unaryop found"); + return NULL; + } +} +PyObject* ast2obj_cmpop(cmpop_ty o) +{ + switch(o) { + case Eq: + Py_INCREF(Eq_singleton); + return Eq_singleton; + case NotEq: + Py_INCREF(NotEq_singleton); + return NotEq_singleton; + case Lt: + Py_INCREF(Lt_singleton); + return Lt_singleton; + case LtE: + Py_INCREF(LtE_singleton); + return LtE_singleton; + case Gt: + Py_INCREF(Gt_singleton); + return Gt_singleton; + case GtE: + Py_INCREF(GtE_singleton); + return GtE_singleton; + case Is: + Py_INCREF(Is_singleton); + return Is_singleton; + case IsNot: + Py_INCREF(IsNot_singleton); + return IsNot_singleton; + case In: + Py_INCREF(In_singleton); + return In_singleton; + case NotIn: + Py_INCREF(NotIn_singleton); + return NotIn_singleton; + default: + /* should never happen, but just in case ... */ + PyErr_Format(PyExc_SystemError, "unknown cmpop found"); + return NULL; + } +} +PyObject* +ast2obj_comprehension(void* _o) +{ + comprehension_ty o = (comprehension_ty)_o; + PyObject *result = NULL, *value = NULL; + if (!o) { + Py_INCREF(Py_None); + return Py_None; + } + + result = PyType_GenericNew(comprehension_type, NULL, NULL); + if (!result) return NULL; + value = ast2obj_expr(o->target); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "target", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->iter); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "iter", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->ifs, ast2obj_expr); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "ifs", value) == -1) + goto failed; + Py_DECREF(value); + return result; +failed: + Py_XDECREF(value); + Py_XDECREF(result); + return NULL; +} + +PyObject* +ast2obj_excepthandler(void* _o) +{ + excepthandler_ty o = (excepthandler_ty)_o; + PyObject *result = NULL, *value = NULL; + if (!o) { + Py_INCREF(Py_None); + return Py_None; + } + + switch (o->kind) { + case ExceptHandler_kind: + result = PyType_GenericNew(ExceptHandler_type, NULL, NULL); + if (!result) goto failed; + value = ast2obj_expr(o->v.ExceptHandler.type); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "type", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->v.ExceptHandler.name); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "name", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->v.ExceptHandler.body, ast2obj_stmt); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "body", value) == -1) + goto failed; + Py_DECREF(value); + break; + } + value = ast2obj_int(o->lineno); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "lineno", value) < 0) + goto failed; + Py_DECREF(value); + value = ast2obj_int(o->col_offset); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "col_offset", value) < 0) + goto failed; + Py_DECREF(value); + return result; +failed: + Py_XDECREF(value); + Py_XDECREF(result); + return NULL; +} + +PyObject* +ast2obj_arguments(void* _o) +{ + arguments_ty o = (arguments_ty)_o; + PyObject *result = NULL, *value = NULL; + if (!o) { + Py_INCREF(Py_None); + return Py_None; + } + + result = PyType_GenericNew(arguments_type, NULL, NULL); + if (!result) return NULL; + value = ast2obj_list(o->args, ast2obj_expr); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "args", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_identifier(o->vararg); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "vararg", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_identifier(o->kwarg); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "kwarg", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_list(o->defaults, ast2obj_expr); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "defaults", value) == -1) + goto failed; + Py_DECREF(value); + return result; +failed: + Py_XDECREF(value); + Py_XDECREF(result); + return NULL; +} + +PyObject* +ast2obj_keyword(void* _o) +{ + keyword_ty o = (keyword_ty)_o; + PyObject *result = NULL, *value = NULL; + if (!o) { + Py_INCREF(Py_None); + return Py_None; + } + + result = PyType_GenericNew(keyword_type, NULL, NULL); + if (!result) return NULL; + value = ast2obj_identifier(o->arg); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "arg", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_expr(o->value); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "value", value) == -1) + goto failed; + Py_DECREF(value); + return result; +failed: + Py_XDECREF(value); + Py_XDECREF(result); + return NULL; +} + +PyObject* +ast2obj_alias(void* _o) +{ + alias_ty o = (alias_ty)_o; + PyObject *result = NULL, *value = NULL; + if (!o) { + Py_INCREF(Py_None); + return Py_None; + } + + result = PyType_GenericNew(alias_type, NULL, NULL); + if (!result) return NULL; + value = ast2obj_identifier(o->name); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "name", value) == -1) + goto failed; + Py_DECREF(value); + value = ast2obj_identifier(o->asname); + if (!value) goto failed; + if (PyObject_SetAttrString(result, "asname", value) == -1) + goto failed; + Py_DECREF(value); + return result; +failed: + Py_XDECREF(value); + Py_XDECREF(result); + return NULL; +} + + +int +obj2ast_mod(PyObject* obj, mod_ty* out, PyArena* arena) +{ + PyObject* tmp = NULL; + int isinstance; + + + if (obj == Py_None) { + *out = NULL; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Module_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + asdl_seq* body; + + if (PyObject_HasAttrString(obj, "body")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "body"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "Module field \"body\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + body = asdl_seq_new(len, arena); + if (body == NULL) goto failed; + for (i = 0; i < len; i++) { + stmt_ty value; + res = obj2ast_stmt(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(body, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"body\" missing from Module"); + return 1; + } + *out = Module(body, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Interactive_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + asdl_seq* body; + + if (PyObject_HasAttrString(obj, "body")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "body"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "Interactive field \"body\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + body = asdl_seq_new(len, arena); + if (body == NULL) goto failed; + for (i = 0; i < len; i++) { + stmt_ty value; + res = obj2ast_stmt(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(body, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"body\" missing from Interactive"); + return 1; + } + *out = Interactive(body, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Expression_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty body; + + if (PyObject_HasAttrString(obj, "body")) { + int res; + tmp = PyObject_GetAttrString(obj, "body"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &body, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"body\" missing from Expression"); + return 1; + } + *out = Expression(body, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Suite_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + asdl_seq* body; + + if (PyObject_HasAttrString(obj, "body")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "body"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "Suite field \"body\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + body = asdl_seq_new(len, arena); + if (body == NULL) goto failed; + for (i = 0; i < len; i++) { + stmt_ty value; + res = obj2ast_stmt(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(body, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"body\" missing from Suite"); + return 1; + } + *out = Suite(body, arena); + if (*out == NULL) goto failed; + return 0; + } + + tmp = PyObject_Repr(obj); + if (tmp == NULL) goto failed; + PyErr_Format(PyExc_TypeError, "expected some sort of mod, but got %.400s", PyString_AS_STRING(tmp)); +failed: + Py_XDECREF(tmp); + return 1; +} + +int +obj2ast_stmt(PyObject* obj, stmt_ty* out, PyArena* arena) +{ + PyObject* tmp = NULL; + int isinstance; + + int lineno; + int col_offset; + + if (obj == Py_None) { + *out = NULL; + return 0; + } + if (PyObject_HasAttrString(obj, "lineno")) { + int res; + tmp = PyObject_GetAttrString(obj, "lineno"); + if (tmp == NULL) goto failed; + res = obj2ast_int(tmp, &lineno, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"lineno\" missing from stmt"); + return 1; + } + if (PyObject_HasAttrString(obj, "col_offset")) { + int res; + tmp = PyObject_GetAttrString(obj, "col_offset"); + if (tmp == NULL) goto failed; + res = obj2ast_int(tmp, &col_offset, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"col_offset\" missing from stmt"); + return 1; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)FunctionDef_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + identifier name; + arguments_ty args; + asdl_seq* body; + asdl_seq* decorator_list; + + if (PyObject_HasAttrString(obj, "name")) { + int res; + tmp = PyObject_GetAttrString(obj, "name"); + if (tmp == NULL) goto failed; + res = obj2ast_identifier(tmp, &name, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"name\" missing from FunctionDef"); + return 1; + } + if (PyObject_HasAttrString(obj, "args")) { + int res; + tmp = PyObject_GetAttrString(obj, "args"); + if (tmp == NULL) goto failed; + res = obj2ast_arguments(tmp, &args, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"args\" missing from FunctionDef"); + return 1; + } + if (PyObject_HasAttrString(obj, "body")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "body"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "FunctionDef field \"body\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + body = asdl_seq_new(len, arena); + if (body == NULL) goto failed; + for (i = 0; i < len; i++) { + stmt_ty value; + res = obj2ast_stmt(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(body, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"body\" missing from FunctionDef"); + return 1; + } + if (PyObject_HasAttrString(obj, "decorator_list")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "decorator_list"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "FunctionDef field \"decorator_list\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + decorator_list = asdl_seq_new(len, arena); + if (decorator_list == NULL) goto failed; + for (i = 0; i < len; i++) { + expr_ty value; + res = obj2ast_expr(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(decorator_list, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"decorator_list\" missing from FunctionDef"); + return 1; + } + *out = FunctionDef(name, args, body, decorator_list, lineno, + col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)ClassDef_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + identifier name; + asdl_seq* bases; + asdl_seq* body; + asdl_seq* decorator_list; + + if (PyObject_HasAttrString(obj, "name")) { + int res; + tmp = PyObject_GetAttrString(obj, "name"); + if (tmp == NULL) goto failed; + res = obj2ast_identifier(tmp, &name, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"name\" missing from ClassDef"); + return 1; + } + if (PyObject_HasAttrString(obj, "bases")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "bases"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "ClassDef field \"bases\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + bases = asdl_seq_new(len, arena); + if (bases == NULL) goto failed; + for (i = 0; i < len; i++) { + expr_ty value; + res = obj2ast_expr(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(bases, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"bases\" missing from ClassDef"); + return 1; + } + if (PyObject_HasAttrString(obj, "body")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "body"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "ClassDef field \"body\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + body = asdl_seq_new(len, arena); + if (body == NULL) goto failed; + for (i = 0; i < len; i++) { + stmt_ty value; + res = obj2ast_stmt(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(body, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"body\" missing from ClassDef"); + return 1; + } + if (PyObject_HasAttrString(obj, "decorator_list")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "decorator_list"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "ClassDef field \"decorator_list\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + decorator_list = asdl_seq_new(len, arena); + if (decorator_list == NULL) goto failed; + for (i = 0; i < len; i++) { + expr_ty value; + res = obj2ast_expr(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(decorator_list, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"decorator_list\" missing from ClassDef"); + return 1; + } + *out = ClassDef(name, bases, body, decorator_list, lineno, + col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Return_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty value; + + if (PyObject_HasAttrString(obj, "value")) { + int res; + tmp = PyObject_GetAttrString(obj, "value"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &value, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + value = NULL; + } + *out = Return(value, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Delete_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + asdl_seq* targets; + + if (PyObject_HasAttrString(obj, "targets")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "targets"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "Delete field \"targets\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + targets = asdl_seq_new(len, arena); + if (targets == NULL) goto failed; + for (i = 0; i < len; i++) { + expr_ty value; + res = obj2ast_expr(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(targets, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"targets\" missing from Delete"); + return 1; + } + *out = Delete(targets, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Assign_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + asdl_seq* targets; + expr_ty value; + + if (PyObject_HasAttrString(obj, "targets")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "targets"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "Assign field \"targets\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + targets = asdl_seq_new(len, arena); + if (targets == NULL) goto failed; + for (i = 0; i < len; i++) { + expr_ty value; + res = obj2ast_expr(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(targets, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"targets\" missing from Assign"); + return 1; + } + if (PyObject_HasAttrString(obj, "value")) { + int res; + tmp = PyObject_GetAttrString(obj, "value"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &value, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"value\" missing from Assign"); + return 1; + } + *out = Assign(targets, value, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)AugAssign_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty target; + operator_ty op; + expr_ty value; + + if (PyObject_HasAttrString(obj, "target")) { + int res; + tmp = PyObject_GetAttrString(obj, "target"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &target, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"target\" missing from AugAssign"); + return 1; + } + if (PyObject_HasAttrString(obj, "op")) { + int res; + tmp = PyObject_GetAttrString(obj, "op"); + if (tmp == NULL) goto failed; + res = obj2ast_operator(tmp, &op, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"op\" missing from AugAssign"); + return 1; + } + if (PyObject_HasAttrString(obj, "value")) { + int res; + tmp = PyObject_GetAttrString(obj, "value"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &value, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"value\" missing from AugAssign"); + return 1; + } + *out = AugAssign(target, op, value, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Print_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty dest; + asdl_seq* values; + bool nl; + + if (PyObject_HasAttrString(obj, "dest")) { + int res; + tmp = PyObject_GetAttrString(obj, "dest"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &dest, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + dest = NULL; + } + if (PyObject_HasAttrString(obj, "values")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "values"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "Print field \"values\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + values = asdl_seq_new(len, arena); + if (values == NULL) goto failed; + for (i = 0; i < len; i++) { + expr_ty value; + res = obj2ast_expr(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(values, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"values\" missing from Print"); + return 1; + } + if (PyObject_HasAttrString(obj, "nl")) { + int res; + tmp = PyObject_GetAttrString(obj, "nl"); + if (tmp == NULL) goto failed; + res = obj2ast_bool(tmp, &nl, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"nl\" missing from Print"); + return 1; + } + *out = Print(dest, values, nl, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)For_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty target; + expr_ty iter; + asdl_seq* body; + asdl_seq* orelse; + + if (PyObject_HasAttrString(obj, "target")) { + int res; + tmp = PyObject_GetAttrString(obj, "target"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &target, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"target\" missing from For"); + return 1; + } + if (PyObject_HasAttrString(obj, "iter")) { + int res; + tmp = PyObject_GetAttrString(obj, "iter"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &iter, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"iter\" missing from For"); + return 1; + } + if (PyObject_HasAttrString(obj, "body")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "body"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "For field \"body\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + body = asdl_seq_new(len, arena); + if (body == NULL) goto failed; + for (i = 0; i < len; i++) { + stmt_ty value; + res = obj2ast_stmt(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(body, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"body\" missing from For"); + return 1; + } + if (PyObject_HasAttrString(obj, "orelse")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "orelse"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "For field \"orelse\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + orelse = asdl_seq_new(len, arena); + if (orelse == NULL) goto failed; + for (i = 0; i < len; i++) { + stmt_ty value; + res = obj2ast_stmt(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(orelse, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"orelse\" missing from For"); + return 1; + } + *out = For(target, iter, body, orelse, lineno, col_offset, + arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)While_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty test; + asdl_seq* body; + asdl_seq* orelse; + + if (PyObject_HasAttrString(obj, "test")) { + int res; + tmp = PyObject_GetAttrString(obj, "test"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &test, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"test\" missing from While"); + return 1; + } + if (PyObject_HasAttrString(obj, "body")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "body"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "While field \"body\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + body = asdl_seq_new(len, arena); + if (body == NULL) goto failed; + for (i = 0; i < len; i++) { + stmt_ty value; + res = obj2ast_stmt(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(body, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"body\" missing from While"); + return 1; + } + if (PyObject_HasAttrString(obj, "orelse")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "orelse"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "While field \"orelse\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + orelse = asdl_seq_new(len, arena); + if (orelse == NULL) goto failed; + for (i = 0; i < len; i++) { + stmt_ty value; + res = obj2ast_stmt(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(orelse, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"orelse\" missing from While"); + return 1; + } + *out = While(test, body, orelse, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)If_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty test; + asdl_seq* body; + asdl_seq* orelse; + + if (PyObject_HasAttrString(obj, "test")) { + int res; + tmp = PyObject_GetAttrString(obj, "test"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &test, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"test\" missing from If"); + return 1; + } + if (PyObject_HasAttrString(obj, "body")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "body"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "If field \"body\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + body = asdl_seq_new(len, arena); + if (body == NULL) goto failed; + for (i = 0; i < len; i++) { + stmt_ty value; + res = obj2ast_stmt(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(body, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"body\" missing from If"); + return 1; + } + if (PyObject_HasAttrString(obj, "orelse")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "orelse"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "If field \"orelse\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + orelse = asdl_seq_new(len, arena); + if (orelse == NULL) goto failed; + for (i = 0; i < len; i++) { + stmt_ty value; + res = obj2ast_stmt(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(orelse, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"orelse\" missing from If"); + return 1; + } + *out = If(test, body, orelse, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)With_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty context_expr; + expr_ty optional_vars; + asdl_seq* body; + + if (PyObject_HasAttrString(obj, "context_expr")) { + int res; + tmp = PyObject_GetAttrString(obj, "context_expr"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &context_expr, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"context_expr\" missing from With"); + return 1; + } + if (PyObject_HasAttrString(obj, "optional_vars")) { + int res; + tmp = PyObject_GetAttrString(obj, "optional_vars"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &optional_vars, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + optional_vars = NULL; + } + if (PyObject_HasAttrString(obj, "body")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "body"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "With field \"body\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + body = asdl_seq_new(len, arena); + if (body == NULL) goto failed; + for (i = 0; i < len; i++) { + stmt_ty value; + res = obj2ast_stmt(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(body, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"body\" missing from With"); + return 1; + } + *out = With(context_expr, optional_vars, body, lineno, + col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Raise_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty type; + expr_ty inst; + expr_ty tback; + + if (PyObject_HasAttrString(obj, "type")) { + int res; + tmp = PyObject_GetAttrString(obj, "type"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &type, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + type = NULL; + } + if (PyObject_HasAttrString(obj, "inst")) { + int res; + tmp = PyObject_GetAttrString(obj, "inst"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &inst, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + inst = NULL; + } + if (PyObject_HasAttrString(obj, "tback")) { + int res; + tmp = PyObject_GetAttrString(obj, "tback"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &tback, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + tback = NULL; + } + *out = Raise(type, inst, tback, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)TryExcept_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + asdl_seq* body; + asdl_seq* handlers; + asdl_seq* orelse; + + if (PyObject_HasAttrString(obj, "body")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "body"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "TryExcept field \"body\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + body = asdl_seq_new(len, arena); + if (body == NULL) goto failed; + for (i = 0; i < len; i++) { + stmt_ty value; + res = obj2ast_stmt(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(body, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"body\" missing from TryExcept"); + return 1; + } + if (PyObject_HasAttrString(obj, "handlers")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "handlers"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "TryExcept field \"handlers\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + handlers = asdl_seq_new(len, arena); + if (handlers == NULL) goto failed; + for (i = 0; i < len; i++) { + excepthandler_ty value; + res = obj2ast_excepthandler(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(handlers, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"handlers\" missing from TryExcept"); + return 1; + } + if (PyObject_HasAttrString(obj, "orelse")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "orelse"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "TryExcept field \"orelse\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + orelse = asdl_seq_new(len, arena); + if (orelse == NULL) goto failed; + for (i = 0; i < len; i++) { + stmt_ty value; + res = obj2ast_stmt(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(orelse, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"orelse\" missing from TryExcept"); + return 1; + } + *out = TryExcept(body, handlers, orelse, lineno, col_offset, + arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)TryFinally_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + asdl_seq* body; + asdl_seq* finalbody; + + if (PyObject_HasAttrString(obj, "body")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "body"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "TryFinally field \"body\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + body = asdl_seq_new(len, arena); + if (body == NULL) goto failed; + for (i = 0; i < len; i++) { + stmt_ty value; + res = obj2ast_stmt(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(body, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"body\" missing from TryFinally"); + return 1; + } + if (PyObject_HasAttrString(obj, "finalbody")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "finalbody"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "TryFinally field \"finalbody\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + finalbody = asdl_seq_new(len, arena); + if (finalbody == NULL) goto failed; + for (i = 0; i < len; i++) { + stmt_ty value; + res = obj2ast_stmt(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(finalbody, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"finalbody\" missing from TryFinally"); + return 1; + } + *out = TryFinally(body, finalbody, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Assert_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty test; + expr_ty msg; + + if (PyObject_HasAttrString(obj, "test")) { + int res; + tmp = PyObject_GetAttrString(obj, "test"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &test, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"test\" missing from Assert"); + return 1; + } + if (PyObject_HasAttrString(obj, "msg")) { + int res; + tmp = PyObject_GetAttrString(obj, "msg"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &msg, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + msg = NULL; + } + *out = Assert(test, msg, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Import_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + asdl_seq* names; + + if (PyObject_HasAttrString(obj, "names")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "names"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "Import field \"names\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + names = asdl_seq_new(len, arena); + if (names == NULL) goto failed; + for (i = 0; i < len; i++) { + alias_ty value; + res = obj2ast_alias(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(names, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"names\" missing from Import"); + return 1; + } + *out = Import(names, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)ImportFrom_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + identifier module; + asdl_seq* names; + int level; + + if (PyObject_HasAttrString(obj, "module")) { + int res; + tmp = PyObject_GetAttrString(obj, "module"); + if (tmp == NULL) goto failed; + res = obj2ast_identifier(tmp, &module, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + module = NULL; + } + if (PyObject_HasAttrString(obj, "names")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "names"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "ImportFrom field \"names\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + names = asdl_seq_new(len, arena); + if (names == NULL) goto failed; + for (i = 0; i < len; i++) { + alias_ty value; + res = obj2ast_alias(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(names, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"names\" missing from ImportFrom"); + return 1; + } + if (PyObject_HasAttrString(obj, "level")) { + int res; + tmp = PyObject_GetAttrString(obj, "level"); + if (tmp == NULL) goto failed; + res = obj2ast_int(tmp, &level, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + level = 0; + } + *out = ImportFrom(module, names, level, lineno, col_offset, + arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Exec_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty body; + expr_ty globals; + expr_ty locals; + + if (PyObject_HasAttrString(obj, "body")) { + int res; + tmp = PyObject_GetAttrString(obj, "body"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &body, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"body\" missing from Exec"); + return 1; + } + if (PyObject_HasAttrString(obj, "globals")) { + int res; + tmp = PyObject_GetAttrString(obj, "globals"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &globals, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + globals = NULL; + } + if (PyObject_HasAttrString(obj, "locals")) { + int res; + tmp = PyObject_GetAttrString(obj, "locals"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &locals, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + locals = NULL; + } + *out = Exec(body, globals, locals, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Global_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + asdl_seq* names; + + if (PyObject_HasAttrString(obj, "names")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "names"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "Global field \"names\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + names = asdl_seq_new(len, arena); + if (names == NULL) goto failed; + for (i = 0; i < len; i++) { + identifier value; + res = obj2ast_identifier(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(names, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"names\" missing from Global"); + return 1; + } + *out = Global(names, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Expr_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty value; + + if (PyObject_HasAttrString(obj, "value")) { + int res; + tmp = PyObject_GetAttrString(obj, "value"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &value, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"value\" missing from Expr"); + return 1; + } + *out = Expr(value, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Pass_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + + *out = Pass(lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Break_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + + *out = Break(lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Continue_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + + *out = Continue(lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + + tmp = PyObject_Repr(obj); + if (tmp == NULL) goto failed; + PyErr_Format(PyExc_TypeError, "expected some sort of stmt, but got %.400s", PyString_AS_STRING(tmp)); +failed: + Py_XDECREF(tmp); + return 1; +} + +int +obj2ast_expr(PyObject* obj, expr_ty* out, PyArena* arena) +{ + PyObject* tmp = NULL; + int isinstance; + + int lineno; + int col_offset; + + if (obj == Py_None) { + *out = NULL; + return 0; + } + if (PyObject_HasAttrString(obj, "lineno")) { + int res; + tmp = PyObject_GetAttrString(obj, "lineno"); + if (tmp == NULL) goto failed; + res = obj2ast_int(tmp, &lineno, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"lineno\" missing from expr"); + return 1; + } + if (PyObject_HasAttrString(obj, "col_offset")) { + int res; + tmp = PyObject_GetAttrString(obj, "col_offset"); + if (tmp == NULL) goto failed; + res = obj2ast_int(tmp, &col_offset, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"col_offset\" missing from expr"); + return 1; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)BoolOp_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + boolop_ty op; + asdl_seq* values; + + if (PyObject_HasAttrString(obj, "op")) { + int res; + tmp = PyObject_GetAttrString(obj, "op"); + if (tmp == NULL) goto failed; + res = obj2ast_boolop(tmp, &op, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"op\" missing from BoolOp"); + return 1; + } + if (PyObject_HasAttrString(obj, "values")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "values"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "BoolOp field \"values\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + values = asdl_seq_new(len, arena); + if (values == NULL) goto failed; + for (i = 0; i < len; i++) { + expr_ty value; + res = obj2ast_expr(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(values, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"values\" missing from BoolOp"); + return 1; + } + *out = BoolOp(op, values, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)BinOp_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty left; + operator_ty op; + expr_ty right; + + if (PyObject_HasAttrString(obj, "left")) { + int res; + tmp = PyObject_GetAttrString(obj, "left"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &left, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"left\" missing from BinOp"); + return 1; + } + if (PyObject_HasAttrString(obj, "op")) { + int res; + tmp = PyObject_GetAttrString(obj, "op"); + if (tmp == NULL) goto failed; + res = obj2ast_operator(tmp, &op, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"op\" missing from BinOp"); + return 1; + } + if (PyObject_HasAttrString(obj, "right")) { + int res; + tmp = PyObject_GetAttrString(obj, "right"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &right, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"right\" missing from BinOp"); + return 1; + } + *out = BinOp(left, op, right, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)UnaryOp_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + unaryop_ty op; + expr_ty operand; + + if (PyObject_HasAttrString(obj, "op")) { + int res; + tmp = PyObject_GetAttrString(obj, "op"); + if (tmp == NULL) goto failed; + res = obj2ast_unaryop(tmp, &op, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"op\" missing from UnaryOp"); + return 1; + } + if (PyObject_HasAttrString(obj, "operand")) { + int res; + tmp = PyObject_GetAttrString(obj, "operand"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &operand, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"operand\" missing from UnaryOp"); + return 1; + } + *out = UnaryOp(op, operand, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Lambda_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + arguments_ty args; + expr_ty body; + + if (PyObject_HasAttrString(obj, "args")) { + int res; + tmp = PyObject_GetAttrString(obj, "args"); + if (tmp == NULL) goto failed; + res = obj2ast_arguments(tmp, &args, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"args\" missing from Lambda"); + return 1; + } + if (PyObject_HasAttrString(obj, "body")) { + int res; + tmp = PyObject_GetAttrString(obj, "body"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &body, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"body\" missing from Lambda"); + return 1; + } + *out = Lambda(args, body, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)IfExp_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty test; + expr_ty body; + expr_ty orelse; + + if (PyObject_HasAttrString(obj, "test")) { + int res; + tmp = PyObject_GetAttrString(obj, "test"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &test, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"test\" missing from IfExp"); + return 1; + } + if (PyObject_HasAttrString(obj, "body")) { + int res; + tmp = PyObject_GetAttrString(obj, "body"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &body, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"body\" missing from IfExp"); + return 1; + } + if (PyObject_HasAttrString(obj, "orelse")) { + int res; + tmp = PyObject_GetAttrString(obj, "orelse"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &orelse, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"orelse\" missing from IfExp"); + return 1; + } + *out = IfExp(test, body, orelse, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Dict_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + asdl_seq* keys; + asdl_seq* values; + + if (PyObject_HasAttrString(obj, "keys")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "keys"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "Dict field \"keys\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + keys = asdl_seq_new(len, arena); + if (keys == NULL) goto failed; + for (i = 0; i < len; i++) { + expr_ty value; + res = obj2ast_expr(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(keys, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"keys\" missing from Dict"); + return 1; + } + if (PyObject_HasAttrString(obj, "values")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "values"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "Dict field \"values\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + values = asdl_seq_new(len, arena); + if (values == NULL) goto failed; + for (i = 0; i < len; i++) { + expr_ty value; + res = obj2ast_expr(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(values, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"values\" missing from Dict"); + return 1; + } + *out = Dict(keys, values, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Set_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + asdl_seq* elts; + + if (PyObject_HasAttrString(obj, "elts")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "elts"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "Set field \"elts\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + elts = asdl_seq_new(len, arena); + if (elts == NULL) goto failed; + for (i = 0; i < len; i++) { + expr_ty value; + res = obj2ast_expr(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(elts, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"elts\" missing from Set"); + return 1; + } + *out = Set(elts, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)ListComp_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty elt; + asdl_seq* generators; + + if (PyObject_HasAttrString(obj, "elt")) { + int res; + tmp = PyObject_GetAttrString(obj, "elt"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &elt, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"elt\" missing from ListComp"); + return 1; + } + if (PyObject_HasAttrString(obj, "generators")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "generators"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "ListComp field \"generators\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + generators = asdl_seq_new(len, arena); + if (generators == NULL) goto failed; + for (i = 0; i < len; i++) { + comprehension_ty value; + res = obj2ast_comprehension(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(generators, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"generators\" missing from ListComp"); + return 1; + } + *out = ListComp(elt, generators, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)SetComp_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty elt; + asdl_seq* generators; + + if (PyObject_HasAttrString(obj, "elt")) { + int res; + tmp = PyObject_GetAttrString(obj, "elt"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &elt, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"elt\" missing from SetComp"); + return 1; + } + if (PyObject_HasAttrString(obj, "generators")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "generators"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "SetComp field \"generators\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + generators = asdl_seq_new(len, arena); + if (generators == NULL) goto failed; + for (i = 0; i < len; i++) { + comprehension_ty value; + res = obj2ast_comprehension(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(generators, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"generators\" missing from SetComp"); + return 1; + } + *out = SetComp(elt, generators, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)DictComp_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty key; + expr_ty value; + asdl_seq* generators; + + if (PyObject_HasAttrString(obj, "key")) { + int res; + tmp = PyObject_GetAttrString(obj, "key"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &key, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"key\" missing from DictComp"); + return 1; + } + if (PyObject_HasAttrString(obj, "value")) { + int res; + tmp = PyObject_GetAttrString(obj, "value"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &value, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"value\" missing from DictComp"); + return 1; + } + if (PyObject_HasAttrString(obj, "generators")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "generators"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "DictComp field \"generators\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + generators = asdl_seq_new(len, arena); + if (generators == NULL) goto failed; + for (i = 0; i < len; i++) { + comprehension_ty value; + res = obj2ast_comprehension(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(generators, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"generators\" missing from DictComp"); + return 1; + } + *out = DictComp(key, value, generators, lineno, col_offset, + arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)GeneratorExp_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty elt; + asdl_seq* generators; + + if (PyObject_HasAttrString(obj, "elt")) { + int res; + tmp = PyObject_GetAttrString(obj, "elt"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &elt, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"elt\" missing from GeneratorExp"); + return 1; + } + if (PyObject_HasAttrString(obj, "generators")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "generators"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "GeneratorExp field \"generators\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + generators = asdl_seq_new(len, arena); + if (generators == NULL) goto failed; + for (i = 0; i < len; i++) { + comprehension_ty value; + res = obj2ast_comprehension(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(generators, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"generators\" missing from GeneratorExp"); + return 1; + } + *out = GeneratorExp(elt, generators, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Yield_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty value; + + if (PyObject_HasAttrString(obj, "value")) { + int res; + tmp = PyObject_GetAttrString(obj, "value"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &value, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + value = NULL; + } + *out = Yield(value, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Compare_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty left; + asdl_int_seq* ops; + asdl_seq* comparators; + + if (PyObject_HasAttrString(obj, "left")) { + int res; + tmp = PyObject_GetAttrString(obj, "left"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &left, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"left\" missing from Compare"); + return 1; + } + if (PyObject_HasAttrString(obj, "ops")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "ops"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "Compare field \"ops\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + ops = asdl_int_seq_new(len, arena); + if (ops == NULL) goto failed; + for (i = 0; i < len; i++) { + cmpop_ty value; + res = obj2ast_cmpop(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(ops, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"ops\" missing from Compare"); + return 1; + } + if (PyObject_HasAttrString(obj, "comparators")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "comparators"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "Compare field \"comparators\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + comparators = asdl_seq_new(len, arena); + if (comparators == NULL) goto failed; + for (i = 0; i < len; i++) { + expr_ty value; + res = obj2ast_expr(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(comparators, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"comparators\" missing from Compare"); + return 1; + } + *out = Compare(left, ops, comparators, lineno, col_offset, + arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Call_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty func; + asdl_seq* args; + asdl_seq* keywords; + expr_ty starargs; + expr_ty kwargs; + + if (PyObject_HasAttrString(obj, "func")) { + int res; + tmp = PyObject_GetAttrString(obj, "func"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &func, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"func\" missing from Call"); + return 1; + } + if (PyObject_HasAttrString(obj, "args")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "args"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "Call field \"args\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + args = asdl_seq_new(len, arena); + if (args == NULL) goto failed; + for (i = 0; i < len; i++) { + expr_ty value; + res = obj2ast_expr(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(args, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"args\" missing from Call"); + return 1; + } + if (PyObject_HasAttrString(obj, "keywords")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "keywords"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "Call field \"keywords\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + keywords = asdl_seq_new(len, arena); + if (keywords == NULL) goto failed; + for (i = 0; i < len; i++) { + keyword_ty value; + res = obj2ast_keyword(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(keywords, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"keywords\" missing from Call"); + return 1; + } + if (PyObject_HasAttrString(obj, "starargs")) { + int res; + tmp = PyObject_GetAttrString(obj, "starargs"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &starargs, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + starargs = NULL; + } + if (PyObject_HasAttrString(obj, "kwargs")) { + int res; + tmp = PyObject_GetAttrString(obj, "kwargs"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &kwargs, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + kwargs = NULL; + } + *out = Call(func, args, keywords, starargs, kwargs, lineno, + col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Repr_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty value; + + if (PyObject_HasAttrString(obj, "value")) { + int res; + tmp = PyObject_GetAttrString(obj, "value"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &value, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"value\" missing from Repr"); + return 1; + } + *out = Repr(value, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Num_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + object n; + + if (PyObject_HasAttrString(obj, "n")) { + int res; + tmp = PyObject_GetAttrString(obj, "n"); + if (tmp == NULL) goto failed; + res = obj2ast_object(tmp, &n, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"n\" missing from Num"); + return 1; + } + *out = Num(n, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Str_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + string s; + + if (PyObject_HasAttrString(obj, "s")) { + int res; + tmp = PyObject_GetAttrString(obj, "s"); + if (tmp == NULL) goto failed; + res = obj2ast_string(tmp, &s, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"s\" missing from Str"); + return 1; + } + *out = Str(s, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Attribute_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty value; + identifier attr; + expr_context_ty ctx; + + if (PyObject_HasAttrString(obj, "value")) { + int res; + tmp = PyObject_GetAttrString(obj, "value"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &value, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"value\" missing from Attribute"); + return 1; + } + if (PyObject_HasAttrString(obj, "attr")) { + int res; + tmp = PyObject_GetAttrString(obj, "attr"); + if (tmp == NULL) goto failed; + res = obj2ast_identifier(tmp, &attr, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"attr\" missing from Attribute"); + return 1; + } + if (PyObject_HasAttrString(obj, "ctx")) { + int res; + tmp = PyObject_GetAttrString(obj, "ctx"); + if (tmp == NULL) goto failed; + res = obj2ast_expr_context(tmp, &ctx, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"ctx\" missing from Attribute"); + return 1; + } + *out = Attribute(value, attr, ctx, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Subscript_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty value; + slice_ty slice; + expr_context_ty ctx; + + if (PyObject_HasAttrString(obj, "value")) { + int res; + tmp = PyObject_GetAttrString(obj, "value"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &value, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"value\" missing from Subscript"); + return 1; + } + if (PyObject_HasAttrString(obj, "slice")) { + int res; + tmp = PyObject_GetAttrString(obj, "slice"); + if (tmp == NULL) goto failed; + res = obj2ast_slice(tmp, &slice, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"slice\" missing from Subscript"); + return 1; + } + if (PyObject_HasAttrString(obj, "ctx")) { + int res; + tmp = PyObject_GetAttrString(obj, "ctx"); + if (tmp == NULL) goto failed; + res = obj2ast_expr_context(tmp, &ctx, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"ctx\" missing from Subscript"); + return 1; + } + *out = Subscript(value, slice, ctx, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Name_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + identifier id; + expr_context_ty ctx; + + if (PyObject_HasAttrString(obj, "id")) { + int res; + tmp = PyObject_GetAttrString(obj, "id"); + if (tmp == NULL) goto failed; + res = obj2ast_identifier(tmp, &id, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"id\" missing from Name"); + return 1; + } + if (PyObject_HasAttrString(obj, "ctx")) { + int res; + tmp = PyObject_GetAttrString(obj, "ctx"); + if (tmp == NULL) goto failed; + res = obj2ast_expr_context(tmp, &ctx, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"ctx\" missing from Name"); + return 1; + } + *out = Name(id, ctx, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)List_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + asdl_seq* elts; + expr_context_ty ctx; + + if (PyObject_HasAttrString(obj, "elts")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "elts"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "List field \"elts\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + elts = asdl_seq_new(len, arena); + if (elts == NULL) goto failed; + for (i = 0; i < len; i++) { + expr_ty value; + res = obj2ast_expr(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(elts, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"elts\" missing from List"); + return 1; + } + if (PyObject_HasAttrString(obj, "ctx")) { + int res; + tmp = PyObject_GetAttrString(obj, "ctx"); + if (tmp == NULL) goto failed; + res = obj2ast_expr_context(tmp, &ctx, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"ctx\" missing from List"); + return 1; + } + *out = List(elts, ctx, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Tuple_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + asdl_seq* elts; + expr_context_ty ctx; + + if (PyObject_HasAttrString(obj, "elts")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "elts"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "Tuple field \"elts\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + elts = asdl_seq_new(len, arena); + if (elts == NULL) goto failed; + for (i = 0; i < len; i++) { + expr_ty value; + res = obj2ast_expr(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(elts, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"elts\" missing from Tuple"); + return 1; + } + if (PyObject_HasAttrString(obj, "ctx")) { + int res; + tmp = PyObject_GetAttrString(obj, "ctx"); + if (tmp == NULL) goto failed; + res = obj2ast_expr_context(tmp, &ctx, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"ctx\" missing from Tuple"); + return 1; + } + *out = Tuple(elts, ctx, lineno, col_offset, arena); + if (*out == NULL) goto failed; + return 0; + } + + tmp = PyObject_Repr(obj); + if (tmp == NULL) goto failed; + PyErr_Format(PyExc_TypeError, "expected some sort of expr, but got %.400s", PyString_AS_STRING(tmp)); +failed: + Py_XDECREF(tmp); + return 1; +} + +int +obj2ast_expr_context(PyObject* obj, expr_context_ty* out, PyArena* arena) +{ + PyObject* tmp = NULL; + int isinstance; + + isinstance = PyObject_IsInstance(obj, (PyObject *)Load_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = Load; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)Store_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = Store; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)Del_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = Del; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)AugLoad_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = AugLoad; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)AugStore_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = AugStore; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)Param_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = Param; + return 0; + } + + tmp = PyObject_Repr(obj); + if (tmp == NULL) goto failed; + PyErr_Format(PyExc_TypeError, "expected some sort of expr_context, but got %.400s", PyString_AS_STRING(tmp)); +failed: + Py_XDECREF(tmp); + return 1; +} + +int +obj2ast_slice(PyObject* obj, slice_ty* out, PyArena* arena) +{ + PyObject* tmp = NULL; + int isinstance; + + + if (obj == Py_None) { + *out = NULL; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Ellipsis_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + + *out = Ellipsis(arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Slice_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty lower; + expr_ty upper; + expr_ty step; + + if (PyObject_HasAttrString(obj, "lower")) { + int res; + tmp = PyObject_GetAttrString(obj, "lower"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &lower, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + lower = NULL; + } + if (PyObject_HasAttrString(obj, "upper")) { + int res; + tmp = PyObject_GetAttrString(obj, "upper"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &upper, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + upper = NULL; + } + if (PyObject_HasAttrString(obj, "step")) { + int res; + tmp = PyObject_GetAttrString(obj, "step"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &step, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + step = NULL; + } + *out = Slice(lower, upper, step, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)ExtSlice_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + asdl_seq* dims; + + if (PyObject_HasAttrString(obj, "dims")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "dims"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "ExtSlice field \"dims\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + dims = asdl_seq_new(len, arena); + if (dims == NULL) goto failed; + for (i = 0; i < len; i++) { + slice_ty value; + res = obj2ast_slice(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(dims, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"dims\" missing from ExtSlice"); + return 1; + } + *out = ExtSlice(dims, arena); + if (*out == NULL) goto failed; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)Index_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty value; + + if (PyObject_HasAttrString(obj, "value")) { + int res; + tmp = PyObject_GetAttrString(obj, "value"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &value, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"value\" missing from Index"); + return 1; + } + *out = Index(value, arena); + if (*out == NULL) goto failed; + return 0; + } + + tmp = PyObject_Repr(obj); + if (tmp == NULL) goto failed; + PyErr_Format(PyExc_TypeError, "expected some sort of slice, but got %.400s", PyString_AS_STRING(tmp)); +failed: + Py_XDECREF(tmp); + return 1; +} + +int +obj2ast_boolop(PyObject* obj, boolop_ty* out, PyArena* arena) +{ + PyObject* tmp = NULL; + int isinstance; + + isinstance = PyObject_IsInstance(obj, (PyObject *)And_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = And; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)Or_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = Or; + return 0; + } + + tmp = PyObject_Repr(obj); + if (tmp == NULL) goto failed; + PyErr_Format(PyExc_TypeError, "expected some sort of boolop, but got %.400s", PyString_AS_STRING(tmp)); +failed: + Py_XDECREF(tmp); + return 1; +} + +int +obj2ast_operator(PyObject* obj, operator_ty* out, PyArena* arena) +{ + PyObject* tmp = NULL; + int isinstance; + + isinstance = PyObject_IsInstance(obj, (PyObject *)Add_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = Add; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)Sub_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = Sub; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)Mult_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = Mult; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)Div_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = Div; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)Mod_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = Mod; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)Pow_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = Pow; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)LShift_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = LShift; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)RShift_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = RShift; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)BitOr_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = BitOr; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)BitXor_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = BitXor; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)BitAnd_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = BitAnd; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)FloorDiv_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = FloorDiv; + return 0; + } + + tmp = PyObject_Repr(obj); + if (tmp == NULL) goto failed; + PyErr_Format(PyExc_TypeError, "expected some sort of operator, but got %.400s", PyString_AS_STRING(tmp)); +failed: + Py_XDECREF(tmp); + return 1; +} + +int +obj2ast_unaryop(PyObject* obj, unaryop_ty* out, PyArena* arena) +{ + PyObject* tmp = NULL; + int isinstance; + + isinstance = PyObject_IsInstance(obj, (PyObject *)Invert_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = Invert; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)Not_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = Not; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)UAdd_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = UAdd; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)USub_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = USub; + return 0; + } + + tmp = PyObject_Repr(obj); + if (tmp == NULL) goto failed; + PyErr_Format(PyExc_TypeError, "expected some sort of unaryop, but got %.400s", PyString_AS_STRING(tmp)); +failed: + Py_XDECREF(tmp); + return 1; +} + +int +obj2ast_cmpop(PyObject* obj, cmpop_ty* out, PyArena* arena) +{ + PyObject* tmp = NULL; + int isinstance; + + isinstance = PyObject_IsInstance(obj, (PyObject *)Eq_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = Eq; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)NotEq_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = NotEq; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)Lt_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = Lt; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)LtE_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = LtE; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)Gt_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = Gt; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)GtE_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = GtE; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)Is_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = Is; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)IsNot_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = IsNot; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)In_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = In; + return 0; + } + isinstance = PyObject_IsInstance(obj, (PyObject *)NotIn_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + *out = NotIn; + return 0; + } + + tmp = PyObject_Repr(obj); + if (tmp == NULL) goto failed; + PyErr_Format(PyExc_TypeError, "expected some sort of cmpop, but got %.400s", PyString_AS_STRING(tmp)); +failed: + Py_XDECREF(tmp); + return 1; +} + +int +obj2ast_comprehension(PyObject* obj, comprehension_ty* out, PyArena* arena) +{ + PyObject* tmp = NULL; + expr_ty target; + expr_ty iter; + asdl_seq* ifs; + + if (PyObject_HasAttrString(obj, "target")) { + int res; + tmp = PyObject_GetAttrString(obj, "target"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &target, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"target\" missing from comprehension"); + return 1; + } + if (PyObject_HasAttrString(obj, "iter")) { + int res; + tmp = PyObject_GetAttrString(obj, "iter"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &iter, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"iter\" missing from comprehension"); + return 1; + } + if (PyObject_HasAttrString(obj, "ifs")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "ifs"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "comprehension field \"ifs\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + ifs = asdl_seq_new(len, arena); + if (ifs == NULL) goto failed; + for (i = 0; i < len; i++) { + expr_ty value; + res = obj2ast_expr(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(ifs, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"ifs\" missing from comprehension"); + return 1; + } + *out = comprehension(target, iter, ifs, arena); + return 0; +failed: + Py_XDECREF(tmp); + return 1; +} + +int +obj2ast_excepthandler(PyObject* obj, excepthandler_ty* out, PyArena* arena) +{ + PyObject* tmp = NULL; + int isinstance; + + int lineno; + int col_offset; + + if (obj == Py_None) { + *out = NULL; + return 0; + } + if (PyObject_HasAttrString(obj, "lineno")) { + int res; + tmp = PyObject_GetAttrString(obj, "lineno"); + if (tmp == NULL) goto failed; + res = obj2ast_int(tmp, &lineno, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"lineno\" missing from excepthandler"); + return 1; + } + if (PyObject_HasAttrString(obj, "col_offset")) { + int res; + tmp = PyObject_GetAttrString(obj, "col_offset"); + if (tmp == NULL) goto failed; + res = obj2ast_int(tmp, &col_offset, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"col_offset\" missing from excepthandler"); + return 1; + } + isinstance = PyObject_IsInstance(obj, (PyObject*)ExceptHandler_type); + if (isinstance == -1) { + return 1; + } + if (isinstance) { + expr_ty type; + expr_ty name; + asdl_seq* body; + + if (PyObject_HasAttrString(obj, "type")) { + int res; + tmp = PyObject_GetAttrString(obj, "type"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &type, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + type = NULL; + } + if (PyObject_HasAttrString(obj, "name")) { + int res; + tmp = PyObject_GetAttrString(obj, "name"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &name, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + name = NULL; + } + if (PyObject_HasAttrString(obj, "body")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "body"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "ExceptHandler field \"body\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + body = asdl_seq_new(len, arena); + if (body == NULL) goto failed; + for (i = 0; i < len; i++) { + stmt_ty value; + res = obj2ast_stmt(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(body, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"body\" missing from ExceptHandler"); + return 1; + } + *out = ExceptHandler(type, name, body, lineno, col_offset, + arena); + if (*out == NULL) goto failed; + return 0; + } + + tmp = PyObject_Repr(obj); + if (tmp == NULL) goto failed; + PyErr_Format(PyExc_TypeError, "expected some sort of excepthandler, but got %.400s", PyString_AS_STRING(tmp)); +failed: + Py_XDECREF(tmp); + return 1; +} + +int +obj2ast_arguments(PyObject* obj, arguments_ty* out, PyArena* arena) +{ + PyObject* tmp = NULL; + asdl_seq* args; + identifier vararg; + identifier kwarg; + asdl_seq* defaults; + + if (PyObject_HasAttrString(obj, "args")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "args"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "arguments field \"args\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + args = asdl_seq_new(len, arena); + if (args == NULL) goto failed; + for (i = 0; i < len; i++) { + expr_ty value; + res = obj2ast_expr(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(args, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"args\" missing from arguments"); + return 1; + } + if (PyObject_HasAttrString(obj, "vararg")) { + int res; + tmp = PyObject_GetAttrString(obj, "vararg"); + if (tmp == NULL) goto failed; + res = obj2ast_identifier(tmp, &vararg, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + vararg = NULL; + } + if (PyObject_HasAttrString(obj, "kwarg")) { + int res; + tmp = PyObject_GetAttrString(obj, "kwarg"); + if (tmp == NULL) goto failed; + res = obj2ast_identifier(tmp, &kwarg, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + kwarg = NULL; + } + if (PyObject_HasAttrString(obj, "defaults")) { + int res; + Py_ssize_t len; + Py_ssize_t i; + tmp = PyObject_GetAttrString(obj, "defaults"); + if (tmp == NULL) goto failed; + if (!PyList_Check(tmp)) { + PyErr_Format(PyExc_TypeError, "arguments field \"defaults\" must be a list, not a %.200s", tmp->ob_type->tp_name); + goto failed; + } + len = PyList_GET_SIZE(tmp); + defaults = asdl_seq_new(len, arena); + if (defaults == NULL) goto failed; + for (i = 0; i < len; i++) { + expr_ty value; + res = obj2ast_expr(PyList_GET_ITEM(tmp, i), &value, arena); + if (res != 0) goto failed; + asdl_seq_SET(defaults, i, value); + } + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"defaults\" missing from arguments"); + return 1; + } + *out = arguments(args, vararg, kwarg, defaults, arena); + return 0; +failed: + Py_XDECREF(tmp); + return 1; +} + +int +obj2ast_keyword(PyObject* obj, keyword_ty* out, PyArena* arena) +{ + PyObject* tmp = NULL; + identifier arg; + expr_ty value; + + if (PyObject_HasAttrString(obj, "arg")) { + int res; + tmp = PyObject_GetAttrString(obj, "arg"); + if (tmp == NULL) goto failed; + res = obj2ast_identifier(tmp, &arg, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"arg\" missing from keyword"); + return 1; + } + if (PyObject_HasAttrString(obj, "value")) { + int res; + tmp = PyObject_GetAttrString(obj, "value"); + if (tmp == NULL) goto failed; + res = obj2ast_expr(tmp, &value, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"value\" missing from keyword"); + return 1; + } + *out = keyword(arg, value, arena); + return 0; +failed: + Py_XDECREF(tmp); + return 1; +} + +int +obj2ast_alias(PyObject* obj, alias_ty* out, PyArena* arena) +{ + PyObject* tmp = NULL; + identifier name; + identifier asname; + + if (PyObject_HasAttrString(obj, "name")) { + int res; + tmp = PyObject_GetAttrString(obj, "name"); + if (tmp == NULL) goto failed; + res = obj2ast_identifier(tmp, &name, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + PyErr_SetString(PyExc_TypeError, "required field \"name\" missing from alias"); + return 1; + } + if (PyObject_HasAttrString(obj, "asname")) { + int res; + tmp = PyObject_GetAttrString(obj, "asname"); + if (tmp == NULL) goto failed; + res = obj2ast_identifier(tmp, &asname, arena); + if (res != 0) goto failed; + Py_XDECREF(tmp); + tmp = NULL; + } else { + asname = NULL; + } + *out = alias(name, asname, arena); + return 0; +failed: + Py_XDECREF(tmp); + return 1; +} + + +PyMODINIT_FUNC +init_ast(void) +{ + PyObject *m, *d; + if (!init_types()) return; + m = Py_InitModule3("_ast", NULL, NULL); + if (!m) return; + d = PyModule_GetDict(m); + if (PyDict_SetItemString(d, "AST", (PyObject*)&AST_type) < 0) return; + if (PyModule_AddIntConstant(m, "PyCF_ONLY_AST", PyCF_ONLY_AST) < 0) + return; + if (PyModule_AddStringConstant(m, "__version__", "82160") < 0) + return; + if (PyDict_SetItemString(d, "mod", (PyObject*)mod_type) < 0) return; + if (PyDict_SetItemString(d, "Module", (PyObject*)Module_type) < 0) + return; + if (PyDict_SetItemString(d, "Interactive", (PyObject*)Interactive_type) + < 0) return; + if (PyDict_SetItemString(d, "Expression", (PyObject*)Expression_type) < + 0) return; + if (PyDict_SetItemString(d, "Suite", (PyObject*)Suite_type) < 0) return; + if (PyDict_SetItemString(d, "stmt", (PyObject*)stmt_type) < 0) return; + if (PyDict_SetItemString(d, "FunctionDef", (PyObject*)FunctionDef_type) + < 0) return; + if (PyDict_SetItemString(d, "ClassDef", (PyObject*)ClassDef_type) < 0) + return; + if (PyDict_SetItemString(d, "Return", (PyObject*)Return_type) < 0) + return; + if (PyDict_SetItemString(d, "Delete", (PyObject*)Delete_type) < 0) + return; + if (PyDict_SetItemString(d, "Assign", (PyObject*)Assign_type) < 0) + return; + if (PyDict_SetItemString(d, "AugAssign", (PyObject*)AugAssign_type) < + 0) return; + if (PyDict_SetItemString(d, "Print", (PyObject*)Print_type) < 0) return; + if (PyDict_SetItemString(d, "For", (PyObject*)For_type) < 0) return; + if (PyDict_SetItemString(d, "While", (PyObject*)While_type) < 0) return; + if (PyDict_SetItemString(d, "If", (PyObject*)If_type) < 0) return; + if (PyDict_SetItemString(d, "With", (PyObject*)With_type) < 0) return; + if (PyDict_SetItemString(d, "Raise", (PyObject*)Raise_type) < 0) return; + if (PyDict_SetItemString(d, "TryExcept", (PyObject*)TryExcept_type) < + 0) return; + if (PyDict_SetItemString(d, "TryFinally", (PyObject*)TryFinally_type) < + 0) return; + if (PyDict_SetItemString(d, "Assert", (PyObject*)Assert_type) < 0) + return; + if (PyDict_SetItemString(d, "Import", (PyObject*)Import_type) < 0) + return; + if (PyDict_SetItemString(d, "ImportFrom", (PyObject*)ImportFrom_type) < + 0) return; + if (PyDict_SetItemString(d, "Exec", (PyObject*)Exec_type) < 0) return; + if (PyDict_SetItemString(d, "Global", (PyObject*)Global_type) < 0) + return; + if (PyDict_SetItemString(d, "Expr", (PyObject*)Expr_type) < 0) return; + if (PyDict_SetItemString(d, "Pass", (PyObject*)Pass_type) < 0) return; + if (PyDict_SetItemString(d, "Break", (PyObject*)Break_type) < 0) return; + if (PyDict_SetItemString(d, "Continue", (PyObject*)Continue_type) < 0) + return; + if (PyDict_SetItemString(d, "expr", (PyObject*)expr_type) < 0) return; + if (PyDict_SetItemString(d, "BoolOp", (PyObject*)BoolOp_type) < 0) + return; + if (PyDict_SetItemString(d, "BinOp", (PyObject*)BinOp_type) < 0) return; + if (PyDict_SetItemString(d, "UnaryOp", (PyObject*)UnaryOp_type) < 0) + return; + if (PyDict_SetItemString(d, "Lambda", (PyObject*)Lambda_type) < 0) + return; + if (PyDict_SetItemString(d, "IfExp", (PyObject*)IfExp_type) < 0) return; + if (PyDict_SetItemString(d, "Dict", (PyObject*)Dict_type) < 0) return; + if (PyDict_SetItemString(d, "Set", (PyObject*)Set_type) < 0) return; + if (PyDict_SetItemString(d, "ListComp", (PyObject*)ListComp_type) < 0) + return; + if (PyDict_SetItemString(d, "SetComp", (PyObject*)SetComp_type) < 0) + return; + if (PyDict_SetItemString(d, "DictComp", (PyObject*)DictComp_type) < 0) + return; + if (PyDict_SetItemString(d, "GeneratorExp", + (PyObject*)GeneratorExp_type) < 0) return; + if (PyDict_SetItemString(d, "Yield", (PyObject*)Yield_type) < 0) return; + if (PyDict_SetItemString(d, "Compare", (PyObject*)Compare_type) < 0) + return; + if (PyDict_SetItemString(d, "Call", (PyObject*)Call_type) < 0) return; + if (PyDict_SetItemString(d, "Repr", (PyObject*)Repr_type) < 0) return; + if (PyDict_SetItemString(d, "Num", (PyObject*)Num_type) < 0) return; + if (PyDict_SetItemString(d, "Str", (PyObject*)Str_type) < 0) return; + if (PyDict_SetItemString(d, "Attribute", (PyObject*)Attribute_type) < + 0) return; + if (PyDict_SetItemString(d, "Subscript", (PyObject*)Subscript_type) < + 0) return; + if (PyDict_SetItemString(d, "Name", (PyObject*)Name_type) < 0) return; + if (PyDict_SetItemString(d, "List", (PyObject*)List_type) < 0) return; + if (PyDict_SetItemString(d, "Tuple", (PyObject*)Tuple_type) < 0) return; + if (PyDict_SetItemString(d, "expr_context", + (PyObject*)expr_context_type) < 0) return; + if (PyDict_SetItemString(d, "Load", (PyObject*)Load_type) < 0) return; + if (PyDict_SetItemString(d, "Store", (PyObject*)Store_type) < 0) return; + if (PyDict_SetItemString(d, "Del", (PyObject*)Del_type) < 0) return; + if (PyDict_SetItemString(d, "AugLoad", (PyObject*)AugLoad_type) < 0) + return; + if (PyDict_SetItemString(d, "AugStore", (PyObject*)AugStore_type) < 0) + return; + if (PyDict_SetItemString(d, "Param", (PyObject*)Param_type) < 0) return; + if (PyDict_SetItemString(d, "slice", (PyObject*)slice_type) < 0) return; + if (PyDict_SetItemString(d, "Ellipsis", (PyObject*)Ellipsis_type) < 0) + return; + if (PyDict_SetItemString(d, "Slice", (PyObject*)Slice_type) < 0) return; + if (PyDict_SetItemString(d, "ExtSlice", (PyObject*)ExtSlice_type) < 0) + return; + if (PyDict_SetItemString(d, "Index", (PyObject*)Index_type) < 0) return; + if (PyDict_SetItemString(d, "boolop", (PyObject*)boolop_type) < 0) + return; + if (PyDict_SetItemString(d, "And", (PyObject*)And_type) < 0) return; + if (PyDict_SetItemString(d, "Or", (PyObject*)Or_type) < 0) return; + if (PyDict_SetItemString(d, "operator", (PyObject*)operator_type) < 0) + return; + if (PyDict_SetItemString(d, "Add", (PyObject*)Add_type) < 0) return; + if (PyDict_SetItemString(d, "Sub", (PyObject*)Sub_type) < 0) return; + if (PyDict_SetItemString(d, "Mult", (PyObject*)Mult_type) < 0) return; + if (PyDict_SetItemString(d, "Div", (PyObject*)Div_type) < 0) return; + if (PyDict_SetItemString(d, "Mod", (PyObject*)Mod_type) < 0) return; + if (PyDict_SetItemString(d, "Pow", (PyObject*)Pow_type) < 0) return; + if (PyDict_SetItemString(d, "LShift", (PyObject*)LShift_type) < 0) + return; + if (PyDict_SetItemString(d, "RShift", (PyObject*)RShift_type) < 0) + return; + if (PyDict_SetItemString(d, "BitOr", (PyObject*)BitOr_type) < 0) return; + if (PyDict_SetItemString(d, "BitXor", (PyObject*)BitXor_type) < 0) + return; + if (PyDict_SetItemString(d, "BitAnd", (PyObject*)BitAnd_type) < 0) + return; + if (PyDict_SetItemString(d, "FloorDiv", (PyObject*)FloorDiv_type) < 0) + return; + if (PyDict_SetItemString(d, "unaryop", (PyObject*)unaryop_type) < 0) + return; + if (PyDict_SetItemString(d, "Invert", (PyObject*)Invert_type) < 0) + return; + if (PyDict_SetItemString(d, "Not", (PyObject*)Not_type) < 0) return; + if (PyDict_SetItemString(d, "UAdd", (PyObject*)UAdd_type) < 0) return; + if (PyDict_SetItemString(d, "USub", (PyObject*)USub_type) < 0) return; + if (PyDict_SetItemString(d, "cmpop", (PyObject*)cmpop_type) < 0) return; + if (PyDict_SetItemString(d, "Eq", (PyObject*)Eq_type) < 0) return; + if (PyDict_SetItemString(d, "NotEq", (PyObject*)NotEq_type) < 0) return; + if (PyDict_SetItemString(d, "Lt", (PyObject*)Lt_type) < 0) return; + if (PyDict_SetItemString(d, "LtE", (PyObject*)LtE_type) < 0) return; + if (PyDict_SetItemString(d, "Gt", (PyObject*)Gt_type) < 0) return; + if (PyDict_SetItemString(d, "GtE", (PyObject*)GtE_type) < 0) return; + if (PyDict_SetItemString(d, "Is", (PyObject*)Is_type) < 0) return; + if (PyDict_SetItemString(d, "IsNot", (PyObject*)IsNot_type) < 0) return; + if (PyDict_SetItemString(d, "In", (PyObject*)In_type) < 0) return; + if (PyDict_SetItemString(d, "NotIn", (PyObject*)NotIn_type) < 0) return; + if (PyDict_SetItemString(d, "comprehension", + (PyObject*)comprehension_type) < 0) return; + if (PyDict_SetItemString(d, "excepthandler", + (PyObject*)excepthandler_type) < 0) return; + if (PyDict_SetItemString(d, "ExceptHandler", + (PyObject*)ExceptHandler_type) < 0) return; + if (PyDict_SetItemString(d, "arguments", (PyObject*)arguments_type) < + 0) return; + if (PyDict_SetItemString(d, "keyword", (PyObject*)keyword_type) < 0) + return; + if (PyDict_SetItemString(d, "alias", (PyObject*)alias_type) < 0) return; +} + + +PyObject* PyAST_mod2obj(mod_ty t) +{ + init_types(); + return ast2obj_mod(t); +} + +/* mode is 0 for "exec", 1 for "eval" and 2 for "single" input */ +mod_ty PyAST_obj2mod(PyObject* ast, PyArena* arena, int mode) +{ + mod_ty res; + PyObject *req_type[3]; + char *req_name[3]; + int isinstance; + + req_type[0] = (PyObject*)Module_type; + req_type[1] = (PyObject*)Expression_type; + req_type[2] = (PyObject*)Interactive_type; + + req_name[0] = "Module"; + req_name[1] = "Expression"; + req_name[2] = "Interactive"; + + assert(0 <= mode && mode <= 2); + + init_types(); + + isinstance = PyObject_IsInstance(ast, req_type[mode]); + if (isinstance == -1) + return NULL; + if (!isinstance) { + PyErr_Format(PyExc_TypeError, "expected %s node, got %.400s", + req_name[mode], Py_TYPE(ast)->tp_name); + return NULL; + } + if (obj2ast_mod(ast, &res, arena) != 0) + return NULL; + else + return res; +} + +int PyAST_Check(PyObject* obj) +{ + init_types(); + return PyObject_IsInstance(obj, (PyObject*)&AST_type); +} + + diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/_warnings.c b/AppPkg/Applications/Python/Python-2.7.10/Python/_warnings.c new file mode 100644 index 0000000000..c880e33c39 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/_warnings.c @@ -0,0 +1,911 @@ +#include "Python.h" +#include "frameobject.h" + +#define MODULE_NAME "_warnings" + +PyDoc_STRVAR(warnings__doc__, +MODULE_NAME " provides basic warning filtering support.\n" +"It is a helper module to speed up interpreter start-up."); + +/* Both 'filters' and 'onceregistry' can be set in warnings.py; + get_warnings_attr() will reset these variables accordingly. */ +static PyObject *_filters; /* List */ +static PyObject *_once_registry; /* Dict */ +static PyObject *_default_action; /* String */ + + +static int +check_matched(PyObject *obj, PyObject *arg) +{ + PyObject *result; + int rc; + + if (obj == Py_None) + return 1; + result = PyObject_CallMethod(obj, "match", "O", arg); + if (result == NULL) + return -1; + + rc = PyObject_IsTrue(result); + Py_DECREF(result); + return rc; +} + +/* + Returns a new reference. + A NULL return value can mean false or an error. +*/ +static PyObject * +get_warnings_attr(const char *attr) +{ + static PyObject *warnings_str = NULL; + PyObject *all_modules; + PyObject *warnings_module; + int result; + + if (warnings_str == NULL) { + warnings_str = PyString_InternFromString("warnings"); + if (warnings_str == NULL) + return NULL; + } + + all_modules = PyImport_GetModuleDict(); + result = PyDict_Contains(all_modules, warnings_str); + if (result == -1 || result == 0) + return NULL; + + warnings_module = PyDict_GetItem(all_modules, warnings_str); + if (!PyObject_HasAttrString(warnings_module, attr)) + return NULL; + return PyObject_GetAttrString(warnings_module, attr); +} + + +static PyObject * +get_once_registry(void) +{ + PyObject *registry; + + registry = get_warnings_attr("onceregistry"); + if (registry == NULL) { + if (PyErr_Occurred()) + return NULL; + return _once_registry; + } + Py_DECREF(_once_registry); + _once_registry = registry; + return registry; +} + + +static PyObject * +get_default_action(void) +{ + PyObject *default_action; + + default_action = get_warnings_attr("defaultaction"); + if (default_action == NULL) { + if (PyErr_Occurred()) { + return NULL; + } + return _default_action; + } + + Py_DECREF(_default_action); + _default_action = default_action; + return default_action; +} + + +/* The item is a borrowed reference. */ +static const char * +get_filter(PyObject *category, PyObject *text, Py_ssize_t lineno, + PyObject *module, PyObject **item) +{ + PyObject *action; + Py_ssize_t i; + PyObject *warnings_filters; + + warnings_filters = get_warnings_attr("filters"); + if (warnings_filters == NULL) { + if (PyErr_Occurred()) + return NULL; + } + else { + Py_DECREF(_filters); + _filters = warnings_filters; + } + + if (!PyList_Check(_filters)) { + PyErr_SetString(PyExc_ValueError, + MODULE_NAME ".filters must be a list"); + return NULL; + } + + /* _filters could change while we are iterating over it. */ + for (i = 0; i < PyList_GET_SIZE(_filters); i++) { + PyObject *tmp_item, *action, *msg, *cat, *mod, *ln_obj; + Py_ssize_t ln; + int is_subclass, good_msg, good_mod; + + tmp_item = *item = PyList_GET_ITEM(_filters, i); + if (PyTuple_Size(tmp_item) != 5) { + PyErr_Format(PyExc_ValueError, + MODULE_NAME ".filters item %zd isn't a 5-tuple", i); + return NULL; + } + + /* Python code: action, msg, cat, mod, ln = item */ + action = PyTuple_GET_ITEM(tmp_item, 0); + msg = PyTuple_GET_ITEM(tmp_item, 1); + cat = PyTuple_GET_ITEM(tmp_item, 2); + mod = PyTuple_GET_ITEM(tmp_item, 3); + ln_obj = PyTuple_GET_ITEM(tmp_item, 4); + + good_msg = check_matched(msg, text); + good_mod = check_matched(mod, module); + is_subclass = PyObject_IsSubclass(category, cat); + ln = PyInt_AsSsize_t(ln_obj); + if (good_msg == -1 || good_mod == -1 || is_subclass == -1 || + (ln == -1 && PyErr_Occurred())) + return NULL; + + if (good_msg && is_subclass && good_mod && (ln == 0 || lineno == ln)) + return PyString_AsString(action); + } + + action = get_default_action(); + if (action != NULL) { + return PyString_AsString(action); + } + + PyErr_SetString(PyExc_ValueError, + MODULE_NAME ".defaultaction not found"); + return NULL; +} + + +static int +already_warned(PyObject *registry, PyObject *key, int should_set) +{ + PyObject *already_warned; + + if (key == NULL) + return -1; + + already_warned = PyDict_GetItem(registry, key); + if (already_warned != NULL) { + int rc = PyObject_IsTrue(already_warned); + if (rc != 0) + return rc; + } + + /* This warning wasn't found in the registry, set it. */ + if (should_set) + return PyDict_SetItem(registry, key, Py_True); + return 0; +} + +/* New reference. */ +static PyObject * +normalize_module(PyObject *filename) +{ + PyObject *module; + const char *mod_str; + Py_ssize_t len; + + int rc = PyObject_IsTrue(filename); + if (rc == -1) + return NULL; + else if (rc == 0) + return PyString_FromString(""); + + mod_str = PyString_AsString(filename); + if (mod_str == NULL) + return NULL; + len = PyString_Size(filename); + if (len < 0) + return NULL; + if (len >= 3 && + strncmp(mod_str + (len - 3), ".py", 3) == 0) { + module = PyString_FromStringAndSize(mod_str, len-3); + } + else { + module = filename; + Py_INCREF(module); + } + return module; +} + +static int +update_registry(PyObject *registry, PyObject *text, PyObject *category, + int add_zero) +{ + PyObject *altkey, *zero = NULL; + int rc; + + if (add_zero) { + zero = PyInt_FromLong(0); + if (zero == NULL) + return -1; + altkey = PyTuple_Pack(3, text, category, zero); + } + else + altkey = PyTuple_Pack(2, text, category); + + rc = already_warned(registry, altkey, 1); + Py_XDECREF(zero); + Py_XDECREF(altkey); + return rc; +} + +static void +show_warning(PyObject *filename, int lineno, PyObject *text, PyObject + *category, PyObject *sourceline) +{ + PyObject *f_stderr; + PyObject *name; + char lineno_str[128]; + + PyOS_snprintf(lineno_str, sizeof(lineno_str), ":%d: ", lineno); + + name = PyObject_GetAttrString(category, "__name__"); + if (name == NULL) /* XXX Can an object lack a '__name__' attribute? */ + return; + + f_stderr = PySys_GetObject("stderr"); + if (f_stderr == NULL) { + fprintf(stderr, "lost sys.stderr\n"); + Py_DECREF(name); + return; + } + + /* Print "filename:lineno: category: text\n" */ + PyFile_WriteObject(filename, f_stderr, Py_PRINT_RAW); + PyFile_WriteString(lineno_str, f_stderr); + PyFile_WriteObject(name, f_stderr, Py_PRINT_RAW); + PyFile_WriteString(": ", f_stderr); + PyFile_WriteObject(text, f_stderr, Py_PRINT_RAW); + PyFile_WriteString("\n", f_stderr); + Py_XDECREF(name); + + /* Print " source_line\n" */ + if (sourceline) { + char *source_line_str = PyString_AS_STRING(sourceline); + while (*source_line_str == ' ' || *source_line_str == '\t' || + *source_line_str == '\014') + source_line_str++; + + PyFile_WriteString(source_line_str, f_stderr); + PyFile_WriteString("\n", f_stderr); + } + else + _Py_DisplaySourceLine(f_stderr, PyString_AS_STRING(filename), + lineno, 2); + PyErr_Clear(); +} + +static PyObject * +warn_explicit(PyObject *category, PyObject *message, + PyObject *filename, int lineno, + PyObject *module, PyObject *registry, PyObject *sourceline) +{ + PyObject *key = NULL, *text = NULL, *result = NULL, *lineno_obj = NULL; + PyObject *item = Py_None; + const char *action; + int rc; + + if (registry && !PyDict_Check(registry) && (registry != Py_None)) { + PyErr_SetString(PyExc_TypeError, "'registry' must be a dict"); + return NULL; + } + + /* Normalize module. */ + if (module == NULL) { + module = normalize_module(filename); + if (module == NULL) + return NULL; + } + else + Py_INCREF(module); + + /* Normalize message. */ + Py_INCREF(message); /* DECREF'ed in cleanup. */ + rc = PyObject_IsInstance(message, PyExc_Warning); + if (rc == -1) { + goto cleanup; + } + if (rc == 1) { + text = PyObject_Str(message); + if (text == NULL) + goto cleanup; + category = (PyObject*)message->ob_type; + } + else { + text = message; + message = PyObject_CallFunction(category, "O", message); + if (message == NULL) + goto cleanup; + } + + lineno_obj = PyInt_FromLong(lineno); + if (lineno_obj == NULL) + goto cleanup; + + /* Create key. */ + key = PyTuple_Pack(3, text, category, lineno_obj); + if (key == NULL) + goto cleanup; + + if ((registry != NULL) && (registry != Py_None)) { + rc = already_warned(registry, key, 0); + if (rc == -1) + goto cleanup; + else if (rc == 1) + goto return_none; + /* Else this warning hasn't been generated before. */ + } + + action = get_filter(category, text, lineno, module, &item); + if (action == NULL) + goto cleanup; + + if (strcmp(action, "error") == 0) { + PyErr_SetObject(category, message); + goto cleanup; + } + + /* Store in the registry that we've been here, *except* when the action + is "always". */ + rc = 0; + if (strcmp(action, "always") != 0) { + if (registry != NULL && registry != Py_None && + PyDict_SetItem(registry, key, Py_True) < 0) + goto cleanup; + else if (strcmp(action, "ignore") == 0) + goto return_none; + else if (strcmp(action, "once") == 0) { + if (registry == NULL || registry == Py_None) { + registry = get_once_registry(); + if (registry == NULL) + goto cleanup; + } + /* _once_registry[(text, category)] = 1 */ + rc = update_registry(registry, text, category, 0); + } + else if (strcmp(action, "module") == 0) { + /* registry[(text, category, 0)] = 1 */ + if (registry != NULL && registry != Py_None) + rc = update_registry(registry, text, category, 0); + } + else if (strcmp(action, "default") != 0) { + PyObject *to_str = PyObject_Str(item); + const char *err_str = "???"; + + if (to_str != NULL) + err_str = PyString_AS_STRING(to_str); + PyErr_Format(PyExc_RuntimeError, + "Unrecognized action (%s) in warnings.filters:\n %s", + action, err_str); + Py_XDECREF(to_str); + goto cleanup; + } + } + + if (rc == 1) /* Already warned for this module. */ + goto return_none; + if (rc == 0) { + PyObject *show_fxn = get_warnings_attr("showwarning"); + if (show_fxn == NULL) { + if (PyErr_Occurred()) + goto cleanup; + show_warning(filename, lineno, text, category, sourceline); + } + else { + PyObject *res; + + if (!PyMethod_Check(show_fxn) && !PyFunction_Check(show_fxn)) { + PyErr_SetString(PyExc_TypeError, + "warnings.showwarning() must be set to a " + "function or method"); + Py_DECREF(show_fxn); + goto cleanup; + } + + res = PyObject_CallFunctionObjArgs(show_fxn, message, category, + filename, lineno_obj, + NULL); + Py_DECREF(show_fxn); + Py_XDECREF(res); + if (res == NULL) + goto cleanup; + } + } + else /* if (rc == -1) */ + goto cleanup; + + return_none: + result = Py_None; + Py_INCREF(result); + + cleanup: + Py_XDECREF(key); + Py_XDECREF(text); + Py_XDECREF(lineno_obj); + Py_DECREF(module); + Py_XDECREF(message); + return result; /* Py_None or NULL. */ +} + +/* filename, module, and registry are new refs, globals is borrowed */ +/* Returns 0 on error (no new refs), 1 on success */ +static int +setup_context(Py_ssize_t stack_level, PyObject **filename, int *lineno, + PyObject **module, PyObject **registry) +{ + PyObject *globals; + + /* Setup globals and lineno. */ + PyFrameObject *f = PyThreadState_GET()->frame; + while (--stack_level > 0 && f != NULL) + f = f->f_back; + + if (f == NULL) { + globals = PyThreadState_Get()->interp->sysdict; + *lineno = 1; + } + else { + globals = f->f_globals; + *lineno = PyFrame_GetLineNumber(f); + } + + *module = NULL; + + /* Setup registry. */ + assert(globals != NULL); + assert(PyDict_Check(globals)); + *registry = PyDict_GetItemString(globals, "__warningregistry__"); + if (*registry == NULL) { + int rc; + + *registry = PyDict_New(); + if (*registry == NULL) + return 0; + + rc = PyDict_SetItemString(globals, "__warningregistry__", *registry); + if (rc < 0) + goto handle_error; + } + else + Py_INCREF(*registry); + + /* Setup module. */ + *module = PyDict_GetItemString(globals, "__name__"); + if (*module == NULL) { + *module = PyString_FromString(""); + if (*module == NULL) + goto handle_error; + } + else + Py_INCREF(*module); + + /* Setup filename. */ + *filename = PyDict_GetItemString(globals, "__file__"); + if (*filename != NULL && PyString_Check(*filename)) { + Py_ssize_t len = PyString_Size(*filename); + const char *file_str = PyString_AsString(*filename); + if (file_str == NULL || (len < 0 && PyErr_Occurred())) + goto handle_error; + + /* if filename.lower().endswith((".pyc", ".pyo")): */ + if (len >= 4 && + file_str[len-4] == '.' && + tolower(file_str[len-3]) == 'p' && + tolower(file_str[len-2]) == 'y' && + (tolower(file_str[len-1]) == 'c' || + tolower(file_str[len-1]) == 'o')) + { + *filename = PyString_FromStringAndSize(file_str, len-1); + if (*filename == NULL) + goto handle_error; + } + else + Py_INCREF(*filename); + } + else { + const char *module_str = PyString_AsString(*module); + *filename = NULL; + if (module_str && strcmp(module_str, "__main__") == 0) { + PyObject *argv = PySys_GetObject("argv"); + if (argv != NULL && PyList_Size(argv) > 0) { + int is_true; + *filename = PyList_GetItem(argv, 0); + Py_INCREF(*filename); + /* If sys.argv[0] is false, then use '__main__'. */ + is_true = PyObject_IsTrue(*filename); + if (is_true < 0) { + Py_DECREF(*filename); + goto handle_error; + } + else if (!is_true) { + Py_DECREF(*filename); + *filename = PyString_FromString("__main__"); + if (*filename == NULL) + goto handle_error; + } + } + else { + /* embedded interpreters don't have sys.argv, see bug #839151 */ + *filename = PyString_FromString("__main__"); + if (*filename == NULL) + goto handle_error; + } + } + if (*filename == NULL) { + *filename = *module; + Py_INCREF(*filename); + } + } + + return 1; + + handle_error: + /* filename not XDECREF'ed here as there is no way to jump here with a + dangling reference. */ + Py_XDECREF(*registry); + Py_XDECREF(*module); + return 0; +} + +static PyObject * +get_category(PyObject *message, PyObject *category) +{ + int rc; + + /* Get category. */ + rc = PyObject_IsInstance(message, PyExc_Warning); + if (rc == -1) + return NULL; + + if (rc == 1) + category = (PyObject*)message->ob_type; + else if (category == NULL) + category = PyExc_UserWarning; + + /* Validate category. */ + rc = PyObject_IsSubclass(category, PyExc_Warning); + if (rc == -1) + return NULL; + if (rc == 0) { + PyErr_SetString(PyExc_ValueError, + "category is not a subclass of Warning"); + return NULL; + } + + return category; +} + +static PyObject * +do_warn(PyObject *message, PyObject *category, Py_ssize_t stack_level) +{ + PyObject *filename, *module, *registry, *res; + int lineno; + + if (!setup_context(stack_level, &filename, &lineno, &module, ®istry)) + return NULL; + + res = warn_explicit(category, message, filename, lineno, module, registry, + NULL); + Py_DECREF(filename); + Py_DECREF(registry); + Py_DECREF(module); + return res; +} + +static PyObject * +warnings_warn(PyObject *self, PyObject *args, PyObject *kwds) +{ + static char *kw_list[] = { "message", "category", "stacklevel", 0 }; + PyObject *message, *category = NULL; + Py_ssize_t stack_level = 1; + + if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|On:warn", kw_list, + &message, &category, &stack_level)) + return NULL; + + category = get_category(message, category); + if (category == NULL) + return NULL; + return do_warn(message, category, stack_level); +} + +static PyObject * +warnings_warn_explicit(PyObject *self, PyObject *args, PyObject *kwds) +{ + static char *kwd_list[] = {"message", "category", "filename", "lineno", + "module", "registry", "module_globals", 0}; + PyObject *message; + PyObject *category; + PyObject *filename; + int lineno; + PyObject *module = NULL; + PyObject *registry = NULL; + PyObject *module_globals = NULL; + + if (!PyArg_ParseTupleAndKeywords(args, kwds, "OOOi|OOO:warn_explicit", + kwd_list, &message, &category, &filename, &lineno, &module, + ®istry, &module_globals)) + return NULL; + + if (module_globals) { + static PyObject *get_source_name = NULL; + static PyObject *splitlines_name = NULL; + PyObject *loader; + PyObject *module_name; + PyObject *source; + PyObject *source_list; + PyObject *source_line; + PyObject *returned; + + if (get_source_name == NULL) { + get_source_name = PyString_InternFromString("get_source"); + if (!get_source_name) + return NULL; + } + if (splitlines_name == NULL) { + splitlines_name = PyString_InternFromString("splitlines"); + if (!splitlines_name) + return NULL; + } + + /* Check/get the requisite pieces needed for the loader. */ + loader = PyDict_GetItemString(module_globals, "__loader__"); + module_name = PyDict_GetItemString(module_globals, "__name__"); + + if (loader == NULL || module_name == NULL) + goto standard_call; + + /* Make sure the loader implements the optional get_source() method. */ + if (!PyObject_HasAttrString(loader, "get_source")) + goto standard_call; + /* Call get_source() to get the source code. */ + source = PyObject_CallMethodObjArgs(loader, get_source_name, + module_name, NULL); + if (!source) + return NULL; + else if (source == Py_None) { + Py_DECREF(Py_None); + goto standard_call; + } + + /* Split the source into lines. */ + source_list = PyObject_CallMethodObjArgs(source, splitlines_name, + NULL); + Py_DECREF(source); + if (!source_list) + return NULL; + + /* Get the source line. */ + source_line = PyList_GetItem(source_list, lineno-1); + if (!source_line) { + Py_DECREF(source_list); + return NULL; + } + + /* Handle the warning. */ + returned = warn_explicit(category, message, filename, lineno, module, + registry, source_line); + Py_DECREF(source_list); + return returned; + } + + standard_call: + return warn_explicit(category, message, filename, lineno, module, + registry, NULL); +} + + +/* Function to issue a warning message; may raise an exception. */ +int +PyErr_WarnEx(PyObject *category, const char *text, Py_ssize_t stack_level) +{ + PyObject *res; + PyObject *message = PyString_FromString(text); + if (message == NULL) + return -1; + + if (category == NULL) + category = PyExc_RuntimeWarning; + + res = do_warn(message, category, stack_level); + Py_DECREF(message); + if (res == NULL) + return -1; + Py_DECREF(res); + + return 0; +} + +/* PyErr_Warn is only for backwards compatibility and will be removed. + Use PyErr_WarnEx instead. */ + +#undef PyErr_Warn + +PyAPI_FUNC(int) +PyErr_Warn(PyObject *category, char *text) +{ + return PyErr_WarnEx(category, text, 1); +} + +/* Warning with explicit origin */ +int +PyErr_WarnExplicit(PyObject *category, const char *text, + const char *filename_str, int lineno, + const char *module_str, PyObject *registry) +{ + PyObject *res; + PyObject *message = PyString_FromString(text); + PyObject *filename = PyString_FromString(filename_str); + PyObject *module = NULL; + int ret = -1; + + if (message == NULL || filename == NULL) + goto exit; + if (module_str != NULL) { + module = PyString_FromString(module_str); + if (module == NULL) + goto exit; + } + + if (category == NULL) + category = PyExc_RuntimeWarning; + res = warn_explicit(category, message, filename, lineno, module, registry, + NULL); + if (res == NULL) + goto exit; + Py_DECREF(res); + ret = 0; + + exit: + Py_XDECREF(message); + Py_XDECREF(module); + Py_XDECREF(filename); + return ret; +} + + +PyDoc_STRVAR(warn_doc, +"Issue a warning, or maybe ignore it or raise an exception."); + +PyDoc_STRVAR(warn_explicit_doc, +"Low-level inferface to warnings functionality."); + +static PyMethodDef warnings_functions[] = { + {"warn", (PyCFunction)warnings_warn, METH_VARARGS | METH_KEYWORDS, + warn_doc}, + {"warn_explicit", (PyCFunction)warnings_warn_explicit, + METH_VARARGS | METH_KEYWORDS, warn_explicit_doc}, + /* XXX(brett.cannon): add showwarning? */ + /* XXX(brett.cannon): Reasonable to add formatwarning? */ + {NULL, NULL} /* sentinel */ +}; + + +static PyObject * +create_filter(PyObject *category, const char *action) +{ + static PyObject *ignore_str = NULL; + static PyObject *error_str = NULL; + static PyObject *default_str = NULL; + PyObject *action_obj = NULL; + PyObject *lineno, *result; + + if (!strcmp(action, "ignore")) { + if (ignore_str == NULL) { + ignore_str = PyString_InternFromString("ignore"); + if (ignore_str == NULL) + return NULL; + } + action_obj = ignore_str; + } + else if (!strcmp(action, "error")) { + if (error_str == NULL) { + error_str = PyString_InternFromString("error"); + if (error_str == NULL) + return NULL; + } + action_obj = error_str; + } + else if (!strcmp(action, "default")) { + if (default_str == NULL) { + default_str = PyString_InternFromString("default"); + if (default_str == NULL) + return NULL; + } + action_obj = default_str; + } + else { + Py_FatalError("unknown action"); + } + + /* This assumes the line number is zero for now. */ + lineno = PyInt_FromLong(0); + if (lineno == NULL) + return NULL; + result = PyTuple_Pack(5, action_obj, Py_None, category, Py_None, lineno); + Py_DECREF(lineno); + return result; +} + +static PyObject * +init_filters(void) +{ + /* Don't silence DeprecationWarning if -3 or -Q were used. */ + PyObject *filters = PyList_New(Py_Py3kWarningFlag || + Py_DivisionWarningFlag ? 3 : 4); + unsigned int pos = 0; /* Post-incremented in each use. */ + unsigned int x; + const char *bytes_action; + + if (filters == NULL) + return NULL; + + /* If guard changes, make sure to update 'filters' initialization above. */ + if (!Py_Py3kWarningFlag && !Py_DivisionWarningFlag) { + PyList_SET_ITEM(filters, pos++, + create_filter(PyExc_DeprecationWarning, "ignore")); + } + PyList_SET_ITEM(filters, pos++, + create_filter(PyExc_PendingDeprecationWarning, "ignore")); + PyList_SET_ITEM(filters, pos++, + create_filter(PyExc_ImportWarning, "ignore")); + if (Py_BytesWarningFlag > 1) + bytes_action = "error"; + else if (Py_BytesWarningFlag) + bytes_action = "default"; + else + bytes_action = "ignore"; + PyList_SET_ITEM(filters, pos++, create_filter(PyExc_BytesWarning, + bytes_action)); + + for (x = 0; x < pos; x += 1) { + if (PyList_GET_ITEM(filters, x) == NULL) { + Py_DECREF(filters); + return NULL; + } + } + + return filters; +} + + +PyMODINIT_FUNC +_PyWarnings_Init(void) +{ + PyObject *m; + + m = Py_InitModule3(MODULE_NAME, warnings_functions, warnings__doc__); + if (m == NULL) + return; + + _filters = init_filters(); + if (_filters == NULL) + return; + Py_INCREF(_filters); + if (PyModule_AddObject(m, "filters", _filters) < 0) + return; + + _once_registry = PyDict_New(); + if (_once_registry == NULL) + return; + Py_INCREF(_once_registry); + if (PyModule_AddObject(m, "once_registry", _once_registry) < 0) + return; + + _default_action = PyString_FromString("default"); + if (_default_action == NULL) + return; + Py_INCREF(_default_action); + if (PyModule_AddObject(m, "default_action", _default_action) < 0) + return; +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/asdl.c b/AppPkg/Applications/Python/Python-2.7.10/Python/asdl.c new file mode 100644 index 0000000000..570575815e --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/asdl.c @@ -0,0 +1,64 @@ +#include "Python.h" +#include "asdl.h" + +asdl_seq * +asdl_seq_new(int size, PyArena *arena) +{ + asdl_seq *seq = NULL; + size_t n = (size ? (sizeof(void *) * (size - 1)) : 0); + + /* check size is sane */ + if (size < 0 || size == INT_MIN || + (size && ((size - 1) > (PY_SIZE_MAX / sizeof(void *))))) { + PyErr_NoMemory(); + return NULL; + } + + /* check if size can be added safely */ + if (n > PY_SIZE_MAX - sizeof(asdl_seq)) { + PyErr_NoMemory(); + return NULL; + } + + n += sizeof(asdl_seq); + + seq = (asdl_seq *)PyArena_Malloc(arena, n); + if (!seq) { + PyErr_NoMemory(); + return NULL; + } + memset(seq, 0, n); + seq->size = size; + return seq; +} + +asdl_int_seq * +asdl_int_seq_new(int size, PyArena *arena) +{ + asdl_int_seq *seq = NULL; + size_t n = (size ? (sizeof(void *) * (size - 1)) : 0); + + /* check size is sane */ + if (size < 0 || size == INT_MIN || + (size && ((size - 1) > (PY_SIZE_MAX / sizeof(void *))))) { + PyErr_NoMemory(); + return NULL; + } + + /* check if size can be added safely */ + if (n > PY_SIZE_MAX - sizeof(asdl_seq)) { + PyErr_NoMemory(); + return NULL; + } + + n += sizeof(asdl_seq); + + seq = (asdl_int_seq *)PyArena_Malloc(arena, n); + if (!seq) { + PyErr_NoMemory(); + return NULL; + } + memset(seq, 0, n); + seq->size = size; + return seq; +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/ast.c b/AppPkg/Applications/Python/Python-2.7.10/Python/ast.c new file mode 100644 index 0000000000..2ec1514c53 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/ast.c @@ -0,0 +1,3587 @@ +/* + * This file includes functions to transform a concrete syntax tree (CST) to + * an abstract syntax tree (AST). The main function is PyAST_FromNode(). + * + */ +#include "Python.h" +#include "Python-ast.h" +#include "grammar.h" +#include "node.h" +#include "pyarena.h" +#include "ast.h" +#include "token.h" +#include "parsetok.h" +#include "graminit.h" + +#include + +/* Data structure used internally */ +struct compiling { + char *c_encoding; /* source encoding */ + int c_future_unicode; /* __future__ unicode literals flag */ + PyArena *c_arena; /* arena for allocating memeory */ + const char *c_filename; /* filename */ +}; + +static asdl_seq *seq_for_testlist(struct compiling *, const node *); +static expr_ty ast_for_expr(struct compiling *, const node *); +static stmt_ty ast_for_stmt(struct compiling *, const node *); +static asdl_seq *ast_for_suite(struct compiling *, const node *); +static asdl_seq *ast_for_exprlist(struct compiling *, const node *, + expr_context_ty); +static expr_ty ast_for_testlist(struct compiling *, const node *); +static stmt_ty ast_for_classdef(struct compiling *, const node *, asdl_seq *); +static expr_ty ast_for_testlist_comp(struct compiling *, const node *); + +/* Note different signature for ast_for_call */ +static expr_ty ast_for_call(struct compiling *, const node *, expr_ty); + +static PyObject *parsenumber(struct compiling *, const char *); +static PyObject *parsestr(struct compiling *, const node *n, const char *); +static PyObject *parsestrplus(struct compiling *, const node *n); + +#ifndef LINENO +#define LINENO(n) ((n)->n_lineno) +#endif + +#define COMP_GENEXP 0 +#define COMP_SETCOMP 1 + +static identifier +new_identifier(const char* n, PyArena *arena) { + PyObject* id = PyString_InternFromString(n); + if (id != NULL) + PyArena_AddPyObject(arena, id); + return id; +} + +#define NEW_IDENTIFIER(n) new_identifier(STR(n), c->c_arena) + +/* This routine provides an invalid object for the syntax error. + The outermost routine must unpack this error and create the + proper object. We do this so that we don't have to pass + the filename to everything function. + + XXX Maybe we should just pass the filename... +*/ + +static int +ast_error(const node *n, const char *errstr) +{ + PyObject *u = Py_BuildValue("zi", errstr, LINENO(n)); + if (!u) + return 0; + PyErr_SetObject(PyExc_SyntaxError, u); + Py_DECREF(u); + return 0; +} + +static void +ast_error_finish(const char *filename) +{ + PyObject *type, *value, *tback, *errstr, *loc, *tmp; + long lineno; + + assert(PyErr_Occurred()); + if (!PyErr_ExceptionMatches(PyExc_SyntaxError)) + return; + + PyErr_Fetch(&type, &value, &tback); + errstr = PyTuple_GetItem(value, 0); + if (!errstr) + return; + Py_INCREF(errstr); + lineno = PyInt_AsLong(PyTuple_GetItem(value, 1)); + if (lineno == -1) { + Py_DECREF(errstr); + return; + } + Py_DECREF(value); + + loc = PyErr_ProgramText(filename, lineno); + if (!loc) { + Py_INCREF(Py_None); + loc = Py_None; + } + tmp = Py_BuildValue("(zlOO)", filename, lineno, Py_None, loc); + Py_DECREF(loc); + if (!tmp) { + Py_DECREF(errstr); + return; + } + value = PyTuple_Pack(2, errstr, tmp); + Py_DECREF(errstr); + Py_DECREF(tmp); + if (!value) + return; + PyErr_Restore(type, value, tback); +} + +static int +ast_warn(struct compiling *c, const node *n, char *msg) +{ + if (PyErr_WarnExplicit(PyExc_SyntaxWarning, msg, c->c_filename, LINENO(n), + NULL, NULL) < 0) { + /* if -Werr, change it to a SyntaxError */ + if (PyErr_Occurred() && PyErr_ExceptionMatches(PyExc_SyntaxWarning)) + ast_error(n, msg); + return 0; + } + return 1; +} + +static int +forbidden_check(struct compiling *c, const node *n, const char *x) +{ + if (!strcmp(x, "None")) + return ast_error(n, "cannot assign to None"); + if (!strcmp(x, "__debug__")) + return ast_error(n, "cannot assign to __debug__"); + if (Py_Py3kWarningFlag) { + if (!(strcmp(x, "True") && strcmp(x, "False")) && + !ast_warn(c, n, "assignment to True or False is forbidden in 3.x")) + return 0; + if (!strcmp(x, "nonlocal") && + !ast_warn(c, n, "nonlocal is a keyword in 3.x")) + return 0; + } + return 1; +} + +/* num_stmts() returns number of contained statements. + + Use this routine to determine how big a sequence is needed for + the statements in a parse tree. Its raison d'etre is this bit of + grammar: + + stmt: simple_stmt | compound_stmt + simple_stmt: small_stmt (';' small_stmt)* [';'] NEWLINE + + A simple_stmt can contain multiple small_stmt elements joined + by semicolons. If the arg is a simple_stmt, the number of + small_stmt elements is returned. +*/ + +static int +num_stmts(const node *n) +{ + int i, l; + node *ch; + + switch (TYPE(n)) { + case single_input: + if (TYPE(CHILD(n, 0)) == NEWLINE) + return 0; + else + return num_stmts(CHILD(n, 0)); + case file_input: + l = 0; + for (i = 0; i < NCH(n); i++) { + ch = CHILD(n, i); + if (TYPE(ch) == stmt) + l += num_stmts(ch); + } + return l; + case stmt: + return num_stmts(CHILD(n, 0)); + case compound_stmt: + return 1; + case simple_stmt: + return NCH(n) / 2; /* Divide by 2 to remove count of semi-colons */ + case suite: + if (NCH(n) == 1) + return num_stmts(CHILD(n, 0)); + else { + l = 0; + for (i = 2; i < (NCH(n) - 1); i++) + l += num_stmts(CHILD(n, i)); + return l; + } + default: { + char buf[128]; + + sprintf(buf, "Non-statement found: %d %d", + TYPE(n), NCH(n)); + Py_FatalError(buf); + } + } + assert(0); + return 0; +} + +/* Transform the CST rooted at node * to the appropriate AST +*/ + +mod_ty +PyAST_FromNode(const node *n, PyCompilerFlags *flags, const char *filename, + PyArena *arena) +{ + int i, j, k, num; + asdl_seq *stmts = NULL; + stmt_ty s; + node *ch; + struct compiling c; + + if (flags && flags->cf_flags & PyCF_SOURCE_IS_UTF8) { + c.c_encoding = "utf-8"; + if (TYPE(n) == encoding_decl) { + ast_error(n, "encoding declaration in Unicode string"); + goto error; + } + } else if (TYPE(n) == encoding_decl) { + c.c_encoding = STR(n); + n = CHILD(n, 0); + } else { + c.c_encoding = NULL; + } + c.c_future_unicode = flags && flags->cf_flags & CO_FUTURE_UNICODE_LITERALS; + c.c_arena = arena; + c.c_filename = filename; + + k = 0; + switch (TYPE(n)) { + case file_input: + stmts = asdl_seq_new(num_stmts(n), arena); + if (!stmts) + return NULL; + for (i = 0; i < NCH(n) - 1; i++) { + ch = CHILD(n, i); + if (TYPE(ch) == NEWLINE) + continue; + REQ(ch, stmt); + num = num_stmts(ch); + if (num == 1) { + s = ast_for_stmt(&c, ch); + if (!s) + goto error; + asdl_seq_SET(stmts, k++, s); + } + else { + ch = CHILD(ch, 0); + REQ(ch, simple_stmt); + for (j = 0; j < num; j++) { + s = ast_for_stmt(&c, CHILD(ch, j * 2)); + if (!s) + goto error; + asdl_seq_SET(stmts, k++, s); + } + } + } + return Module(stmts, arena); + case eval_input: { + expr_ty testlist_ast; + + /* XXX Why not comp_for here? */ + testlist_ast = ast_for_testlist(&c, CHILD(n, 0)); + if (!testlist_ast) + goto error; + return Expression(testlist_ast, arena); + } + case single_input: + if (TYPE(CHILD(n, 0)) == NEWLINE) { + stmts = asdl_seq_new(1, arena); + if (!stmts) + goto error; + asdl_seq_SET(stmts, 0, Pass(n->n_lineno, n->n_col_offset, + arena)); + if (!asdl_seq_GET(stmts, 0)) + goto error; + return Interactive(stmts, arena); + } + else { + n = CHILD(n, 0); + num = num_stmts(n); + stmts = asdl_seq_new(num, arena); + if (!stmts) + goto error; + if (num == 1) { + s = ast_for_stmt(&c, n); + if (!s) + goto error; + asdl_seq_SET(stmts, 0, s); + } + else { + /* Only a simple_stmt can contain multiple statements. */ + REQ(n, simple_stmt); + for (i = 0; i < NCH(n); i += 2) { + if (TYPE(CHILD(n, i)) == NEWLINE) + break; + s = ast_for_stmt(&c, CHILD(n, i)); + if (!s) + goto error; + asdl_seq_SET(stmts, i / 2, s); + } + } + + return Interactive(stmts, arena); + } + default: + PyErr_Format(PyExc_SystemError, + "invalid node %d for PyAST_FromNode", TYPE(n)); + goto error; + } + error: + ast_error_finish(filename); + return NULL; +} + +/* Return the AST repr. of the operator represented as syntax (|, ^, etc.) +*/ + +static operator_ty +get_operator(const node *n) +{ + switch (TYPE(n)) { + case VBAR: + return BitOr; + case CIRCUMFLEX: + return BitXor; + case AMPER: + return BitAnd; + case LEFTSHIFT: + return LShift; + case RIGHTSHIFT: + return RShift; + case PLUS: + return Add; + case MINUS: + return Sub; + case STAR: + return Mult; + case SLASH: + return Div; + case DOUBLESLASH: + return FloorDiv; + case PERCENT: + return Mod; + default: + return (operator_ty)0; + } +} + +/* Set the context ctx for expr_ty e, recursively traversing e. + + Only sets context for expr kinds that "can appear in assignment context" + (according to ../Parser/Python.asdl). For other expr kinds, it sets + an appropriate syntax error and returns false. +*/ + +static int +set_context(struct compiling *c, expr_ty e, expr_context_ty ctx, const node *n) +{ + asdl_seq *s = NULL; + /* If a particular expression type can't be used for assign / delete, + set expr_name to its name and an error message will be generated. + */ + const char* expr_name = NULL; + + /* The ast defines augmented store and load contexts, but the + implementation here doesn't actually use them. The code may be + a little more complex than necessary as a result. It also means + that expressions in an augmented assignment have a Store context. + Consider restructuring so that augmented assignment uses + set_context(), too. + */ + assert(ctx != AugStore && ctx != AugLoad); + + switch (e->kind) { + case Attribute_kind: + if (ctx == Store && !forbidden_check(c, n, + PyBytes_AS_STRING(e->v.Attribute.attr))) + return 0; + e->v.Attribute.ctx = ctx; + break; + case Subscript_kind: + e->v.Subscript.ctx = ctx; + break; + case Name_kind: + if (ctx == Store && !forbidden_check(c, n, + PyBytes_AS_STRING(e->v.Name.id))) + return 0; + e->v.Name.ctx = ctx; + break; + case List_kind: + e->v.List.ctx = ctx; + s = e->v.List.elts; + break; + case Tuple_kind: + if (asdl_seq_LEN(e->v.Tuple.elts)) { + e->v.Tuple.ctx = ctx; + s = e->v.Tuple.elts; + } + else { + expr_name = "()"; + } + break; + case Lambda_kind: + expr_name = "lambda"; + break; + case Call_kind: + expr_name = "function call"; + break; + case BoolOp_kind: + case BinOp_kind: + case UnaryOp_kind: + expr_name = "operator"; + break; + case GeneratorExp_kind: + expr_name = "generator expression"; + break; + case Yield_kind: + expr_name = "yield expression"; + break; + case ListComp_kind: + expr_name = "list comprehension"; + break; + case SetComp_kind: + expr_name = "set comprehension"; + break; + case DictComp_kind: + expr_name = "dict comprehension"; + break; + case Dict_kind: + case Set_kind: + case Num_kind: + case Str_kind: + expr_name = "literal"; + break; + case Compare_kind: + expr_name = "comparison"; + break; + case Repr_kind: + expr_name = "repr"; + break; + case IfExp_kind: + expr_name = "conditional expression"; + break; + default: + PyErr_Format(PyExc_SystemError, + "unexpected expression in assignment %d (line %d)", + e->kind, e->lineno); + return 0; + } + /* Check for error string set by switch */ + if (expr_name) { + char buf[300]; + PyOS_snprintf(buf, sizeof(buf), + "can't %s %s", + ctx == Store ? "assign to" : "delete", + expr_name); + return ast_error(n, buf); + } + + /* If the LHS is a list or tuple, we need to set the assignment + context for all the contained elements. + */ + if (s) { + int i; + + for (i = 0; i < asdl_seq_LEN(s); i++) { + if (!set_context(c, (expr_ty)asdl_seq_GET(s, i), ctx, n)) + return 0; + } + } + return 1; +} + +static operator_ty +ast_for_augassign(struct compiling *c, const node *n) +{ + REQ(n, augassign); + n = CHILD(n, 0); + switch (STR(n)[0]) { + case '+': + return Add; + case '-': + return Sub; + case '/': + if (STR(n)[1] == '/') + return FloorDiv; + else + return Div; + case '%': + return Mod; + case '<': + return LShift; + case '>': + return RShift; + case '&': + return BitAnd; + case '^': + return BitXor; + case '|': + return BitOr; + case '*': + if (STR(n)[1] == '*') + return Pow; + else + return Mult; + default: + PyErr_Format(PyExc_SystemError, "invalid augassign: %s", STR(n)); + return (operator_ty)0; + } +} + +static cmpop_ty +ast_for_comp_op(struct compiling *c, const node *n) +{ + /* comp_op: '<'|'>'|'=='|'>='|'<='|'<>'|'!='|'in'|'not' 'in'|'is' + |'is' 'not' + */ + REQ(n, comp_op); + if (NCH(n) == 1) { + n = CHILD(n, 0); + switch (TYPE(n)) { + case LESS: + return Lt; + case GREATER: + return Gt; + case EQEQUAL: /* == */ + return Eq; + case LESSEQUAL: + return LtE; + case GREATEREQUAL: + return GtE; + case NOTEQUAL: + return NotEq; + case NAME: + if (strcmp(STR(n), "in") == 0) + return In; + if (strcmp(STR(n), "is") == 0) + return Is; + default: + PyErr_Format(PyExc_SystemError, "invalid comp_op: %s", + STR(n)); + return (cmpop_ty)0; + } + } + else if (NCH(n) == 2) { + /* handle "not in" and "is not" */ + switch (TYPE(CHILD(n, 0))) { + case NAME: + if (strcmp(STR(CHILD(n, 1)), "in") == 0) + return NotIn; + if (strcmp(STR(CHILD(n, 0)), "is") == 0) + return IsNot; + default: + PyErr_Format(PyExc_SystemError, "invalid comp_op: %s %s", + STR(CHILD(n, 0)), STR(CHILD(n, 1))); + return (cmpop_ty)0; + } + } + PyErr_Format(PyExc_SystemError, "invalid comp_op: has %d children", + NCH(n)); + return (cmpop_ty)0; +} + +static asdl_seq * +seq_for_testlist(struct compiling *c, const node *n) +{ + /* testlist: test (',' test)* [','] */ + asdl_seq *seq; + expr_ty expression; + int i; + assert(TYPE(n) == testlist || + TYPE(n) == listmaker || + TYPE(n) == testlist_comp || + TYPE(n) == testlist_safe || + TYPE(n) == testlist1); + + seq = asdl_seq_new((NCH(n) + 1) / 2, c->c_arena); + if (!seq) + return NULL; + + for (i = 0; i < NCH(n); i += 2) { + assert(TYPE(CHILD(n, i)) == test || TYPE(CHILD(n, i)) == old_test); + + expression = ast_for_expr(c, CHILD(n, i)); + if (!expression) + return NULL; + + assert(i / 2 < seq->size); + asdl_seq_SET(seq, i / 2, expression); + } + return seq; +} + +static expr_ty +compiler_complex_args(struct compiling *c, const node *n) +{ + int i, len = (NCH(n) + 1) / 2; + expr_ty result; + asdl_seq *args = asdl_seq_new(len, c->c_arena); + if (!args) + return NULL; + + /* fpdef: NAME | '(' fplist ')' + fplist: fpdef (',' fpdef)* [','] + */ + REQ(n, fplist); + for (i = 0; i < len; i++) { + PyObject *arg_id; + const node *fpdef_node = CHILD(n, 2*i); + const node *child; + expr_ty arg; +set_name: + /* fpdef_node is either a NAME or an fplist */ + child = CHILD(fpdef_node, 0); + if (TYPE(child) == NAME) { + if (!forbidden_check(c, n, STR(child))) + return NULL; + arg_id = NEW_IDENTIFIER(child); + if (!arg_id) + return NULL; + arg = Name(arg_id, Store, LINENO(child), child->n_col_offset, + c->c_arena); + } + else { + assert(TYPE(fpdef_node) == fpdef); + /* fpdef_node[0] is not a name, so it must be '(', get CHILD[1] */ + child = CHILD(fpdef_node, 1); + assert(TYPE(child) == fplist); + /* NCH == 1 means we have (x), we need to elide the extra parens */ + if (NCH(child) == 1) { + fpdef_node = CHILD(child, 0); + assert(TYPE(fpdef_node) == fpdef); + goto set_name; + } + arg = compiler_complex_args(c, child); + } + asdl_seq_SET(args, i, arg); + } + + result = Tuple(args, Store, LINENO(n), n->n_col_offset, c->c_arena); + if (!set_context(c, result, Store, n)) + return NULL; + return result; +} + + +/* Create AST for argument list. */ + +static arguments_ty +ast_for_arguments(struct compiling *c, const node *n) +{ + /* parameters: '(' [varargslist] ')' + varargslist: (fpdef ['=' test] ',')* ('*' NAME [',' '**' NAME] + | '**' NAME) | fpdef ['=' test] (',' fpdef ['=' test])* [','] + */ + int i, j, k, n_args = 0, n_defaults = 0, found_default = 0; + asdl_seq *args, *defaults; + identifier vararg = NULL, kwarg = NULL; + node *ch; + + if (TYPE(n) == parameters) { + if (NCH(n) == 2) /* () as argument list */ + return arguments(NULL, NULL, NULL, NULL, c->c_arena); + n = CHILD(n, 1); + } + REQ(n, varargslist); + + /* first count the number of normal args & defaults */ + for (i = 0; i < NCH(n); i++) { + ch = CHILD(n, i); + if (TYPE(ch) == fpdef) + n_args++; + if (TYPE(ch) == EQUAL) + n_defaults++; + } + args = (n_args ? asdl_seq_new(n_args, c->c_arena) : NULL); + if (!args && n_args) + return NULL; + defaults = (n_defaults ? asdl_seq_new(n_defaults, c->c_arena) : NULL); + if (!defaults && n_defaults) + return NULL; + + /* fpdef: NAME | '(' fplist ')' + fplist: fpdef (',' fpdef)* [','] + */ + i = 0; + j = 0; /* index for defaults */ + k = 0; /* index for args */ + while (i < NCH(n)) { + ch = CHILD(n, i); + switch (TYPE(ch)) { + case fpdef: { + int complex_args = 0, parenthesized = 0; + handle_fpdef: + /* XXX Need to worry about checking if TYPE(CHILD(n, i+1)) is + anything other than EQUAL or a comma? */ + /* XXX Should NCH(n) check be made a separate check? */ + if (i + 1 < NCH(n) && TYPE(CHILD(n, i + 1)) == EQUAL) { + expr_ty expression = ast_for_expr(c, CHILD(n, i + 2)); + if (!expression) + return NULL; + assert(defaults != NULL); + asdl_seq_SET(defaults, j++, expression); + i += 2; + found_default = 1; + } + else if (found_default) { + /* def f((x)=4): pass should raise an error. + def f((x, (y))): pass will just incur the tuple unpacking warning. */ + if (parenthesized && !complex_args) { + ast_error(n, "parenthesized arg with default"); + return NULL; + } + ast_error(n, + "non-default argument follows default argument"); + return NULL; + } + if (NCH(ch) == 3) { + ch = CHILD(ch, 1); + /* def foo((x)): is not complex, special case. */ + if (NCH(ch) != 1) { + /* We have complex arguments, setup for unpacking. */ + if (Py_Py3kWarningFlag && !ast_warn(c, ch, + "tuple parameter unpacking has been removed in 3.x")) + return NULL; + complex_args = 1; + asdl_seq_SET(args, k++, compiler_complex_args(c, ch)); + if (!asdl_seq_GET(args, k-1)) + return NULL; + } else { + /* def foo((x)): setup for checking NAME below. */ + /* Loop because there can be many parens and tuple + unpacking mixed in. */ + parenthesized = 1; + ch = CHILD(ch, 0); + assert(TYPE(ch) == fpdef); + goto handle_fpdef; + } + } + if (TYPE(CHILD(ch, 0)) == NAME) { + PyObject *id; + expr_ty name; + if (!forbidden_check(c, n, STR(CHILD(ch, 0)))) + return NULL; + id = NEW_IDENTIFIER(CHILD(ch, 0)); + if (!id) + return NULL; + name = Name(id, Param, LINENO(ch), ch->n_col_offset, + c->c_arena); + if (!name) + return NULL; + asdl_seq_SET(args, k++, name); + + } + i += 2; /* the name and the comma */ + if (parenthesized && Py_Py3kWarningFlag && + !ast_warn(c, ch, "parenthesized argument names " + "are invalid in 3.x")) + return NULL; + + break; + } + case STAR: + if (!forbidden_check(c, CHILD(n, i+1), STR(CHILD(n, i+1)))) + return NULL; + vararg = NEW_IDENTIFIER(CHILD(n, i+1)); + if (!vararg) + return NULL; + i += 3; + break; + case DOUBLESTAR: + if (!forbidden_check(c, CHILD(n, i+1), STR(CHILD(n, i+1)))) + return NULL; + kwarg = NEW_IDENTIFIER(CHILD(n, i+1)); + if (!kwarg) + return NULL; + i += 3; + break; + default: + PyErr_Format(PyExc_SystemError, + "unexpected node in varargslist: %d @ %d", + TYPE(ch), i); + return NULL; + } + } + + return arguments(args, vararg, kwarg, defaults, c->c_arena); +} + +static expr_ty +ast_for_dotted_name(struct compiling *c, const node *n) +{ + expr_ty e; + identifier id; + int lineno, col_offset; + int i; + + REQ(n, dotted_name); + + lineno = LINENO(n); + col_offset = n->n_col_offset; + + id = NEW_IDENTIFIER(CHILD(n, 0)); + if (!id) + return NULL; + e = Name(id, Load, lineno, col_offset, c->c_arena); + if (!e) + return NULL; + + for (i = 2; i < NCH(n); i+=2) { + id = NEW_IDENTIFIER(CHILD(n, i)); + if (!id) + return NULL; + e = Attribute(e, id, Load, lineno, col_offset, c->c_arena); + if (!e) + return NULL; + } + + return e; +} + +static expr_ty +ast_for_decorator(struct compiling *c, const node *n) +{ + /* decorator: '@' dotted_name [ '(' [arglist] ')' ] NEWLINE */ + expr_ty d = NULL; + expr_ty name_expr; + + REQ(n, decorator); + REQ(CHILD(n, 0), AT); + REQ(RCHILD(n, -1), NEWLINE); + + name_expr = ast_for_dotted_name(c, CHILD(n, 1)); + if (!name_expr) + return NULL; + + if (NCH(n) == 3) { /* No arguments */ + d = name_expr; + name_expr = NULL; + } + else if (NCH(n) == 5) { /* Call with no arguments */ + d = Call(name_expr, NULL, NULL, NULL, NULL, LINENO(n), + n->n_col_offset, c->c_arena); + if (!d) + return NULL; + name_expr = NULL; + } + else { + d = ast_for_call(c, CHILD(n, 3), name_expr); + if (!d) + return NULL; + name_expr = NULL; + } + + return d; +} + +static asdl_seq* +ast_for_decorators(struct compiling *c, const node *n) +{ + asdl_seq* decorator_seq; + expr_ty d; + int i; + + REQ(n, decorators); + decorator_seq = asdl_seq_new(NCH(n), c->c_arena); + if (!decorator_seq) + return NULL; + + for (i = 0; i < NCH(n); i++) { + d = ast_for_decorator(c, CHILD(n, i)); + if (!d) + return NULL; + asdl_seq_SET(decorator_seq, i, d); + } + return decorator_seq; +} + +static stmt_ty +ast_for_funcdef(struct compiling *c, const node *n, asdl_seq *decorator_seq) +{ + /* funcdef: 'def' NAME parameters ':' suite */ + identifier name; + arguments_ty args; + asdl_seq *body; + int name_i = 1; + + REQ(n, funcdef); + + name = NEW_IDENTIFIER(CHILD(n, name_i)); + if (!name) + return NULL; + else if (!forbidden_check(c, CHILD(n, name_i), STR(CHILD(n, name_i)))) + return NULL; + args = ast_for_arguments(c, CHILD(n, name_i + 1)); + if (!args) + return NULL; + body = ast_for_suite(c, CHILD(n, name_i + 3)); + if (!body) + return NULL; + + return FunctionDef(name, args, body, decorator_seq, LINENO(n), + n->n_col_offset, c->c_arena); +} + +static stmt_ty +ast_for_decorated(struct compiling *c, const node *n) +{ + /* decorated: decorators (classdef | funcdef) */ + stmt_ty thing = NULL; + asdl_seq *decorator_seq = NULL; + + REQ(n, decorated); + + decorator_seq = ast_for_decorators(c, CHILD(n, 0)); + if (!decorator_seq) + return NULL; + + assert(TYPE(CHILD(n, 1)) == funcdef || + TYPE(CHILD(n, 1)) == classdef); + + if (TYPE(CHILD(n, 1)) == funcdef) { + thing = ast_for_funcdef(c, CHILD(n, 1), decorator_seq); + } else if (TYPE(CHILD(n, 1)) == classdef) { + thing = ast_for_classdef(c, CHILD(n, 1), decorator_seq); + } + /* we count the decorators in when talking about the class' or + function's line number */ + if (thing) { + thing->lineno = LINENO(n); + thing->col_offset = n->n_col_offset; + } + return thing; +} + +static expr_ty +ast_for_lambdef(struct compiling *c, const node *n) +{ + /* lambdef: 'lambda' [varargslist] ':' test */ + arguments_ty args; + expr_ty expression; + + if (NCH(n) == 3) { + args = arguments(NULL, NULL, NULL, NULL, c->c_arena); + if (!args) + return NULL; + expression = ast_for_expr(c, CHILD(n, 2)); + if (!expression) + return NULL; + } + else { + args = ast_for_arguments(c, CHILD(n, 1)); + if (!args) + return NULL; + expression = ast_for_expr(c, CHILD(n, 3)); + if (!expression) + return NULL; + } + + return Lambda(args, expression, LINENO(n), n->n_col_offset, c->c_arena); +} + +static expr_ty +ast_for_ifexpr(struct compiling *c, const node *n) +{ + /* test: or_test 'if' or_test 'else' test */ + expr_ty expression, body, orelse; + + assert(NCH(n) == 5); + body = ast_for_expr(c, CHILD(n, 0)); + if (!body) + return NULL; + expression = ast_for_expr(c, CHILD(n, 2)); + if (!expression) + return NULL; + orelse = ast_for_expr(c, CHILD(n, 4)); + if (!orelse) + return NULL; + return IfExp(expression, body, orelse, LINENO(n), n->n_col_offset, + c->c_arena); +} + +/* XXX(nnorwitz): the listcomp and genexpr code should be refactored + so there is only a single version. Possibly for loops can also re-use + the code. +*/ + +/* Count the number of 'for' loop in a list comprehension. + + Helper for ast_for_listcomp(). +*/ + +static int +count_list_fors(struct compiling *c, const node *n) +{ + int n_fors = 0; + node *ch = CHILD(n, 1); + + count_list_for: + n_fors++; + REQ(ch, list_for); + if (NCH(ch) == 5) + ch = CHILD(ch, 4); + else + return n_fors; + count_list_iter: + REQ(ch, list_iter); + ch = CHILD(ch, 0); + if (TYPE(ch) == list_for) + goto count_list_for; + else if (TYPE(ch) == list_if) { + if (NCH(ch) == 3) { + ch = CHILD(ch, 2); + goto count_list_iter; + } + else + return n_fors; + } + + /* Should never be reached */ + PyErr_SetString(PyExc_SystemError, "logic error in count_list_fors"); + return -1; +} + +/* Count the number of 'if' statements in a list comprehension. + + Helper for ast_for_listcomp(). +*/ + +static int +count_list_ifs(struct compiling *c, const node *n) +{ + int n_ifs = 0; + + count_list_iter: + REQ(n, list_iter); + if (TYPE(CHILD(n, 0)) == list_for) + return n_ifs; + n = CHILD(n, 0); + REQ(n, list_if); + n_ifs++; + if (NCH(n) == 2) + return n_ifs; + n = CHILD(n, 2); + goto count_list_iter; +} + +static expr_ty +ast_for_listcomp(struct compiling *c, const node *n) +{ + /* listmaker: test ( list_for | (',' test)* [','] ) + list_for: 'for' exprlist 'in' testlist_safe [list_iter] + list_iter: list_for | list_if + list_if: 'if' test [list_iter] + testlist_safe: test [(',' test)+ [',']] + */ + expr_ty elt, first; + asdl_seq *listcomps; + int i, n_fors; + node *ch; + + REQ(n, listmaker); + assert(NCH(n) > 1); + + elt = ast_for_expr(c, CHILD(n, 0)); + if (!elt) + return NULL; + + n_fors = count_list_fors(c, n); + if (n_fors == -1) + return NULL; + + listcomps = asdl_seq_new(n_fors, c->c_arena); + if (!listcomps) + return NULL; + + ch = CHILD(n, 1); + for (i = 0; i < n_fors; i++) { + comprehension_ty lc; + asdl_seq *t; + expr_ty expression; + node *for_ch; + + REQ(ch, list_for); + + for_ch = CHILD(ch, 1); + t = ast_for_exprlist(c, for_ch, Store); + if (!t) + return NULL; + expression = ast_for_testlist(c, CHILD(ch, 3)); + if (!expression) + return NULL; + + /* Check the # of children rather than the length of t, since + [x for x, in ... ] has 1 element in t, but still requires a Tuple. + */ + first = (expr_ty)asdl_seq_GET(t, 0); + if (NCH(for_ch) == 1) + lc = comprehension(first, expression, NULL, c->c_arena); + else + lc = comprehension(Tuple(t, Store, first->lineno, first->col_offset, + c->c_arena), + expression, NULL, c->c_arena); + if (!lc) + return NULL; + + if (NCH(ch) == 5) { + int j, n_ifs; + asdl_seq *ifs; + expr_ty list_for_expr; + + ch = CHILD(ch, 4); + n_ifs = count_list_ifs(c, ch); + if (n_ifs == -1) + return NULL; + + ifs = asdl_seq_new(n_ifs, c->c_arena); + if (!ifs) + return NULL; + + for (j = 0; j < n_ifs; j++) { + REQ(ch, list_iter); + ch = CHILD(ch, 0); + REQ(ch, list_if); + + list_for_expr = ast_for_expr(c, CHILD(ch, 1)); + if (!list_for_expr) + return NULL; + + asdl_seq_SET(ifs, j, list_for_expr); + if (NCH(ch) == 3) + ch = CHILD(ch, 2); + } + /* on exit, must guarantee that ch is a list_for */ + if (TYPE(ch) == list_iter) + ch = CHILD(ch, 0); + lc->ifs = ifs; + } + asdl_seq_SET(listcomps, i, lc); + } + + return ListComp(elt, listcomps, LINENO(n), n->n_col_offset, c->c_arena); +} + +/* + Count the number of 'for' loops in a comprehension. + + Helper for ast_for_comprehension(). +*/ + +static int +count_comp_fors(struct compiling *c, const node *n) +{ + int n_fors = 0; + + count_comp_for: + n_fors++; + REQ(n, comp_for); + if (NCH(n) == 5) + n = CHILD(n, 4); + else + return n_fors; + count_comp_iter: + REQ(n, comp_iter); + n = CHILD(n, 0); + if (TYPE(n) == comp_for) + goto count_comp_for; + else if (TYPE(n) == comp_if) { + if (NCH(n) == 3) { + n = CHILD(n, 2); + goto count_comp_iter; + } + else + return n_fors; + } + + /* Should never be reached */ + PyErr_SetString(PyExc_SystemError, + "logic error in count_comp_fors"); + return -1; +} + +/* Count the number of 'if' statements in a comprehension. + + Helper for ast_for_comprehension(). +*/ + +static int +count_comp_ifs(struct compiling *c, const node *n) +{ + int n_ifs = 0; + + while (1) { + REQ(n, comp_iter); + if (TYPE(CHILD(n, 0)) == comp_for) + return n_ifs; + n = CHILD(n, 0); + REQ(n, comp_if); + n_ifs++; + if (NCH(n) == 2) + return n_ifs; + n = CHILD(n, 2); + } +} + +static asdl_seq * +ast_for_comprehension(struct compiling *c, const node *n) +{ + int i, n_fors; + asdl_seq *comps; + + n_fors = count_comp_fors(c, n); + if (n_fors == -1) + return NULL; + + comps = asdl_seq_new(n_fors, c->c_arena); + if (!comps) + return NULL; + + for (i = 0; i < n_fors; i++) { + comprehension_ty comp; + asdl_seq *t; + expr_ty expression, first; + node *for_ch; + + REQ(n, comp_for); + + for_ch = CHILD(n, 1); + t = ast_for_exprlist(c, for_ch, Store); + if (!t) + return NULL; + expression = ast_for_expr(c, CHILD(n, 3)); + if (!expression) + return NULL; + + /* Check the # of children rather than the length of t, since + (x for x, in ...) has 1 element in t, but still requires a Tuple. */ + first = (expr_ty)asdl_seq_GET(t, 0); + if (NCH(for_ch) == 1) + comp = comprehension(first, expression, NULL, c->c_arena); + else + comp = comprehension(Tuple(t, Store, first->lineno, first->col_offset, + c->c_arena), + expression, NULL, c->c_arena); + if (!comp) + return NULL; + + if (NCH(n) == 5) { + int j, n_ifs; + asdl_seq *ifs; + + n = CHILD(n, 4); + n_ifs = count_comp_ifs(c, n); + if (n_ifs == -1) + return NULL; + + ifs = asdl_seq_new(n_ifs, c->c_arena); + if (!ifs) + return NULL; + + for (j = 0; j < n_ifs; j++) { + REQ(n, comp_iter); + n = CHILD(n, 0); + REQ(n, comp_if); + + expression = ast_for_expr(c, CHILD(n, 1)); + if (!expression) + return NULL; + asdl_seq_SET(ifs, j, expression); + if (NCH(n) == 3) + n = CHILD(n, 2); + } + /* on exit, must guarantee that n is a comp_for */ + if (TYPE(n) == comp_iter) + n = CHILD(n, 0); + comp->ifs = ifs; + } + asdl_seq_SET(comps, i, comp); + } + return comps; +} + +static expr_ty +ast_for_itercomp(struct compiling *c, const node *n, int type) +{ + expr_ty elt; + asdl_seq *comps; + + assert(NCH(n) > 1); + + elt = ast_for_expr(c, CHILD(n, 0)); + if (!elt) + return NULL; + + comps = ast_for_comprehension(c, CHILD(n, 1)); + if (!comps) + return NULL; + + if (type == COMP_GENEXP) + return GeneratorExp(elt, comps, LINENO(n), n->n_col_offset, c->c_arena); + else if (type == COMP_SETCOMP) + return SetComp(elt, comps, LINENO(n), n->n_col_offset, c->c_arena); + else + /* Should never happen */ + return NULL; +} + +static expr_ty +ast_for_dictcomp(struct compiling *c, const node *n) +{ + expr_ty key, value; + asdl_seq *comps; + + assert(NCH(n) > 3); + REQ(CHILD(n, 1), COLON); + + key = ast_for_expr(c, CHILD(n, 0)); + if (!key) + return NULL; + + value = ast_for_expr(c, CHILD(n, 2)); + if (!value) + return NULL; + + comps = ast_for_comprehension(c, CHILD(n, 3)); + if (!comps) + return NULL; + + return DictComp(key, value, comps, LINENO(n), n->n_col_offset, c->c_arena); +} + +static expr_ty +ast_for_genexp(struct compiling *c, const node *n) +{ + assert(TYPE(n) == (testlist_comp) || TYPE(n) == (argument)); + return ast_for_itercomp(c, n, COMP_GENEXP); +} + +static expr_ty +ast_for_setcomp(struct compiling *c, const node *n) +{ + assert(TYPE(n) == (dictorsetmaker)); + return ast_for_itercomp(c, n, COMP_SETCOMP); +} + +static expr_ty +ast_for_atom(struct compiling *c, const node *n) +{ + /* atom: '(' [yield_expr|testlist_comp] ')' | '[' [listmaker] ']' + | '{' [dictmaker] '}' | '`' testlist '`' | NAME | NUMBER | STRING+ + */ + node *ch = CHILD(n, 0); + + switch (TYPE(ch)) { + case NAME: { + /* All names start in Load context, but may later be + changed. */ + PyObject *name = NEW_IDENTIFIER(ch); + if (!name) + return NULL; + return Name(name, Load, LINENO(n), n->n_col_offset, c->c_arena); + } + case STRING: { + PyObject *str = parsestrplus(c, n); + if (!str) { +#ifdef Py_USING_UNICODE + if (PyErr_ExceptionMatches(PyExc_UnicodeError)){ + PyObject *type, *value, *tback, *errstr; + PyErr_Fetch(&type, &value, &tback); + errstr = PyObject_Str(value); + if (errstr) { + char *s = ""; + char buf[128]; + s = PyString_AsString(errstr); + PyOS_snprintf(buf, sizeof(buf), "(unicode error) %s", s); + ast_error(n, buf); + Py_DECREF(errstr); + } else { + ast_error(n, "(unicode error) unknown error"); + } + Py_DECREF(type); + Py_DECREF(value); + Py_XDECREF(tback); + } +#endif + return NULL; + } + PyArena_AddPyObject(c->c_arena, str); + return Str(str, LINENO(n), n->n_col_offset, c->c_arena); + } + case NUMBER: { + PyObject *pynum = parsenumber(c, STR(ch)); + if (!pynum) + return NULL; + + PyArena_AddPyObject(c->c_arena, pynum); + return Num(pynum, LINENO(n), n->n_col_offset, c->c_arena); + } + case LPAR: /* some parenthesized expressions */ + ch = CHILD(n, 1); + + if (TYPE(ch) == RPAR) + return Tuple(NULL, Load, LINENO(n), n->n_col_offset, c->c_arena); + + if (TYPE(ch) == yield_expr) + return ast_for_expr(c, ch); + + return ast_for_testlist_comp(c, ch); + case LSQB: /* list (or list comprehension) */ + ch = CHILD(n, 1); + + if (TYPE(ch) == RSQB) + return List(NULL, Load, LINENO(n), n->n_col_offset, c->c_arena); + + REQ(ch, listmaker); + if (NCH(ch) == 1 || TYPE(CHILD(ch, 1)) == COMMA) { + asdl_seq *elts = seq_for_testlist(c, ch); + if (!elts) + return NULL; + + return List(elts, Load, LINENO(n), n->n_col_offset, c->c_arena); + } + else + return ast_for_listcomp(c, ch); + case LBRACE: { + /* dictorsetmaker: + * (test ':' test (comp_for | (',' test ':' test)* [','])) | + * (test (comp_for | (',' test)* [','])) + */ + int i, size; + asdl_seq *keys, *values; + + ch = CHILD(n, 1); + if (TYPE(ch) == RBRACE) { + /* it's an empty dict */ + return Dict(NULL, NULL, LINENO(n), n->n_col_offset, c->c_arena); + } else if (NCH(ch) == 1 || TYPE(CHILD(ch, 1)) == COMMA) { + /* it's a simple set */ + asdl_seq *elts; + size = (NCH(ch) + 1) / 2; /* +1 in case no trailing comma */ + elts = asdl_seq_new(size, c->c_arena); + if (!elts) + return NULL; + for (i = 0; i < NCH(ch); i += 2) { + expr_ty expression; + expression = ast_for_expr(c, CHILD(ch, i)); + if (!expression) + return NULL; + asdl_seq_SET(elts, i / 2, expression); + } + return Set(elts, LINENO(n), n->n_col_offset, c->c_arena); + } else if (TYPE(CHILD(ch, 1)) == comp_for) { + /* it's a set comprehension */ + return ast_for_setcomp(c, ch); + } else if (NCH(ch) > 3 && TYPE(CHILD(ch, 3)) == comp_for) { + return ast_for_dictcomp(c, ch); + } else { + /* it's a dict */ + size = (NCH(ch) + 1) / 4; /* +1 in case no trailing comma */ + keys = asdl_seq_new(size, c->c_arena); + if (!keys) + return NULL; + + values = asdl_seq_new(size, c->c_arena); + if (!values) + return NULL; + + for (i = 0; i < NCH(ch); i += 4) { + expr_ty expression; + + expression = ast_for_expr(c, CHILD(ch, i)); + if (!expression) + return NULL; + + asdl_seq_SET(keys, i / 4, expression); + + expression = ast_for_expr(c, CHILD(ch, i + 2)); + if (!expression) + return NULL; + + asdl_seq_SET(values, i / 4, expression); + } + return Dict(keys, values, LINENO(n), n->n_col_offset, c->c_arena); + } + } + case BACKQUOTE: { /* repr */ + expr_ty expression; + if (Py_Py3kWarningFlag && + !ast_warn(c, n, "backquote not supported in 3.x; use repr()")) + return NULL; + expression = ast_for_testlist(c, CHILD(n, 1)); + if (!expression) + return NULL; + + return Repr(expression, LINENO(n), n->n_col_offset, c->c_arena); + } + default: + PyErr_Format(PyExc_SystemError, "unhandled atom %d", TYPE(ch)); + return NULL; + } +} + +static slice_ty +ast_for_slice(struct compiling *c, const node *n) +{ + node *ch; + expr_ty lower = NULL, upper = NULL, step = NULL; + + REQ(n, subscript); + + /* + subscript: '.' '.' '.' | test | [test] ':' [test] [sliceop] + sliceop: ':' [test] + */ + ch = CHILD(n, 0); + if (TYPE(ch) == DOT) + return Ellipsis(c->c_arena); + + if (NCH(n) == 1 && TYPE(ch) == test) { + /* 'step' variable hold no significance in terms of being used over + other vars */ + step = ast_for_expr(c, ch); + if (!step) + return NULL; + + return Index(step, c->c_arena); + } + + if (TYPE(ch) == test) { + lower = ast_for_expr(c, ch); + if (!lower) + return NULL; + } + + /* If there's an upper bound it's in the second or third position. */ + if (TYPE(ch) == COLON) { + if (NCH(n) > 1) { + node *n2 = CHILD(n, 1); + + if (TYPE(n2) == test) { + upper = ast_for_expr(c, n2); + if (!upper) + return NULL; + } + } + } else if (NCH(n) > 2) { + node *n2 = CHILD(n, 2); + + if (TYPE(n2) == test) { + upper = ast_for_expr(c, n2); + if (!upper) + return NULL; + } + } + + ch = CHILD(n, NCH(n) - 1); + if (TYPE(ch) == sliceop) { + if (NCH(ch) == 1) { + /* + This is an extended slice (ie "x[::]") with no expression in the + step field. We set this literally to "None" in order to + disambiguate it from x[:]. (The interpreter might have to call + __getslice__ for x[:], but it must call __getitem__ for x[::].) + */ + identifier none = new_identifier("None", c->c_arena); + if (!none) + return NULL; + ch = CHILD(ch, 0); + step = Name(none, Load, LINENO(ch), ch->n_col_offset, c->c_arena); + if (!step) + return NULL; + } else { + ch = CHILD(ch, 1); + if (TYPE(ch) == test) { + step = ast_for_expr(c, ch); + if (!step) + return NULL; + } + } + } + + return Slice(lower, upper, step, c->c_arena); +} + +static expr_ty +ast_for_binop(struct compiling *c, const node *n) +{ + /* Must account for a sequence of expressions. + How should A op B op C by represented? + BinOp(BinOp(A, op, B), op, C). + */ + + int i, nops; + expr_ty expr1, expr2, result; + operator_ty newoperator; + + expr1 = ast_for_expr(c, CHILD(n, 0)); + if (!expr1) + return NULL; + + expr2 = ast_for_expr(c, CHILD(n, 2)); + if (!expr2) + return NULL; + + newoperator = get_operator(CHILD(n, 1)); + if (!newoperator) + return NULL; + + result = BinOp(expr1, newoperator, expr2, LINENO(n), n->n_col_offset, + c->c_arena); + if (!result) + return NULL; + + nops = (NCH(n) - 1) / 2; + for (i = 1; i < nops; i++) { + expr_ty tmp_result, tmp; + const node* next_oper = CHILD(n, i * 2 + 1); + + newoperator = get_operator(next_oper); + if (!newoperator) + return NULL; + + tmp = ast_for_expr(c, CHILD(n, i * 2 + 2)); + if (!tmp) + return NULL; + + tmp_result = BinOp(result, newoperator, tmp, + LINENO(next_oper), next_oper->n_col_offset, + c->c_arena); + if (!tmp_result) + return NULL; + result = tmp_result; + } + return result; +} + +static expr_ty +ast_for_trailer(struct compiling *c, const node *n, expr_ty left_expr) +{ + /* trailer: '(' [arglist] ')' | '[' subscriptlist ']' | '.' NAME + subscriptlist: subscript (',' subscript)* [','] + subscript: '.' '.' '.' | test | [test] ':' [test] [sliceop] + */ + REQ(n, trailer); + if (TYPE(CHILD(n, 0)) == LPAR) { + if (NCH(n) == 2) + return Call(left_expr, NULL, NULL, NULL, NULL, LINENO(n), + n->n_col_offset, c->c_arena); + else + return ast_for_call(c, CHILD(n, 1), left_expr); + } + else if (TYPE(CHILD(n, 0)) == DOT ) { + PyObject *attr_id = NEW_IDENTIFIER(CHILD(n, 1)); + if (!attr_id) + return NULL; + return Attribute(left_expr, attr_id, Load, + LINENO(n), n->n_col_offset, c->c_arena); + } + else { + REQ(CHILD(n, 0), LSQB); + REQ(CHILD(n, 2), RSQB); + n = CHILD(n, 1); + if (NCH(n) == 1) { + slice_ty slc = ast_for_slice(c, CHILD(n, 0)); + if (!slc) + return NULL; + return Subscript(left_expr, slc, Load, LINENO(n), n->n_col_offset, + c->c_arena); + } + else { + /* The grammar is ambiguous here. The ambiguity is resolved + by treating the sequence as a tuple literal if there are + no slice features. + */ + int j; + slice_ty slc; + expr_ty e; + bool simple = true; + asdl_seq *slices, *elts; + slices = asdl_seq_new((NCH(n) + 1) / 2, c->c_arena); + if (!slices) + return NULL; + for (j = 0; j < NCH(n); j += 2) { + slc = ast_for_slice(c, CHILD(n, j)); + if (!slc) + return NULL; + if (slc->kind != Index_kind) + simple = false; + asdl_seq_SET(slices, j / 2, slc); + } + if (!simple) { + return Subscript(left_expr, ExtSlice(slices, c->c_arena), + Load, LINENO(n), n->n_col_offset, c->c_arena); + } + /* extract Index values and put them in a Tuple */ + elts = asdl_seq_new(asdl_seq_LEN(slices), c->c_arena); + if (!elts) + return NULL; + for (j = 0; j < asdl_seq_LEN(slices); ++j) { + slc = (slice_ty)asdl_seq_GET(slices, j); + assert(slc->kind == Index_kind && slc->v.Index.value); + asdl_seq_SET(elts, j, slc->v.Index.value); + } + e = Tuple(elts, Load, LINENO(n), n->n_col_offset, c->c_arena); + if (!e) + return NULL; + return Subscript(left_expr, Index(e, c->c_arena), + Load, LINENO(n), n->n_col_offset, c->c_arena); + } + } +} + +static expr_ty +ast_for_factor(struct compiling *c, const node *n) +{ + node *pfactor, *ppower, *patom, *pnum; + expr_ty expression; + + /* If the unary - operator is applied to a constant, don't generate + a UNARY_NEGATIVE opcode. Just store the approriate value as a + constant. The peephole optimizer already does something like + this but it doesn't handle the case where the constant is + (sys.maxint - 1). In that case, we want a PyIntObject, not a + PyLongObject. + */ + if (TYPE(CHILD(n, 0)) == MINUS && + NCH(n) == 2 && + TYPE((pfactor = CHILD(n, 1))) == factor && + NCH(pfactor) == 1 && + TYPE((ppower = CHILD(pfactor, 0))) == power && + NCH(ppower) == 1 && + TYPE((patom = CHILD(ppower, 0))) == atom && + TYPE((pnum = CHILD(patom, 0))) == NUMBER) { + PyObject *pynum; + char *s = PyObject_MALLOC(strlen(STR(pnum)) + 2); + if (s == NULL) + return NULL; + s[0] = '-'; + strcpy(s + 1, STR(pnum)); + pynum = parsenumber(c, s); + PyObject_FREE(s); + if (!pynum) + return NULL; + + PyArena_AddPyObject(c->c_arena, pynum); + return Num(pynum, LINENO(n), n->n_col_offset, c->c_arena); + } + + expression = ast_for_expr(c, CHILD(n, 1)); + if (!expression) + return NULL; + + switch (TYPE(CHILD(n, 0))) { + case PLUS: + return UnaryOp(UAdd, expression, LINENO(n), n->n_col_offset, + c->c_arena); + case MINUS: + return UnaryOp(USub, expression, LINENO(n), n->n_col_offset, + c->c_arena); + case TILDE: + return UnaryOp(Invert, expression, LINENO(n), + n->n_col_offset, c->c_arena); + } + PyErr_Format(PyExc_SystemError, "unhandled factor: %d", + TYPE(CHILD(n, 0))); + return NULL; +} + +static expr_ty +ast_for_power(struct compiling *c, const node *n) +{ + /* power: atom trailer* ('**' factor)* + */ + int i; + expr_ty e, tmp; + REQ(n, power); + e = ast_for_atom(c, CHILD(n, 0)); + if (!e) + return NULL; + if (NCH(n) == 1) + return e; + for (i = 1; i < NCH(n); i++) { + node *ch = CHILD(n, i); + if (TYPE(ch) != trailer) + break; + tmp = ast_for_trailer(c, ch, e); + if (!tmp) + return NULL; + tmp->lineno = e->lineno; + tmp->col_offset = e->col_offset; + e = tmp; + } + if (TYPE(CHILD(n, NCH(n) - 1)) == factor) { + expr_ty f = ast_for_expr(c, CHILD(n, NCH(n) - 1)); + if (!f) + return NULL; + tmp = BinOp(e, Pow, f, LINENO(n), n->n_col_offset, c->c_arena); + if (!tmp) + return NULL; + e = tmp; + } + return e; +} + +/* Do not name a variable 'expr'! Will cause a compile error. +*/ + +static expr_ty +ast_for_expr(struct compiling *c, const node *n) +{ + /* handle the full range of simple expressions + test: or_test ['if' or_test 'else' test] | lambdef + or_test: and_test ('or' and_test)* + and_test: not_test ('and' not_test)* + not_test: 'not' not_test | comparison + comparison: expr (comp_op expr)* + expr: xor_expr ('|' xor_expr)* + xor_expr: and_expr ('^' and_expr)* + and_expr: shift_expr ('&' shift_expr)* + shift_expr: arith_expr (('<<'|'>>') arith_expr)* + arith_expr: term (('+'|'-') term)* + term: factor (('*'|'/'|'%'|'//') factor)* + factor: ('+'|'-'|'~') factor | power + power: atom trailer* ('**' factor)* + + As well as modified versions that exist for backward compatibility, + to explicitly allow: + [ x for x in lambda: 0, lambda: 1 ] + (which would be ambiguous without these extra rules) + + old_test: or_test | old_lambdef + old_lambdef: 'lambda' [vararglist] ':' old_test + + */ + + asdl_seq *seq; + int i; + + loop: + switch (TYPE(n)) { + case test: + case old_test: + if (TYPE(CHILD(n, 0)) == lambdef || + TYPE(CHILD(n, 0)) == old_lambdef) + return ast_for_lambdef(c, CHILD(n, 0)); + else if (NCH(n) > 1) + return ast_for_ifexpr(c, n); + /* Fallthrough */ + case or_test: + case and_test: + if (NCH(n) == 1) { + n = CHILD(n, 0); + goto loop; + } + seq = asdl_seq_new((NCH(n) + 1) / 2, c->c_arena); + if (!seq) + return NULL; + for (i = 0; i < NCH(n); i += 2) { + expr_ty e = ast_for_expr(c, CHILD(n, i)); + if (!e) + return NULL; + asdl_seq_SET(seq, i / 2, e); + } + if (!strcmp(STR(CHILD(n, 1)), "and")) + return BoolOp(And, seq, LINENO(n), n->n_col_offset, + c->c_arena); + assert(!strcmp(STR(CHILD(n, 1)), "or")); + return BoolOp(Or, seq, LINENO(n), n->n_col_offset, c->c_arena); + case not_test: + if (NCH(n) == 1) { + n = CHILD(n, 0); + goto loop; + } + else { + expr_ty expression = ast_for_expr(c, CHILD(n, 1)); + if (!expression) + return NULL; + + return UnaryOp(Not, expression, LINENO(n), n->n_col_offset, + c->c_arena); + } + case comparison: + if (NCH(n) == 1) { + n = CHILD(n, 0); + goto loop; + } + else { + expr_ty expression; + asdl_int_seq *ops; + asdl_seq *cmps; + ops = asdl_int_seq_new(NCH(n) / 2, c->c_arena); + if (!ops) + return NULL; + cmps = asdl_seq_new(NCH(n) / 2, c->c_arena); + if (!cmps) { + return NULL; + } + for (i = 1; i < NCH(n); i += 2) { + cmpop_ty newoperator; + + newoperator = ast_for_comp_op(c, CHILD(n, i)); + if (!newoperator) { + return NULL; + } + + expression = ast_for_expr(c, CHILD(n, i + 1)); + if (!expression) { + return NULL; + } + + asdl_seq_SET(ops, i / 2, newoperator); + asdl_seq_SET(cmps, i / 2, expression); + } + expression = ast_for_expr(c, CHILD(n, 0)); + if (!expression) { + return NULL; + } + + return Compare(expression, ops, cmps, LINENO(n), + n->n_col_offset, c->c_arena); + } + break; + + /* The next five cases all handle BinOps. The main body of code + is the same in each case, but the switch turned inside out to + reuse the code for each type of operator. + */ + case expr: + case xor_expr: + case and_expr: + case shift_expr: + case arith_expr: + case term: + if (NCH(n) == 1) { + n = CHILD(n, 0); + goto loop; + } + return ast_for_binop(c, n); + case yield_expr: { + expr_ty exp = NULL; + if (NCH(n) == 2) { + exp = ast_for_testlist(c, CHILD(n, 1)); + if (!exp) + return NULL; + } + return Yield(exp, LINENO(n), n->n_col_offset, c->c_arena); + } + case factor: + if (NCH(n) == 1) { + n = CHILD(n, 0); + goto loop; + } + return ast_for_factor(c, n); + case power: + return ast_for_power(c, n); + default: + PyErr_Format(PyExc_SystemError, "unhandled expr: %d", TYPE(n)); + return NULL; + } + /* should never get here unless if error is set */ + return NULL; +} + +static expr_ty +ast_for_call(struct compiling *c, const node *n, expr_ty func) +{ + /* + arglist: (argument ',')* (argument [',']| '*' test [',' '**' test] + | '**' test) + argument: [test '='] test [comp_for] # Really [keyword '='] test + */ + + int i, nargs, nkeywords, ngens; + asdl_seq *args; + asdl_seq *keywords; + expr_ty vararg = NULL, kwarg = NULL; + + REQ(n, arglist); + + nargs = 0; + nkeywords = 0; + ngens = 0; + for (i = 0; i < NCH(n); i++) { + node *ch = CHILD(n, i); + if (TYPE(ch) == argument) { + if (NCH(ch) == 1) + nargs++; + else if (TYPE(CHILD(ch, 1)) == comp_for) + ngens++; + else + nkeywords++; + } + } + if (ngens > 1 || (ngens && (nargs || nkeywords))) { + ast_error(n, "Generator expression must be parenthesized " + "if not sole argument"); + return NULL; + } + + if (nargs + nkeywords + ngens > 255) { + ast_error(n, "more than 255 arguments"); + return NULL; + } + + args = asdl_seq_new(nargs + ngens, c->c_arena); + if (!args) + return NULL; + keywords = asdl_seq_new(nkeywords, c->c_arena); + if (!keywords) + return NULL; + nargs = 0; + nkeywords = 0; + for (i = 0; i < NCH(n); i++) { + node *ch = CHILD(n, i); + if (TYPE(ch) == argument) { + expr_ty e; + if (NCH(ch) == 1) { + if (nkeywords) { + ast_error(CHILD(ch, 0), + "non-keyword arg after keyword arg"); + return NULL; + } + if (vararg) { + ast_error(CHILD(ch, 0), + "only named arguments may follow *expression"); + return NULL; + } + e = ast_for_expr(c, CHILD(ch, 0)); + if (!e) + return NULL; + asdl_seq_SET(args, nargs++, e); + } + else if (TYPE(CHILD(ch, 1)) == comp_for) { + e = ast_for_genexp(c, ch); + if (!e) + return NULL; + asdl_seq_SET(args, nargs++, e); + } + else { + keyword_ty kw; + identifier key; + int k; + char *tmp; + + /* CHILD(ch, 0) is test, but must be an identifier? */ + e = ast_for_expr(c, CHILD(ch, 0)); + if (!e) + return NULL; + /* f(lambda x: x[0] = 3) ends up getting parsed with + * LHS test = lambda x: x[0], and RHS test = 3. + * SF bug 132313 points out that complaining about a keyword + * then is very confusing. + */ + if (e->kind == Lambda_kind) { + ast_error(CHILD(ch, 0), + "lambda cannot contain assignment"); + return NULL; + } else if (e->kind != Name_kind) { + ast_error(CHILD(ch, 0), "keyword can't be an expression"); + return NULL; + } + key = e->v.Name.id; + if (!forbidden_check(c, CHILD(ch, 0), PyBytes_AS_STRING(key))) + return NULL; + for (k = 0; k < nkeywords; k++) { + tmp = PyString_AS_STRING( + ((keyword_ty)asdl_seq_GET(keywords, k))->arg); + if (!strcmp(tmp, PyString_AS_STRING(key))) { + ast_error(CHILD(ch, 0), "keyword argument repeated"); + return NULL; + } + } + e = ast_for_expr(c, CHILD(ch, 2)); + if (!e) + return NULL; + kw = keyword(key, e, c->c_arena); + if (!kw) + return NULL; + asdl_seq_SET(keywords, nkeywords++, kw); + } + } + else if (TYPE(ch) == STAR) { + vararg = ast_for_expr(c, CHILD(n, i+1)); + if (!vararg) + return NULL; + i++; + } + else if (TYPE(ch) == DOUBLESTAR) { + kwarg = ast_for_expr(c, CHILD(n, i+1)); + if (!kwarg) + return NULL; + i++; + } + } + + return Call(func, args, keywords, vararg, kwarg, func->lineno, + func->col_offset, c->c_arena); +} + +static expr_ty +ast_for_testlist(struct compiling *c, const node* n) +{ + /* testlist_comp: test (',' test)* [','] */ + /* testlist: test (',' test)* [','] */ + /* testlist_safe: test (',' test)+ [','] */ + /* testlist1: test (',' test)* */ + assert(NCH(n) > 0); + if (TYPE(n) == testlist_comp) { + if (NCH(n) > 1) + assert(TYPE(CHILD(n, 1)) != comp_for); + } + else { + assert(TYPE(n) == testlist || + TYPE(n) == testlist_safe || + TYPE(n) == testlist1); + } + if (NCH(n) == 1) + return ast_for_expr(c, CHILD(n, 0)); + else { + asdl_seq *tmp = seq_for_testlist(c, n); + if (!tmp) + return NULL; + return Tuple(tmp, Load, LINENO(n), n->n_col_offset, c->c_arena); + } +} + +static expr_ty +ast_for_testlist_comp(struct compiling *c, const node* n) +{ + /* testlist_comp: test ( comp_for | (',' test)* [','] ) */ + /* argument: test [ comp_for ] */ + assert(TYPE(n) == testlist_comp || TYPE(n) == argument); + if (NCH(n) > 1 && TYPE(CHILD(n, 1)) == comp_for) + return ast_for_genexp(c, n); + return ast_for_testlist(c, n); +} + +/* like ast_for_testlist() but returns a sequence */ +static asdl_seq* +ast_for_class_bases(struct compiling *c, const node* n) +{ + /* testlist: test (',' test)* [','] */ + assert(NCH(n) > 0); + REQ(n, testlist); + if (NCH(n) == 1) { + expr_ty base; + asdl_seq *bases = asdl_seq_new(1, c->c_arena); + if (!bases) + return NULL; + base = ast_for_expr(c, CHILD(n, 0)); + if (!base) + return NULL; + asdl_seq_SET(bases, 0, base); + return bases; + } + + return seq_for_testlist(c, n); +} + +static stmt_ty +ast_for_expr_stmt(struct compiling *c, const node *n) +{ + REQ(n, expr_stmt); + /* expr_stmt: testlist (augassign (yield_expr|testlist) + | ('=' (yield_expr|testlist))*) + testlist: test (',' test)* [','] + augassign: '+=' | '-=' | '*=' | '/=' | '%=' | '&=' | '|=' | '^=' + | '<<=' | '>>=' | '**=' | '//=' + test: ... here starts the operator precendence dance + */ + + if (NCH(n) == 1) { + expr_ty e = ast_for_testlist(c, CHILD(n, 0)); + if (!e) + return NULL; + + return Expr(e, LINENO(n), n->n_col_offset, c->c_arena); + } + else if (TYPE(CHILD(n, 1)) == augassign) { + expr_ty expr1, expr2; + operator_ty newoperator; + node *ch = CHILD(n, 0); + + expr1 = ast_for_testlist(c, ch); + if (!expr1) + return NULL; + if(!set_context(c, expr1, Store, ch)) + return NULL; + /* set_context checks that most expressions are not the left side. + Augmented assignments can only have a name, a subscript, or an + attribute on the left, though, so we have to explicitly check for + those. */ + switch (expr1->kind) { + case Name_kind: + case Attribute_kind: + case Subscript_kind: + break; + default: + ast_error(ch, "illegal expression for augmented assignment"); + return NULL; + } + + ch = CHILD(n, 2); + if (TYPE(ch) == testlist) + expr2 = ast_for_testlist(c, ch); + else + expr2 = ast_for_expr(c, ch); + if (!expr2) + return NULL; + + newoperator = ast_for_augassign(c, CHILD(n, 1)); + if (!newoperator) + return NULL; + + return AugAssign(expr1, newoperator, expr2, LINENO(n), n->n_col_offset, + c->c_arena); + } + else { + int i; + asdl_seq *targets; + node *value; + expr_ty expression; + + /* a normal assignment */ + REQ(CHILD(n, 1), EQUAL); + targets = asdl_seq_new(NCH(n) / 2, c->c_arena); + if (!targets) + return NULL; + for (i = 0; i < NCH(n) - 2; i += 2) { + expr_ty e; + node *ch = CHILD(n, i); + if (TYPE(ch) == yield_expr) { + ast_error(ch, "assignment to yield expression not possible"); + return NULL; + } + e = ast_for_testlist(c, ch); + if (!e) + return NULL; + + /* set context to assign */ + if (!set_context(c, e, Store, CHILD(n, i))) + return NULL; + + asdl_seq_SET(targets, i / 2, e); + } + value = CHILD(n, NCH(n) - 1); + if (TYPE(value) == testlist) + expression = ast_for_testlist(c, value); + else + expression = ast_for_expr(c, value); + if (!expression) + return NULL; + return Assign(targets, expression, LINENO(n), n->n_col_offset, + c->c_arena); + } +} + +static stmt_ty +ast_for_print_stmt(struct compiling *c, const node *n) +{ + /* print_stmt: 'print' ( [ test (',' test)* [','] ] + | '>>' test [ (',' test)+ [','] ] ) + */ + expr_ty dest = NULL, expression; + asdl_seq *seq = NULL; + bool nl; + int i, j, values_count, start = 1; + + REQ(n, print_stmt); + if (NCH(n) >= 2 && TYPE(CHILD(n, 1)) == RIGHTSHIFT) { + dest = ast_for_expr(c, CHILD(n, 2)); + if (!dest) + return NULL; + start = 4; + } + values_count = (NCH(n) + 1 - start) / 2; + if (values_count) { + seq = asdl_seq_new(values_count, c->c_arena); + if (!seq) + return NULL; + for (i = start, j = 0; i < NCH(n); i += 2, ++j) { + expression = ast_for_expr(c, CHILD(n, i)); + if (!expression) + return NULL; + asdl_seq_SET(seq, j, expression); + } + } + nl = (TYPE(CHILD(n, NCH(n) - 1)) == COMMA) ? false : true; + return Print(dest, seq, nl, LINENO(n), n->n_col_offset, c->c_arena); +} + +static asdl_seq * +ast_for_exprlist(struct compiling *c, const node *n, expr_context_ty context) +{ + asdl_seq *seq; + int i; + expr_ty e; + + REQ(n, exprlist); + + seq = asdl_seq_new((NCH(n) + 1) / 2, c->c_arena); + if (!seq) + return NULL; + for (i = 0; i < NCH(n); i += 2) { + e = ast_for_expr(c, CHILD(n, i)); + if (!e) + return NULL; + asdl_seq_SET(seq, i / 2, e); + if (context && !set_context(c, e, context, CHILD(n, i))) + return NULL; + } + return seq; +} + +static stmt_ty +ast_for_del_stmt(struct compiling *c, const node *n) +{ + asdl_seq *expr_list; + + /* del_stmt: 'del' exprlist */ + REQ(n, del_stmt); + + expr_list = ast_for_exprlist(c, CHILD(n, 1), Del); + if (!expr_list) + return NULL; + return Delete(expr_list, LINENO(n), n->n_col_offset, c->c_arena); +} + +static stmt_ty +ast_for_flow_stmt(struct compiling *c, const node *n) +{ + /* + flow_stmt: break_stmt | continue_stmt | return_stmt | raise_stmt + | yield_stmt + break_stmt: 'break' + continue_stmt: 'continue' + return_stmt: 'return' [testlist] + yield_stmt: yield_expr + yield_expr: 'yield' testlist + raise_stmt: 'raise' [test [',' test [',' test]]] + */ + node *ch; + + REQ(n, flow_stmt); + ch = CHILD(n, 0); + switch (TYPE(ch)) { + case break_stmt: + return Break(LINENO(n), n->n_col_offset, c->c_arena); + case continue_stmt: + return Continue(LINENO(n), n->n_col_offset, c->c_arena); + case yield_stmt: { /* will reduce to yield_expr */ + expr_ty exp = ast_for_expr(c, CHILD(ch, 0)); + if (!exp) + return NULL; + return Expr(exp, LINENO(n), n->n_col_offset, c->c_arena); + } + case return_stmt: + if (NCH(ch) == 1) + return Return(NULL, LINENO(n), n->n_col_offset, c->c_arena); + else { + expr_ty expression = ast_for_testlist(c, CHILD(ch, 1)); + if (!expression) + return NULL; + return Return(expression, LINENO(n), n->n_col_offset, + c->c_arena); + } + case raise_stmt: + if (NCH(ch) == 1) + return Raise(NULL, NULL, NULL, LINENO(n), n->n_col_offset, + c->c_arena); + else if (NCH(ch) == 2) { + expr_ty expression = ast_for_expr(c, CHILD(ch, 1)); + if (!expression) + return NULL; + return Raise(expression, NULL, NULL, LINENO(n), + n->n_col_offset, c->c_arena); + } + else if (NCH(ch) == 4) { + expr_ty expr1, expr2; + + expr1 = ast_for_expr(c, CHILD(ch, 1)); + if (!expr1) + return NULL; + expr2 = ast_for_expr(c, CHILD(ch, 3)); + if (!expr2) + return NULL; + + return Raise(expr1, expr2, NULL, LINENO(n), n->n_col_offset, + c->c_arena); + } + else if (NCH(ch) == 6) { + expr_ty expr1, expr2, expr3; + + expr1 = ast_for_expr(c, CHILD(ch, 1)); + if (!expr1) + return NULL; + expr2 = ast_for_expr(c, CHILD(ch, 3)); + if (!expr2) + return NULL; + expr3 = ast_for_expr(c, CHILD(ch, 5)); + if (!expr3) + return NULL; + + return Raise(expr1, expr2, expr3, LINENO(n), n->n_col_offset, + c->c_arena); + } + default: + PyErr_Format(PyExc_SystemError, + "unexpected flow_stmt: %d", TYPE(ch)); + return NULL; + } + + PyErr_SetString(PyExc_SystemError, "unhandled flow statement"); + return NULL; +} + +static alias_ty +alias_for_import_name(struct compiling *c, const node *n, int store) +{ + /* + import_as_name: NAME ['as' NAME] + dotted_as_name: dotted_name ['as' NAME] + dotted_name: NAME ('.' NAME)* + */ + PyObject *str, *name; + + loop: + switch (TYPE(n)) { + case import_as_name: { + node *name_node = CHILD(n, 0); + str = NULL; + if (NCH(n) == 3) { + node *str_node = CHILD(n, 2); + if (store && !forbidden_check(c, str_node, STR(str_node))) + return NULL; + str = NEW_IDENTIFIER(str_node); + if (!str) + return NULL; + } + else { + if (!forbidden_check(c, name_node, STR(name_node))) + return NULL; + } + name = NEW_IDENTIFIER(name_node); + if (!name) + return NULL; + return alias(name, str, c->c_arena); + } + case dotted_as_name: + if (NCH(n) == 1) { + n = CHILD(n, 0); + goto loop; + } + else { + node *asname_node = CHILD(n, 2); + alias_ty a = alias_for_import_name(c, CHILD(n, 0), 0); + if (!a) + return NULL; + assert(!a->asname); + if (!forbidden_check(c, asname_node, STR(asname_node))) + return NULL; + a->asname = NEW_IDENTIFIER(asname_node); + if (!a->asname) + return NULL; + return a; + } + break; + case dotted_name: + if (NCH(n) == 1) { + node *name_node = CHILD(n, 0); + if (store && !forbidden_check(c, name_node, STR(name_node))) + return NULL; + name = NEW_IDENTIFIER(name_node); + if (!name) + return NULL; + return alias(name, NULL, c->c_arena); + } + else { + /* Create a string of the form "a.b.c" */ + int i; + size_t len; + char *s; + + len = 0; + for (i = 0; i < NCH(n); i += 2) + /* length of string plus one for the dot */ + len += strlen(STR(CHILD(n, i))) + 1; + len--; /* the last name doesn't have a dot */ + str = PyString_FromStringAndSize(NULL, len); + if (!str) + return NULL; + s = PyString_AS_STRING(str); + if (!s) + return NULL; + for (i = 0; i < NCH(n); i += 2) { + char *sch = STR(CHILD(n, i)); + strcpy(s, STR(CHILD(n, i))); + s += strlen(sch); + *s++ = '.'; + } + --s; + *s = '\0'; + PyString_InternInPlace(&str); + PyArena_AddPyObject(c->c_arena, str); + return alias(str, NULL, c->c_arena); + } + break; + case STAR: + str = PyString_InternFromString("*"); + PyArena_AddPyObject(c->c_arena, str); + return alias(str, NULL, c->c_arena); + default: + PyErr_Format(PyExc_SystemError, + "unexpected import name: %d", TYPE(n)); + return NULL; + } + + PyErr_SetString(PyExc_SystemError, "unhandled import name condition"); + return NULL; +} + +static stmt_ty +ast_for_import_stmt(struct compiling *c, const node *n) +{ + /* + import_stmt: import_name | import_from + import_name: 'import' dotted_as_names + import_from: 'from' ('.'* dotted_name | '.') 'import' + ('*' | '(' import_as_names ')' | import_as_names) + */ + int lineno; + int col_offset; + int i; + asdl_seq *aliases; + + REQ(n, import_stmt); + lineno = LINENO(n); + col_offset = n->n_col_offset; + n = CHILD(n, 0); + if (TYPE(n) == import_name) { + n = CHILD(n, 1); + REQ(n, dotted_as_names); + aliases = asdl_seq_new((NCH(n) + 1) / 2, c->c_arena); + if (!aliases) + return NULL; + for (i = 0; i < NCH(n); i += 2) { + alias_ty import_alias = alias_for_import_name(c, CHILD(n, i), 1); + if (!import_alias) + return NULL; + asdl_seq_SET(aliases, i / 2, import_alias); + } + return Import(aliases, lineno, col_offset, c->c_arena); + } + else if (TYPE(n) == import_from) { + int n_children; + int idx, ndots = 0; + alias_ty mod = NULL; + identifier modname = NULL; + + /* Count the number of dots (for relative imports) and check for the + optional module name */ + for (idx = 1; idx < NCH(n); idx++) { + if (TYPE(CHILD(n, idx)) == dotted_name) { + mod = alias_for_import_name(c, CHILD(n, idx), 0); + if (!mod) + return NULL; + idx++; + break; + } else if (TYPE(CHILD(n, idx)) != DOT) { + break; + } + ndots++; + } + idx++; /* skip over the 'import' keyword */ + switch (TYPE(CHILD(n, idx))) { + case STAR: + /* from ... import * */ + n = CHILD(n, idx); + n_children = 1; + break; + case LPAR: + /* from ... import (x, y, z) */ + n = CHILD(n, idx + 1); + n_children = NCH(n); + break; + case import_as_names: + /* from ... import x, y, z */ + n = CHILD(n, idx); + n_children = NCH(n); + if (n_children % 2 == 0) { + ast_error(n, "trailing comma not allowed without" + " surrounding parentheses"); + return NULL; + } + break; + default: + ast_error(n, "Unexpected node-type in from-import"); + return NULL; + } + + aliases = asdl_seq_new((n_children + 1) / 2, c->c_arena); + if (!aliases) + return NULL; + + /* handle "from ... import *" special b/c there's no children */ + if (TYPE(n) == STAR) { + alias_ty import_alias = alias_for_import_name(c, n, 1); + if (!import_alias) + return NULL; + asdl_seq_SET(aliases, 0, import_alias); + } + else { + for (i = 0; i < NCH(n); i += 2) { + alias_ty import_alias = alias_for_import_name(c, CHILD(n, i), 1); + if (!import_alias) + return NULL; + asdl_seq_SET(aliases, i / 2, import_alias); + } + } + if (mod != NULL) + modname = mod->name; + return ImportFrom(modname, aliases, ndots, lineno, col_offset, + c->c_arena); + } + PyErr_Format(PyExc_SystemError, + "unknown import statement: starts with command '%s'", + STR(CHILD(n, 0))); + return NULL; +} + +static stmt_ty +ast_for_global_stmt(struct compiling *c, const node *n) +{ + /* global_stmt: 'global' NAME (',' NAME)* */ + identifier name; + asdl_seq *s; + int i; + + REQ(n, global_stmt); + s = asdl_seq_new(NCH(n) / 2, c->c_arena); + if (!s) + return NULL; + for (i = 1; i < NCH(n); i += 2) { + name = NEW_IDENTIFIER(CHILD(n, i)); + if (!name) + return NULL; + asdl_seq_SET(s, i / 2, name); + } + return Global(s, LINENO(n), n->n_col_offset, c->c_arena); +} + +static stmt_ty +ast_for_exec_stmt(struct compiling *c, const node *n) +{ + expr_ty expr1, globals = NULL, locals = NULL; + int n_children = NCH(n); + if (n_children != 2 && n_children != 4 && n_children != 6) { + PyErr_Format(PyExc_SystemError, + "poorly formed 'exec' statement: %d parts to statement", + n_children); + return NULL; + } + + /* exec_stmt: 'exec' expr ['in' test [',' test]] */ + REQ(n, exec_stmt); + expr1 = ast_for_expr(c, CHILD(n, 1)); + if (!expr1) + return NULL; + + if (expr1->kind == Tuple_kind && n_children < 4 && + (asdl_seq_LEN(expr1->v.Tuple.elts) == 2 || + asdl_seq_LEN(expr1->v.Tuple.elts) == 3)) { + /* Backwards compatibility: passing exec args as a tuple */ + globals = asdl_seq_GET(expr1->v.Tuple.elts, 1); + if (asdl_seq_LEN(expr1->v.Tuple.elts) == 3) { + locals = asdl_seq_GET(expr1->v.Tuple.elts, 2); + } + expr1 = asdl_seq_GET(expr1->v.Tuple.elts, 0); + } + + if (n_children >= 4) { + globals = ast_for_expr(c, CHILD(n, 3)); + if (!globals) + return NULL; + } + if (n_children == 6) { + locals = ast_for_expr(c, CHILD(n, 5)); + if (!locals) + return NULL; + } + + return Exec(expr1, globals, locals, LINENO(n), n->n_col_offset, + c->c_arena); +} + +static stmt_ty +ast_for_assert_stmt(struct compiling *c, const node *n) +{ + /* assert_stmt: 'assert' test [',' test] */ + REQ(n, assert_stmt); + if (NCH(n) == 2) { + expr_ty expression = ast_for_expr(c, CHILD(n, 1)); + if (!expression) + return NULL; + return Assert(expression, NULL, LINENO(n), n->n_col_offset, + c->c_arena); + } + else if (NCH(n) == 4) { + expr_ty expr1, expr2; + + expr1 = ast_for_expr(c, CHILD(n, 1)); + if (!expr1) + return NULL; + expr2 = ast_for_expr(c, CHILD(n, 3)); + if (!expr2) + return NULL; + + return Assert(expr1, expr2, LINENO(n), n->n_col_offset, c->c_arena); + } + PyErr_Format(PyExc_SystemError, + "improper number of parts to 'assert' statement: %d", + NCH(n)); + return NULL; +} + +static asdl_seq * +ast_for_suite(struct compiling *c, const node *n) +{ + /* suite: simple_stmt | NEWLINE INDENT stmt+ DEDENT */ + asdl_seq *seq; + stmt_ty s; + int i, total, num, end, pos = 0; + node *ch; + + REQ(n, suite); + + total = num_stmts(n); + seq = asdl_seq_new(total, c->c_arena); + if (!seq) + return NULL; + if (TYPE(CHILD(n, 0)) == simple_stmt) { + n = CHILD(n, 0); + /* simple_stmt always ends with a NEWLINE, + and may have a trailing SEMI + */ + end = NCH(n) - 1; + if (TYPE(CHILD(n, end - 1)) == SEMI) + end--; + /* loop by 2 to skip semi-colons */ + for (i = 0; i < end; i += 2) { + ch = CHILD(n, i); + s = ast_for_stmt(c, ch); + if (!s) + return NULL; + asdl_seq_SET(seq, pos++, s); + } + } + else { + for (i = 2; i < (NCH(n) - 1); i++) { + ch = CHILD(n, i); + REQ(ch, stmt); + num = num_stmts(ch); + if (num == 1) { + /* small_stmt or compound_stmt with only one child */ + s = ast_for_stmt(c, ch); + if (!s) + return NULL; + asdl_seq_SET(seq, pos++, s); + } + else { + int j; + ch = CHILD(ch, 0); + REQ(ch, simple_stmt); + for (j = 0; j < NCH(ch); j += 2) { + /* statement terminates with a semi-colon ';' */ + if (NCH(CHILD(ch, j)) == 0) { + assert((j + 1) == NCH(ch)); + break; + } + s = ast_for_stmt(c, CHILD(ch, j)); + if (!s) + return NULL; + asdl_seq_SET(seq, pos++, s); + } + } + } + } + assert(pos == seq->size); + return seq; +} + +static stmt_ty +ast_for_if_stmt(struct compiling *c, const node *n) +{ + /* if_stmt: 'if' test ':' suite ('elif' test ':' suite)* + ['else' ':' suite] + */ + char *s; + + REQ(n, if_stmt); + + if (NCH(n) == 4) { + expr_ty expression; + asdl_seq *suite_seq; + + expression = ast_for_expr(c, CHILD(n, 1)); + if (!expression) + return NULL; + suite_seq = ast_for_suite(c, CHILD(n, 3)); + if (!suite_seq) + return NULL; + + return If(expression, suite_seq, NULL, LINENO(n), n->n_col_offset, + c->c_arena); + } + + s = STR(CHILD(n, 4)); + /* s[2], the third character in the string, will be + 's' for el_s_e, or + 'i' for el_i_f + */ + if (s[2] == 's') { + expr_ty expression; + asdl_seq *seq1, *seq2; + + expression = ast_for_expr(c, CHILD(n, 1)); + if (!expression) + return NULL; + seq1 = ast_for_suite(c, CHILD(n, 3)); + if (!seq1) + return NULL; + seq2 = ast_for_suite(c, CHILD(n, 6)); + if (!seq2) + return NULL; + + return If(expression, seq1, seq2, LINENO(n), n->n_col_offset, + c->c_arena); + } + else if (s[2] == 'i') { + int i, n_elif, has_else = 0; + expr_ty expression; + asdl_seq *suite_seq; + asdl_seq *orelse = NULL; + n_elif = NCH(n) - 4; + /* must reference the child n_elif+1 since 'else' token is third, + not fourth, child from the end. */ + if (TYPE(CHILD(n, (n_elif + 1))) == NAME + && STR(CHILD(n, (n_elif + 1)))[2] == 's') { + has_else = 1; + n_elif -= 3; + } + n_elif /= 4; + + if (has_else) { + asdl_seq *suite_seq2; + + orelse = asdl_seq_new(1, c->c_arena); + if (!orelse) + return NULL; + expression = ast_for_expr(c, CHILD(n, NCH(n) - 6)); + if (!expression) + return NULL; + suite_seq = ast_for_suite(c, CHILD(n, NCH(n) - 4)); + if (!suite_seq) + return NULL; + suite_seq2 = ast_for_suite(c, CHILD(n, NCH(n) - 1)); + if (!suite_seq2) + return NULL; + + asdl_seq_SET(orelse, 0, + If(expression, suite_seq, suite_seq2, + LINENO(CHILD(n, NCH(n) - 6)), + CHILD(n, NCH(n) - 6)->n_col_offset, + c->c_arena)); + /* the just-created orelse handled the last elif */ + n_elif--; + } + + for (i = 0; i < n_elif; i++) { + int off = 5 + (n_elif - i - 1) * 4; + asdl_seq *newobj = asdl_seq_new(1, c->c_arena); + if (!newobj) + return NULL; + expression = ast_for_expr(c, CHILD(n, off)); + if (!expression) + return NULL; + suite_seq = ast_for_suite(c, CHILD(n, off + 2)); + if (!suite_seq) + return NULL; + + asdl_seq_SET(newobj, 0, + If(expression, suite_seq, orelse, + LINENO(CHILD(n, off)), + CHILD(n, off)->n_col_offset, c->c_arena)); + orelse = newobj; + } + expression = ast_for_expr(c, CHILD(n, 1)); + if (!expression) + return NULL; + suite_seq = ast_for_suite(c, CHILD(n, 3)); + if (!suite_seq) + return NULL; + return If(expression, suite_seq, orelse, + LINENO(n), n->n_col_offset, c->c_arena); + } + + PyErr_Format(PyExc_SystemError, + "unexpected token in 'if' statement: %s", s); + return NULL; +} + +static stmt_ty +ast_for_while_stmt(struct compiling *c, const node *n) +{ + /* while_stmt: 'while' test ':' suite ['else' ':' suite] */ + REQ(n, while_stmt); + + if (NCH(n) == 4) { + expr_ty expression; + asdl_seq *suite_seq; + + expression = ast_for_expr(c, CHILD(n, 1)); + if (!expression) + return NULL; + suite_seq = ast_for_suite(c, CHILD(n, 3)); + if (!suite_seq) + return NULL; + return While(expression, suite_seq, NULL, LINENO(n), n->n_col_offset, + c->c_arena); + } + else if (NCH(n) == 7) { + expr_ty expression; + asdl_seq *seq1, *seq2; + + expression = ast_for_expr(c, CHILD(n, 1)); + if (!expression) + return NULL; + seq1 = ast_for_suite(c, CHILD(n, 3)); + if (!seq1) + return NULL; + seq2 = ast_for_suite(c, CHILD(n, 6)); + if (!seq2) + return NULL; + + return While(expression, seq1, seq2, LINENO(n), n->n_col_offset, + c->c_arena); + } + + PyErr_Format(PyExc_SystemError, + "wrong number of tokens for 'while' statement: %d", + NCH(n)); + return NULL; +} + +static stmt_ty +ast_for_for_stmt(struct compiling *c, const node *n) +{ + asdl_seq *_target, *seq = NULL, *suite_seq; + expr_ty expression; + expr_ty target, first; + const node *node_target; + /* for_stmt: 'for' exprlist 'in' testlist ':' suite ['else' ':' suite] */ + REQ(n, for_stmt); + + if (NCH(n) == 9) { + seq = ast_for_suite(c, CHILD(n, 8)); + if (!seq) + return NULL; + } + + node_target = CHILD(n, 1); + _target = ast_for_exprlist(c, node_target, Store); + if (!_target) + return NULL; + /* Check the # of children rather than the length of _target, since + for x, in ... has 1 element in _target, but still requires a Tuple. */ + first = (expr_ty)asdl_seq_GET(_target, 0); + if (NCH(node_target) == 1) + target = first; + else + target = Tuple(_target, Store, first->lineno, first->col_offset, c->c_arena); + + expression = ast_for_testlist(c, CHILD(n, 3)); + if (!expression) + return NULL; + suite_seq = ast_for_suite(c, CHILD(n, 5)); + if (!suite_seq) + return NULL; + + return For(target, expression, suite_seq, seq, LINENO(n), n->n_col_offset, + c->c_arena); +} + +static excepthandler_ty +ast_for_except_clause(struct compiling *c, const node *exc, node *body) +{ + /* except_clause: 'except' [test [(',' | 'as') test]] */ + REQ(exc, except_clause); + REQ(body, suite); + + if (NCH(exc) == 1) { + asdl_seq *suite_seq = ast_for_suite(c, body); + if (!suite_seq) + return NULL; + + return ExceptHandler(NULL, NULL, suite_seq, LINENO(exc), + exc->n_col_offset, c->c_arena); + } + else if (NCH(exc) == 2) { + expr_ty expression; + asdl_seq *suite_seq; + + expression = ast_for_expr(c, CHILD(exc, 1)); + if (!expression) + return NULL; + suite_seq = ast_for_suite(c, body); + if (!suite_seq) + return NULL; + + return ExceptHandler(expression, NULL, suite_seq, LINENO(exc), + exc->n_col_offset, c->c_arena); + } + else if (NCH(exc) == 4) { + asdl_seq *suite_seq; + expr_ty expression; + expr_ty e = ast_for_expr(c, CHILD(exc, 3)); + if (!e) + return NULL; + if (!set_context(c, e, Store, CHILD(exc, 3))) + return NULL; + expression = ast_for_expr(c, CHILD(exc, 1)); + if (!expression) + return NULL; + suite_seq = ast_for_suite(c, body); + if (!suite_seq) + return NULL; + + return ExceptHandler(expression, e, suite_seq, LINENO(exc), + exc->n_col_offset, c->c_arena); + } + + PyErr_Format(PyExc_SystemError, + "wrong number of children for 'except' clause: %d", + NCH(exc)); + return NULL; +} + +static stmt_ty +ast_for_try_stmt(struct compiling *c, const node *n) +{ + const int nch = NCH(n); + int n_except = (nch - 3)/3; + asdl_seq *body, *orelse = NULL, *finally = NULL; + + REQ(n, try_stmt); + + body = ast_for_suite(c, CHILD(n, 2)); + if (body == NULL) + return NULL; + + if (TYPE(CHILD(n, nch - 3)) == NAME) { + if (strcmp(STR(CHILD(n, nch - 3)), "finally") == 0) { + if (nch >= 9 && TYPE(CHILD(n, nch - 6)) == NAME) { + /* we can assume it's an "else", + because nch >= 9 for try-else-finally and + it would otherwise have a type of except_clause */ + orelse = ast_for_suite(c, CHILD(n, nch - 4)); + if (orelse == NULL) + return NULL; + n_except--; + } + + finally = ast_for_suite(c, CHILD(n, nch - 1)); + if (finally == NULL) + return NULL; + n_except--; + } + else { + /* we can assume it's an "else", + otherwise it would have a type of except_clause */ + orelse = ast_for_suite(c, CHILD(n, nch - 1)); + if (orelse == NULL) + return NULL; + n_except--; + } + } + else if (TYPE(CHILD(n, nch - 3)) != except_clause) { + ast_error(n, "malformed 'try' statement"); + return NULL; + } + + if (n_except > 0) { + int i; + stmt_ty except_st; + /* process except statements to create a try ... except */ + asdl_seq *handlers = asdl_seq_new(n_except, c->c_arena); + if (handlers == NULL) + return NULL; + + for (i = 0; i < n_except; i++) { + excepthandler_ty e = ast_for_except_clause(c, CHILD(n, 3 + i * 3), + CHILD(n, 5 + i * 3)); + if (!e) + return NULL; + asdl_seq_SET(handlers, i, e); + } + + except_st = TryExcept(body, handlers, orelse, LINENO(n), + n->n_col_offset, c->c_arena); + if (!finally) + return except_st; + + /* if a 'finally' is present too, we nest the TryExcept within a + TryFinally to emulate try ... except ... finally */ + body = asdl_seq_new(1, c->c_arena); + if (body == NULL) + return NULL; + asdl_seq_SET(body, 0, except_st); + } + + /* must be a try ... finally (except clauses are in body, if any exist) */ + assert(finally != NULL); + return TryFinally(body, finally, LINENO(n), n->n_col_offset, c->c_arena); +} + +/* with_item: test ['as' expr] */ +static stmt_ty +ast_for_with_item(struct compiling *c, const node *n, asdl_seq *content) +{ + expr_ty context_expr, optional_vars = NULL; + + REQ(n, with_item); + context_expr = ast_for_expr(c, CHILD(n, 0)); + if (!context_expr) + return NULL; + if (NCH(n) == 3) { + optional_vars = ast_for_expr(c, CHILD(n, 2)); + + if (!optional_vars) { + return NULL; + } + if (!set_context(c, optional_vars, Store, n)) { + return NULL; + } + } + + return With(context_expr, optional_vars, content, LINENO(n), + n->n_col_offset, c->c_arena); +} + +/* with_stmt: 'with' with_item (',' with_item)* ':' suite */ +static stmt_ty +ast_for_with_stmt(struct compiling *c, const node *n) +{ + int i; + stmt_ty ret; + asdl_seq *inner; + + REQ(n, with_stmt); + + /* process the with items inside-out */ + i = NCH(n) - 1; + /* the suite of the innermost with item is the suite of the with stmt */ + inner = ast_for_suite(c, CHILD(n, i)); + if (!inner) + return NULL; + + for (;;) { + i -= 2; + ret = ast_for_with_item(c, CHILD(n, i), inner); + if (!ret) + return NULL; + /* was this the last item? */ + if (i == 1) + break; + /* if not, wrap the result so far in a new sequence */ + inner = asdl_seq_new(1, c->c_arena); + if (!inner) + return NULL; + asdl_seq_SET(inner, 0, ret); + } + + return ret; +} + +static stmt_ty +ast_for_classdef(struct compiling *c, const node *n, asdl_seq *decorator_seq) +{ + /* classdef: 'class' NAME ['(' testlist ')'] ':' suite */ + PyObject *classname; + asdl_seq *bases, *s; + + REQ(n, classdef); + + if (!forbidden_check(c, n, STR(CHILD(n, 1)))) + return NULL; + + if (NCH(n) == 4) { + s = ast_for_suite(c, CHILD(n, 3)); + if (!s) + return NULL; + classname = NEW_IDENTIFIER(CHILD(n, 1)); + if (!classname) + return NULL; + return ClassDef(classname, NULL, s, decorator_seq, LINENO(n), + n->n_col_offset, c->c_arena); + } + /* check for empty base list */ + if (TYPE(CHILD(n,3)) == RPAR) { + s = ast_for_suite(c, CHILD(n,5)); + if (!s) + return NULL; + classname = NEW_IDENTIFIER(CHILD(n, 1)); + if (!classname) + return NULL; + return ClassDef(classname, NULL, s, decorator_seq, LINENO(n), + n->n_col_offset, c->c_arena); + } + + /* else handle the base class list */ + bases = ast_for_class_bases(c, CHILD(n, 3)); + if (!bases) + return NULL; + + s = ast_for_suite(c, CHILD(n, 6)); + if (!s) + return NULL; + classname = NEW_IDENTIFIER(CHILD(n, 1)); + if (!classname) + return NULL; + return ClassDef(classname, bases, s, decorator_seq, + LINENO(n), n->n_col_offset, c->c_arena); +} + +static stmt_ty +ast_for_stmt(struct compiling *c, const node *n) +{ + if (TYPE(n) == stmt) { + assert(NCH(n) == 1); + n = CHILD(n, 0); + } + if (TYPE(n) == simple_stmt) { + assert(num_stmts(n) == 1); + n = CHILD(n, 0); + } + if (TYPE(n) == small_stmt) { + n = CHILD(n, 0); + /* small_stmt: expr_stmt | print_stmt | del_stmt | pass_stmt + | flow_stmt | import_stmt | global_stmt | exec_stmt + | assert_stmt + */ + switch (TYPE(n)) { + case expr_stmt: + return ast_for_expr_stmt(c, n); + case print_stmt: + return ast_for_print_stmt(c, n); + case del_stmt: + return ast_for_del_stmt(c, n); + case pass_stmt: + return Pass(LINENO(n), n->n_col_offset, c->c_arena); + case flow_stmt: + return ast_for_flow_stmt(c, n); + case import_stmt: + return ast_for_import_stmt(c, n); + case global_stmt: + return ast_for_global_stmt(c, n); + case exec_stmt: + return ast_for_exec_stmt(c, n); + case assert_stmt: + return ast_for_assert_stmt(c, n); + default: + PyErr_Format(PyExc_SystemError, + "unhandled small_stmt: TYPE=%d NCH=%d\n", + TYPE(n), NCH(n)); + return NULL; + } + } + else { + /* compound_stmt: if_stmt | while_stmt | for_stmt | try_stmt + | funcdef | classdef | decorated + */ + node *ch = CHILD(n, 0); + REQ(n, compound_stmt); + switch (TYPE(ch)) { + case if_stmt: + return ast_for_if_stmt(c, ch); + case while_stmt: + return ast_for_while_stmt(c, ch); + case for_stmt: + return ast_for_for_stmt(c, ch); + case try_stmt: + return ast_for_try_stmt(c, ch); + case with_stmt: + return ast_for_with_stmt(c, ch); + case funcdef: + return ast_for_funcdef(c, ch, NULL); + case classdef: + return ast_for_classdef(c, ch, NULL); + case decorated: + return ast_for_decorated(c, ch); + default: + PyErr_Format(PyExc_SystemError, + "unhandled small_stmt: TYPE=%d NCH=%d\n", + TYPE(n), NCH(n)); + return NULL; + } + } +} + +static PyObject * +parsenumber(struct compiling *c, const char *s) +{ + const char *end; + long x; + double dx; +#ifndef WITHOUT_COMPLEX + Py_complex complex; + int imflag; +#endif + + assert(s != NULL); + errno = 0; + end = s + strlen(s) - 1; +#ifndef WITHOUT_COMPLEX + imflag = *end == 'j' || *end == 'J'; +#endif + if (*end == 'l' || *end == 'L') + return PyLong_FromString((char *)s, (char **)0, 0); + x = PyOS_strtol((char *)s, (char **)&end, 0); + if (*end == '\0') { + if (errno != 0) + return PyLong_FromString((char *)s, (char **)0, 0); + return PyInt_FromLong(x); + } + /* XXX Huge floats may silently fail */ +#ifndef WITHOUT_COMPLEX + if (imflag) { + complex.real = 0.; + complex.imag = PyOS_string_to_double(s, (char **)&end, NULL); + if (complex.imag == -1.0 && PyErr_Occurred()) + return NULL; + return PyComplex_FromCComplex(complex); + } + else +#endif + { + dx = PyOS_string_to_double(s, NULL, NULL); + if (dx == -1.0 && PyErr_Occurred()) + return NULL; + return PyFloat_FromDouble(dx); + } +} + +static PyObject * +decode_utf8(struct compiling *c, const char **sPtr, const char *end, char* encoding) +{ +#ifndef Py_USING_UNICODE + Py_FatalError("decode_utf8 should not be called in this build."); + return NULL; +#else + PyObject *u, *v; + char *s, *t; + t = s = (char *)*sPtr; + /* while (s < end && *s != '\\') s++; */ /* inefficient for u".." */ + while (s < end && (*s & 0x80)) s++; + *sPtr = s; + u = PyUnicode_DecodeUTF8(t, s - t, NULL); + if (u == NULL) + return NULL; + v = PyUnicode_AsEncodedString(u, encoding, NULL); + Py_DECREF(u); + return v; +#endif +} + +#ifdef Py_USING_UNICODE +static PyObject * +decode_unicode(struct compiling *c, const char *s, size_t len, int rawmode, const char *encoding) +{ + PyObject *v; + PyObject *u = NULL; + char *buf; + char *p; + const char *end; + if (encoding != NULL && strcmp(encoding, "iso-8859-1")) { + /* check for integer overflow */ + if (len > PY_SIZE_MAX / 6) + return NULL; + /* "" (2 bytes) may become "\U000000E4" (10 bytes), or 1:5 + "\ä" (3 bytes) may become "\u005c\U000000E4" (16 bytes), or ~1:6 */ + u = PyString_FromStringAndSize((char *)NULL, len * 6); + if (u == NULL) + return NULL; + p = buf = PyString_AsString(u); + end = s + len; + while (s < end) { + if (*s == '\\') { + *p++ = *s++; + if (*s & 0x80) { + strcpy(p, "u005c"); + p += 5; + } + } + if (*s & 0x80) { /* XXX inefficient */ + PyObject *w; + char *r; + Py_ssize_t rn, i; + w = decode_utf8(c, &s, end, "utf-32-be"); + if (w == NULL) { + Py_DECREF(u); + return NULL; + } + r = PyString_AsString(w); + rn = PyString_Size(w); + assert(rn % 4 == 0); + for (i = 0; i < rn; i += 4) { + sprintf(p, "\\U%02x%02x%02x%02x", + r[i + 0] & 0xFF, + r[i + 1] & 0xFF, + r[i + 2] & 0xFF, + r[i + 3] & 0xFF); + p += 10; + } + Py_DECREF(w); + } else { + *p++ = *s++; + } + } + len = p - buf; + s = buf; + } + if (rawmode) + v = PyUnicode_DecodeRawUnicodeEscape(s, len, NULL); + else + v = PyUnicode_DecodeUnicodeEscape(s, len, NULL); + Py_XDECREF(u); + return v; +} +#endif + +/* s is a Python string literal, including the bracketing quote characters, + * and r &/or u prefixes (if any), and embedded escape sequences (if any). + * parsestr parses it, and returns the decoded Python string object. + */ +static PyObject * +parsestr(struct compiling *c, const node *n, const char *s) +{ + size_t len, i; + int quote = Py_CHARMASK(*s); + int rawmode = 0; + int need_encoding; + int unicode = c->c_future_unicode; + int bytes = 0; + + if (isalpha(quote) || quote == '_') { + if (quote == 'u' || quote == 'U') { + quote = *++s; + unicode = 1; + } + if (quote == 'b' || quote == 'B') { + quote = *++s; + unicode = 0; + bytes = 1; + } + if (quote == 'r' || quote == 'R') { + quote = *++s; + rawmode = 1; + } + } + if (quote != '\'' && quote != '\"') { + PyErr_BadInternalCall(); + return NULL; + } + s++; + len = strlen(s); + if (len > INT_MAX) { + PyErr_SetString(PyExc_OverflowError, + "string to parse is too long"); + return NULL; + } + if (s[--len] != quote) { + PyErr_BadInternalCall(); + return NULL; + } + if (len >= 4 && s[0] == quote && s[1] == quote) { + s += 2; + len -= 2; + if (s[--len] != quote || s[--len] != quote) { + PyErr_BadInternalCall(); + return NULL; + } + } + if (Py_Py3kWarningFlag && bytes) { + for (i = 0; i < len; i++) { + if ((unsigned char)s[i] > 127) { + if (!ast_warn(c, n, + "non-ascii bytes literals not supported in 3.x")) + return NULL; + break; + } + } + } +#ifdef Py_USING_UNICODE + if (unicode || Py_UnicodeFlag) { + return decode_unicode(c, s, len, rawmode, c->c_encoding); + } +#endif + need_encoding = (c->c_encoding != NULL && + strcmp(c->c_encoding, "utf-8") != 0 && + strcmp(c->c_encoding, "iso-8859-1") != 0); + if (rawmode || strchr(s, '\\') == NULL) { + if (need_encoding) { +#ifndef Py_USING_UNICODE + /* This should not happen - we never see any other + encoding. */ + Py_FatalError( + "cannot deal with encodings in this build."); +#else + PyObject *v, *u = PyUnicode_DecodeUTF8(s, len, NULL); + if (u == NULL) + return NULL; + v = PyUnicode_AsEncodedString(u, c->c_encoding, NULL); + Py_DECREF(u); + return v; +#endif + } else { + return PyString_FromStringAndSize(s, len); + } + } + + return PyString_DecodeEscape(s, len, NULL, unicode, + need_encoding ? c->c_encoding : NULL); +} + +/* Build a Python string object out of a STRING atom. This takes care of + * compile-time literal catenation, calling parsestr() on each piece, and + * pasting the intermediate results together. + */ +static PyObject * +parsestrplus(struct compiling *c, const node *n) +{ + PyObject *v; + int i; + REQ(CHILD(n, 0), STRING); + if ((v = parsestr(c, n, STR(CHILD(n, 0)))) != NULL) { + /* String literal concatenation */ + for (i = 1; i < NCH(n); i++) { + PyObject *s; + s = parsestr(c, n, STR(CHILD(n, i))); + if (s == NULL) + goto onError; + if (PyString_Check(v) && PyString_Check(s)) { + PyString_ConcatAndDel(&v, s); + if (v == NULL) + goto onError; + } +#ifdef Py_USING_UNICODE + else { + PyObject *temp = PyUnicode_Concat(v, s); + Py_DECREF(s); + Py_DECREF(v); + v = temp; + if (v == NULL) + goto onError; + } +#endif + } + } + return v; + + onError: + Py_XDECREF(v); + return NULL; +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/bltinmodule.c b/AppPkg/Applications/Python/Python-2.7.10/Python/bltinmodule.c new file mode 100644 index 0000000000..188d6886bc --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/bltinmodule.c @@ -0,0 +1,3061 @@ +/* Built-in functions */ + +#include "Python.h" +#include "Python-ast.h" + +#include "node.h" +#include "code.h" +#include "eval.h" + +#include +#include /* for DBL_MANT_DIG and friends */ + +#ifdef RISCOS +#include "unixstuff.h" +#endif + +/* The default encoding used by the platform file system APIs + Can remain NULL for all platforms that don't have such a concept +*/ +#if defined(MS_WINDOWS) && defined(HAVE_USABLE_WCHAR_T) +const char *Py_FileSystemDefaultEncoding = "mbcs"; +#elif defined(__APPLE__) +const char *Py_FileSystemDefaultEncoding = "utf-8"; +#else +const char *Py_FileSystemDefaultEncoding = NULL; /* use default */ +#endif + +/* Forward */ +static PyObject *filterstring(PyObject *, PyObject *); +#ifdef Py_USING_UNICODE +static PyObject *filterunicode(PyObject *, PyObject *); +#endif +static PyObject *filtertuple (PyObject *, PyObject *); + +static PyObject * +builtin___import__(PyObject *self, PyObject *args, PyObject *kwds) +{ + static char *kwlist[] = {"name", "globals", "locals", "fromlist", + "level", 0}; + char *name; + PyObject *globals = NULL; + PyObject *locals = NULL; + PyObject *fromlist = NULL; + int level = -1; + + if (!PyArg_ParseTupleAndKeywords(args, kwds, "s|OOOi:__import__", + kwlist, &name, &globals, &locals, &fromlist, &level)) + return NULL; + return PyImport_ImportModuleLevel(name, globals, locals, + fromlist, level); +} + +PyDoc_STRVAR(import_doc, +"__import__(name, globals={}, locals={}, fromlist=[], level=-1) -> module\n\ +\n\ +Import a module. Because this function is meant for use by the Python\n\ +interpreter and not for general use it is better to use\n\ +importlib.import_module() to programmatically import a module.\n\ +\n\ +The globals argument is only used to determine the context;\n\ +they are not modified. The locals argument is unused. The fromlist\n\ +should be a list of names to emulate ``from name import ...'', or an\n\ +empty list to emulate ``import name''.\n\ +When importing a module from a package, note that __import__('A.B', ...)\n\ +returns package A when fromlist is empty, but its submodule B when\n\ +fromlist is not empty. Level is used to determine whether to perform \n\ +absolute or relative imports. -1 is the original strategy of attempting\n\ +both absolute and relative imports, 0 is absolute, a positive number\n\ +is the number of parent directories to search relative to the current module."); + + +static PyObject * +builtin_abs(PyObject *self, PyObject *v) +{ + return PyNumber_Absolute(v); +} + +PyDoc_STRVAR(abs_doc, +"abs(number) -> number\n\ +\n\ +Return the absolute value of the argument."); + +static PyObject * +builtin_all(PyObject *self, PyObject *v) +{ + PyObject *it, *item; + PyObject *(*iternext)(PyObject *); + int cmp; + + it = PyObject_GetIter(v); + if (it == NULL) + return NULL; + iternext = *Py_TYPE(it)->tp_iternext; + + for (;;) { + item = iternext(it); + if (item == NULL) + break; + cmp = PyObject_IsTrue(item); + Py_DECREF(item); + if (cmp < 0) { + Py_DECREF(it); + return NULL; + } + if (cmp == 0) { + Py_DECREF(it); + Py_RETURN_FALSE; + } + } + Py_DECREF(it); + if (PyErr_Occurred()) { + if (PyErr_ExceptionMatches(PyExc_StopIteration)) + PyErr_Clear(); + else + return NULL; + } + Py_RETURN_TRUE; +} + +PyDoc_STRVAR(all_doc, +"all(iterable) -> bool\n\ +\n\ +Return True if bool(x) is True for all values x in the iterable.\n\ +If the iterable is empty, return True."); + +static PyObject * +builtin_any(PyObject *self, PyObject *v) +{ + PyObject *it, *item; + PyObject *(*iternext)(PyObject *); + int cmp; + + it = PyObject_GetIter(v); + if (it == NULL) + return NULL; + iternext = *Py_TYPE(it)->tp_iternext; + + for (;;) { + item = iternext(it); + if (item == NULL) + break; + cmp = PyObject_IsTrue(item); + Py_DECREF(item); + if (cmp < 0) { + Py_DECREF(it); + return NULL; + } + if (cmp == 1) { + Py_DECREF(it); + Py_RETURN_TRUE; + } + } + Py_DECREF(it); + if (PyErr_Occurred()) { + if (PyErr_ExceptionMatches(PyExc_StopIteration)) + PyErr_Clear(); + else + return NULL; + } + Py_RETURN_FALSE; +} + +PyDoc_STRVAR(any_doc, +"any(iterable) -> bool\n\ +\n\ +Return True if bool(x) is True for any x in the iterable.\n\ +If the iterable is empty, return False."); + +static PyObject * +builtin_apply(PyObject *self, PyObject *args) +{ + PyObject *func, *alist = NULL, *kwdict = NULL; + PyObject *t = NULL, *retval = NULL; + + if (PyErr_WarnPy3k("apply() not supported in 3.x; " + "use func(*args, **kwargs)", 1) < 0) + return NULL; + + if (!PyArg_UnpackTuple(args, "apply", 1, 3, &func, &alist, &kwdict)) + return NULL; + if (alist != NULL) { + if (!PyTuple_Check(alist)) { + if (!PySequence_Check(alist)) { + PyErr_Format(PyExc_TypeError, + "apply() arg 2 expected sequence, found %s", + alist->ob_type->tp_name); + return NULL; + } + t = PySequence_Tuple(alist); + if (t == NULL) + return NULL; + alist = t; + } + } + if (kwdict != NULL && !PyDict_Check(kwdict)) { + PyErr_Format(PyExc_TypeError, + "apply() arg 3 expected dictionary, found %s", + kwdict->ob_type->tp_name); + goto finally; + } + retval = PyEval_CallObjectWithKeywords(func, alist, kwdict); + finally: + Py_XDECREF(t); + return retval; +} + +PyDoc_STRVAR(apply_doc, +"apply(object[, args[, kwargs]]) -> value\n\ +\n\ +Call a callable object with positional arguments taken from the tuple args,\n\ +and keyword arguments taken from the optional dictionary kwargs.\n\ +Note that classes are callable, as are instances with a __call__() method.\n\ +\n\ +Deprecated since release 2.3. Instead, use the extended call syntax:\n\ + function(*args, **keywords)."); + + +static PyObject * +builtin_bin(PyObject *self, PyObject *v) +{ + return PyNumber_ToBase(v, 2); +} + +PyDoc_STRVAR(bin_doc, +"bin(number) -> string\n\ +\n\ +Return the binary representation of an integer or long integer."); + + +static PyObject * +builtin_callable(PyObject *self, PyObject *v) +{ + return PyBool_FromLong((long)PyCallable_Check(v)); +} + +PyDoc_STRVAR(callable_doc, +"callable(object) -> bool\n\ +\n\ +Return whether the object is callable (i.e., some kind of function).\n\ +Note that classes are callable, as are instances with a __call__() method."); + + +static PyObject * +builtin_filter(PyObject *self, PyObject *args) +{ + PyObject *func, *seq, *result, *it, *arg; + Py_ssize_t len; /* guess for result list size */ + register Py_ssize_t j; + + if (!PyArg_UnpackTuple(args, "filter", 2, 2, &func, &seq)) + return NULL; + + /* Strings and tuples return a result of the same type. */ + if (PyString_Check(seq)) + return filterstring(func, seq); +#ifdef Py_USING_UNICODE + if (PyUnicode_Check(seq)) + return filterunicode(func, seq); +#endif + if (PyTuple_Check(seq)) + return filtertuple(func, seq); + + /* Pre-allocate argument list tuple. */ + arg = PyTuple_New(1); + if (arg == NULL) + return NULL; + + /* Get iterator. */ + it = PyObject_GetIter(seq); + if (it == NULL) + goto Fail_arg; + + /* Guess a result list size. */ + len = _PyObject_LengthHint(seq, 8); + if (len == -1) + goto Fail_it; + + /* Get a result list. */ + if (PyList_Check(seq) && seq->ob_refcnt == 1) { + /* Eww - can modify the list in-place. */ + Py_INCREF(seq); + result = seq; + } + else { + result = PyList_New(len); + if (result == NULL) + goto Fail_it; + } + + /* Build the result list. */ + j = 0; + for (;;) { + PyObject *item; + int ok; + + item = PyIter_Next(it); + if (item == NULL) { + if (PyErr_Occurred()) + goto Fail_result_it; + break; + } + + if (func == (PyObject *)&PyBool_Type || func == Py_None) { + ok = PyObject_IsTrue(item); + } + else { + PyObject *good; + PyTuple_SET_ITEM(arg, 0, item); + good = PyObject_Call(func, arg, NULL); + PyTuple_SET_ITEM(arg, 0, NULL); + if (good == NULL) { + Py_DECREF(item); + goto Fail_result_it; + } + ok = PyObject_IsTrue(good); + Py_DECREF(good); + } + if (ok > 0) { + if (j < len) + PyList_SET_ITEM(result, j, item); + else { + int status = PyList_Append(result, item); + Py_DECREF(item); + if (status < 0) + goto Fail_result_it; + } + ++j; + } + else { + Py_DECREF(item); + if (ok < 0) + goto Fail_result_it; + } + } + + + /* Cut back result list if len is too big. */ + if (j < len && PyList_SetSlice(result, j, len, NULL) < 0) + goto Fail_result_it; + + Py_DECREF(it); + Py_DECREF(arg); + return result; + +Fail_result_it: + Py_DECREF(result); +Fail_it: + Py_DECREF(it); +Fail_arg: + Py_DECREF(arg); + return NULL; +} + +PyDoc_STRVAR(filter_doc, +"filter(function or None, sequence) -> list, tuple, or string\n" +"\n" +"Return those items of sequence for which function(item) is true. If\n" +"function is None, return the items that are true. If sequence is a tuple\n" +"or string, return the same type, else return a list."); + +static PyObject * +builtin_format(PyObject *self, PyObject *args) +{ + PyObject *value; + PyObject *format_spec = NULL; + + if (!PyArg_ParseTuple(args, "O|O:format", &value, &format_spec)) + return NULL; + + return PyObject_Format(value, format_spec); +} + +PyDoc_STRVAR(format_doc, +"format(value[, format_spec]) -> string\n\ +\n\ +Returns value.__format__(format_spec)\n\ +format_spec defaults to \"\""); + +static PyObject * +builtin_chr(PyObject *self, PyObject *args) +{ + long x; + char s[1]; + + if (!PyArg_ParseTuple(args, "l:chr", &x)) + return NULL; + if (x < 0 || x >= 256) { + PyErr_SetString(PyExc_ValueError, + "chr() arg not in range(256)"); + return NULL; + } + s[0] = (char)x; + return PyString_FromStringAndSize(s, 1); +} + +PyDoc_STRVAR(chr_doc, +"chr(i) -> character\n\ +\n\ +Return a string of one character with ordinal i; 0 <= i < 256."); + + +#ifdef Py_USING_UNICODE +static PyObject * +builtin_unichr(PyObject *self, PyObject *args) +{ + int x; + + if (!PyArg_ParseTuple(args, "i:unichr", &x)) + return NULL; + + return PyUnicode_FromOrdinal(x); +} + +PyDoc_STRVAR(unichr_doc, +"unichr(i) -> Unicode character\n\ +\n\ +Return a Unicode string of one character with ordinal i; 0 <= i <= 0x10ffff."); +#endif + + +static PyObject * +builtin_cmp(PyObject *self, PyObject *args) +{ + PyObject *a, *b; + int c; + + if (!PyArg_UnpackTuple(args, "cmp", 2, 2, &a, &b)) + return NULL; + if (PyObject_Cmp(a, b, &c) < 0) + return NULL; + return PyInt_FromLong((long)c); +} + +PyDoc_STRVAR(cmp_doc, +"cmp(x, y) -> integer\n\ +\n\ +Return negative if xy."); + + +static PyObject * +builtin_coerce(PyObject *self, PyObject *args) +{ + PyObject *v, *w; + PyObject *res; + + if (PyErr_WarnPy3k("coerce() not supported in 3.x", 1) < 0) + return NULL; + + if (!PyArg_UnpackTuple(args, "coerce", 2, 2, &v, &w)) + return NULL; + if (PyNumber_Coerce(&v, &w) < 0) + return NULL; + res = PyTuple_Pack(2, v, w); + Py_DECREF(v); + Py_DECREF(w); + return res; +} + +PyDoc_STRVAR(coerce_doc, +"coerce(x, y) -> (x1, y1)\n\ +\n\ +Return a tuple consisting of the two numeric arguments converted to\n\ +a common type, using the same rules as used by arithmetic operations.\n\ +If coercion is not possible, raise TypeError."); + +static PyObject * +builtin_compile(PyObject *self, PyObject *args, PyObject *kwds) +{ + char *str; + char *filename; + char *startstr; + int mode = -1; + int dont_inherit = 0; + int supplied_flags = 0; + int is_ast; + PyCompilerFlags cf; + PyObject *result = NULL, *cmd, *tmp = NULL; + Py_ssize_t length; + static char *kwlist[] = {"source", "filename", "mode", "flags", + "dont_inherit", NULL}; + int start[] = {Py_file_input, Py_eval_input, Py_single_input}; + + if (!PyArg_ParseTupleAndKeywords(args, kwds, "Oss|ii:compile", + kwlist, &cmd, &filename, &startstr, + &supplied_flags, &dont_inherit)) + return NULL; + + cf.cf_flags = supplied_flags; + + if (supplied_flags & + ~(PyCF_MASK | PyCF_MASK_OBSOLETE | PyCF_DONT_IMPLY_DEDENT | PyCF_ONLY_AST)) + { + PyErr_SetString(PyExc_ValueError, + "compile(): unrecognised flags"); + return NULL; + } + /* XXX Warn if (supplied_flags & PyCF_MASK_OBSOLETE) != 0? */ + + if (!dont_inherit) { + PyEval_MergeCompilerFlags(&cf); + } + + if (strcmp(startstr, "exec") == 0) + mode = 0; + else if (strcmp(startstr, "eval") == 0) + mode = 1; + else if (strcmp(startstr, "single") == 0) + mode = 2; + else { + PyErr_SetString(PyExc_ValueError, + "compile() arg 3 must be 'exec', 'eval' or 'single'"); + return NULL; + } + + is_ast = PyAST_Check(cmd); + if (is_ast == -1) + return NULL; + if (is_ast) { + if (supplied_flags & PyCF_ONLY_AST) { + Py_INCREF(cmd); + result = cmd; + } + else { + PyArena *arena; + mod_ty mod; + + arena = PyArena_New(); + if (arena == NULL) + return NULL; + mod = PyAST_obj2mod(cmd, arena, mode); + if (mod == NULL) { + PyArena_Free(arena); + return NULL; + } + result = (PyObject*)PyAST_Compile(mod, filename, + &cf, arena); + PyArena_Free(arena); + } + return result; + } + +#ifdef Py_USING_UNICODE + if (PyUnicode_Check(cmd)) { + tmp = PyUnicode_AsUTF8String(cmd); + if (tmp == NULL) + return NULL; + cmd = tmp; + cf.cf_flags |= PyCF_SOURCE_IS_UTF8; + } +#endif + + if (PyObject_AsReadBuffer(cmd, (const void **)&str, &length)) + goto cleanup; + if ((size_t)length != strlen(str)) { + PyErr_SetString(PyExc_TypeError, + "compile() expected string without null bytes"); + goto cleanup; + } + result = Py_CompileStringFlags(str, filename, start[mode], &cf); +cleanup: + Py_XDECREF(tmp); + return result; +} + +PyDoc_STRVAR(compile_doc, +"compile(source, filename, mode[, flags[, dont_inherit]]) -> code object\n\ +\n\ +Compile the source string (a Python module, statement or expression)\n\ +into a code object that can be executed by the exec statement or eval().\n\ +The filename will be used for run-time error messages.\n\ +The mode must be 'exec' to compile a module, 'single' to compile a\n\ +single (interactive) statement, or 'eval' to compile an expression.\n\ +The flags argument, if present, controls which future statements influence\n\ +the compilation of the code.\n\ +The dont_inherit argument, if non-zero, stops the compilation inheriting\n\ +the effects of any future statements in effect in the code calling\n\ +compile; if absent or zero these statements do influence the compilation,\n\ +in addition to any features explicitly specified."); + +static PyObject * +builtin_dir(PyObject *self, PyObject *args) +{ + PyObject *arg = NULL; + + if (!PyArg_UnpackTuple(args, "dir", 0, 1, &arg)) + return NULL; + return PyObject_Dir(arg); +} + +PyDoc_STRVAR(dir_doc, +"dir([object]) -> list of strings\n" +"\n" +"If called without an argument, return the names in the current scope.\n" +"Else, return an alphabetized list of names comprising (some of) the attributes\n" +"of the given object, and of attributes reachable from it.\n" +"If the object supplies a method named __dir__, it will be used; otherwise\n" +"the default dir() logic is used and returns:\n" +" for a module object: the module's attributes.\n" +" for a class object: its attributes, and recursively the attributes\n" +" of its bases.\n" +" for any other object: its attributes, its class's attributes, and\n" +" recursively the attributes of its class's base classes."); + +static PyObject * +builtin_divmod(PyObject *self, PyObject *args) +{ + PyObject *v, *w; + + if (!PyArg_UnpackTuple(args, "divmod", 2, 2, &v, &w)) + return NULL; + return PyNumber_Divmod(v, w); +} + +PyDoc_STRVAR(divmod_doc, +"divmod(x, y) -> (quotient, remainder)\n\ +\n\ +Return the tuple ((x-x%y)/y, x%y). Invariant: div*y + mod == x."); + + +static PyObject * +builtin_eval(PyObject *self, PyObject *args) +{ + PyObject *cmd, *result, *tmp = NULL; + PyObject *globals = Py_None, *locals = Py_None; + char *str; + PyCompilerFlags cf; + + if (!PyArg_UnpackTuple(args, "eval", 1, 3, &cmd, &globals, &locals)) + return NULL; + if (locals != Py_None && !PyMapping_Check(locals)) { + PyErr_SetString(PyExc_TypeError, "locals must be a mapping"); + return NULL; + } + if (globals != Py_None && !PyDict_Check(globals)) { + PyErr_SetString(PyExc_TypeError, PyMapping_Check(globals) ? + "globals must be a real dict; try eval(expr, {}, mapping)" + : "globals must be a dict"); + return NULL; + } + if (globals == Py_None) { + globals = PyEval_GetGlobals(); + if (locals == Py_None) + locals = PyEval_GetLocals(); + } + else if (locals == Py_None) + locals = globals; + + if (globals == NULL || locals == NULL) { + PyErr_SetString(PyExc_TypeError, + "eval must be given globals and locals " + "when called without a frame"); + return NULL; + } + + if (PyDict_GetItemString(globals, "__builtins__") == NULL) { + if (PyDict_SetItemString(globals, "__builtins__", + PyEval_GetBuiltins()) != 0) + return NULL; + } + + if (PyCode_Check(cmd)) { + if (PyCode_GetNumFree((PyCodeObject *)cmd) > 0) { + PyErr_SetString(PyExc_TypeError, + "code object passed to eval() may not contain free variables"); + return NULL; + } + return PyEval_EvalCode((PyCodeObject *) cmd, globals, locals); + } + + if (!PyString_Check(cmd) && + !PyUnicode_Check(cmd)) { + PyErr_SetString(PyExc_TypeError, + "eval() arg 1 must be a string or code object"); + return NULL; + } + cf.cf_flags = 0; + +#ifdef Py_USING_UNICODE + if (PyUnicode_Check(cmd)) { + tmp = PyUnicode_AsUTF8String(cmd); + if (tmp == NULL) + return NULL; + cmd = tmp; + cf.cf_flags |= PyCF_SOURCE_IS_UTF8; + } +#endif + if (PyString_AsStringAndSize(cmd, &str, NULL)) { + Py_XDECREF(tmp); + return NULL; + } + while (*str == ' ' || *str == '\t') + str++; + + (void)PyEval_MergeCompilerFlags(&cf); + result = PyRun_StringFlags(str, Py_eval_input, globals, locals, &cf); + Py_XDECREF(tmp); + return result; +} + +PyDoc_STRVAR(eval_doc, +"eval(source[, globals[, locals]]) -> value\n\ +\n\ +Evaluate the source in the context of globals and locals.\n\ +The source may be a string representing a Python expression\n\ +or a code object as returned by compile().\n\ +The globals must be a dictionary and locals can be any mapping,\n\ +defaulting to the current globals and locals.\n\ +If only globals is given, locals defaults to it.\n"); + + +static PyObject * +builtin_execfile(PyObject *self, PyObject *args) +{ + char *filename; + PyObject *globals = Py_None, *locals = Py_None; + PyObject *res; + FILE* fp = NULL; + PyCompilerFlags cf; + int exists; + + if (PyErr_WarnPy3k("execfile() not supported in 3.x; use exec()", + 1) < 0) + return NULL; + + if (!PyArg_ParseTuple(args, "s|O!O:execfile", + &filename, + &PyDict_Type, &globals, + &locals)) + return NULL; + if (locals != Py_None && !PyMapping_Check(locals)) { + PyErr_SetString(PyExc_TypeError, "locals must be a mapping"); + return NULL; + } + if (globals == Py_None) { + globals = PyEval_GetGlobals(); + if (locals == Py_None) + locals = PyEval_GetLocals(); + } + else if (locals == Py_None) + locals = globals; + if (PyDict_GetItemString(globals, "__builtins__") == NULL) { + if (PyDict_SetItemString(globals, "__builtins__", + PyEval_GetBuiltins()) != 0) + return NULL; + } + + exists = 0; + /* Test for existence or directory. */ +#if defined(PLAN9) + { + Dir *d; + + if ((d = dirstat(filename))!=nil) { + if(d->mode & DMDIR) + werrstr("is a directory"); + else + exists = 1; + free(d); + } + } +#elif defined(RISCOS) + if (object_exists(filename)) { + if (isdir(filename)) + errno = EISDIR; + else + exists = 1; + } +#else /* standard Posix */ + { + struct stat s; + if (stat(filename, &s) == 0) { + if (S_ISDIR(s.st_mode)) +# if defined(PYOS_OS2) && defined(PYCC_VACPP) + errno = EOS2ERR; +# else + errno = EISDIR; +# endif + else + exists = 1; + } + } +#endif + + if (exists) { + Py_BEGIN_ALLOW_THREADS + fp = fopen(filename, "r" PY_STDIOTEXTMODE); + Py_END_ALLOW_THREADS + + if (fp == NULL) { + exists = 0; + } + } + + if (!exists) { + PyErr_SetFromErrnoWithFilename(PyExc_IOError, filename); + return NULL; + } + cf.cf_flags = 0; + if (PyEval_MergeCompilerFlags(&cf)) + res = PyRun_FileExFlags(fp, filename, Py_file_input, globals, + locals, 1, &cf); + else + res = PyRun_FileEx(fp, filename, Py_file_input, globals, + locals, 1); + return res; +} + +PyDoc_STRVAR(execfile_doc, +"execfile(filename[, globals[, locals]])\n\ +\n\ +Read and execute a Python script from a file.\n\ +The globals and locals are dictionaries, defaulting to the current\n\ +globals and locals. If only globals is given, locals defaults to it."); + + +static PyObject * +builtin_getattr(PyObject *self, PyObject *args) +{ + PyObject *v, *result, *dflt = NULL; + PyObject *name; + + if (!PyArg_UnpackTuple(args, "getattr", 2, 3, &v, &name, &dflt)) + return NULL; +#ifdef Py_USING_UNICODE + if (PyUnicode_Check(name)) { + name = _PyUnicode_AsDefaultEncodedString(name, NULL); + if (name == NULL) + return NULL; + } +#endif + + if (!PyString_Check(name)) { + PyErr_SetString(PyExc_TypeError, + "getattr(): attribute name must be string"); + return NULL; + } + result = PyObject_GetAttr(v, name); + if (result == NULL && dflt != NULL && + PyErr_ExceptionMatches(PyExc_AttributeError)) + { + PyErr_Clear(); + Py_INCREF(dflt); + result = dflt; + } + return result; +} + +PyDoc_STRVAR(getattr_doc, +"getattr(object, name[, default]) -> value\n\ +\n\ +Get a named attribute from an object; getattr(x, 'y') is equivalent to x.y.\n\ +When a default argument is given, it is returned when the attribute doesn't\n\ +exist; without it, an exception is raised in that case."); + + +static PyObject * +builtin_globals(PyObject *self) +{ + PyObject *d; + + d = PyEval_GetGlobals(); + Py_XINCREF(d); + return d; +} + +PyDoc_STRVAR(globals_doc, +"globals() -> dictionary\n\ +\n\ +Return the dictionary containing the current scope's global variables."); + + +static PyObject * +builtin_hasattr(PyObject *self, PyObject *args) +{ + PyObject *v; + PyObject *name; + + if (!PyArg_UnpackTuple(args, "hasattr", 2, 2, &v, &name)) + return NULL; +#ifdef Py_USING_UNICODE + if (PyUnicode_Check(name)) { + name = _PyUnicode_AsDefaultEncodedString(name, NULL); + if (name == NULL) + return NULL; + } +#endif + + if (!PyString_Check(name)) { + PyErr_SetString(PyExc_TypeError, + "hasattr(): attribute name must be string"); + return NULL; + } + v = PyObject_GetAttr(v, name); + if (v == NULL) { + if (!PyErr_ExceptionMatches(PyExc_Exception)) + return NULL; + else { + PyErr_Clear(); + Py_INCREF(Py_False); + return Py_False; + } + } + Py_DECREF(v); + Py_INCREF(Py_True); + return Py_True; +} + +PyDoc_STRVAR(hasattr_doc, +"hasattr(object, name) -> bool\n\ +\n\ +Return whether the object has an attribute with the given name.\n\ +(This is done by calling getattr(object, name) and catching exceptions.)"); + + +static PyObject * +builtin_id(PyObject *self, PyObject *v) +{ + return PyLong_FromVoidPtr(v); +} + +PyDoc_STRVAR(id_doc, +"id(object) -> integer\n\ +\n\ +Return the identity of an object. This is guaranteed to be unique among\n\ +simultaneously existing objects. (Hint: it's the object's memory address.)"); + + +static PyObject * +builtin_map(PyObject *self, PyObject *args) +{ + typedef struct { + PyObject *it; /* the iterator object */ + int saw_StopIteration; /* bool: did the iterator end? */ + } sequence; + + PyObject *func, *result; + sequence *seqs = NULL, *sqp; + Py_ssize_t n, len; + register int i, j; + + n = PyTuple_Size(args); + if (n < 2) { + PyErr_SetString(PyExc_TypeError, + "map() requires at least two args"); + return NULL; + } + + func = PyTuple_GetItem(args, 0); + n--; + + if (func == Py_None) { + if (PyErr_WarnPy3k("map(None, ...) not supported in 3.x; " + "use list(...)", 1) < 0) + return NULL; + if (n == 1) { + /* map(None, S) is the same as list(S). */ + return PySequence_List(PyTuple_GetItem(args, 1)); + } + } + + /* Get space for sequence descriptors. Must NULL out the iterator + * pointers so that jumping to Fail_2 later doesn't see trash. + */ + if ((seqs = PyMem_NEW(sequence, n)) == NULL) { + PyErr_NoMemory(); + return NULL; + } + for (i = 0; i < n; ++i) { + seqs[i].it = (PyObject*)NULL; + seqs[i].saw_StopIteration = 0; + } + + /* Do a first pass to obtain iterators for the arguments, and set len + * to the largest of their lengths. + */ + len = 0; + for (i = 0, sqp = seqs; i < n; ++i, ++sqp) { + PyObject *curseq; + Py_ssize_t curlen; + + /* Get iterator. */ + curseq = PyTuple_GetItem(args, i+1); + sqp->it = PyObject_GetIter(curseq); + if (sqp->it == NULL) { + static char errmsg[] = + "argument %d to map() must support iteration"; + char errbuf[sizeof(errmsg) + 25]; + PyOS_snprintf(errbuf, sizeof(errbuf), errmsg, i+2); + PyErr_SetString(PyExc_TypeError, errbuf); + goto Fail_2; + } + + /* Update len. */ + curlen = _PyObject_LengthHint(curseq, 8); + if (curlen > len) + len = curlen; + } + + /* Get space for the result list. */ + if ((result = (PyObject *) PyList_New(len)) == NULL) + goto Fail_2; + + /* Iterate over the sequences until all have stopped. */ + for (i = 0; ; ++i) { + PyObject *alist, *item=NULL, *value; + int numactive = 0; + + if (func == Py_None && n == 1) + alist = NULL; + else if ((alist = PyTuple_New(n)) == NULL) + goto Fail_1; + + for (j = 0, sqp = seqs; j < n; ++j, ++sqp) { + if (sqp->saw_StopIteration) { + Py_INCREF(Py_None); + item = Py_None; + } + else { + item = PyIter_Next(sqp->it); + if (item) + ++numactive; + else { + if (PyErr_Occurred()) { + Py_XDECREF(alist); + goto Fail_1; + } + Py_INCREF(Py_None); + item = Py_None; + sqp->saw_StopIteration = 1; + } + } + if (alist) + PyTuple_SET_ITEM(alist, j, item); + else + break; + } + + if (!alist) + alist = item; + + if (numactive == 0) { + Py_DECREF(alist); + break; + } + + if (func == Py_None) + value = alist; + else { + value = PyEval_CallObject(func, alist); + Py_DECREF(alist); + if (value == NULL) + goto Fail_1; + } + if (i >= len) { + int status = PyList_Append(result, value); + Py_DECREF(value); + if (status < 0) + goto Fail_1; + } + else if (PyList_SetItem(result, i, value) < 0) + goto Fail_1; + } + + if (i < len && PyList_SetSlice(result, i, len, NULL) < 0) + goto Fail_1; + + goto Succeed; + +Fail_1: + Py_DECREF(result); +Fail_2: + result = NULL; +Succeed: + assert(seqs); + for (i = 0; i < n; ++i) + Py_XDECREF(seqs[i].it); + PyMem_DEL(seqs); + return result; +} + +PyDoc_STRVAR(map_doc, +"map(function, sequence[, sequence, ...]) -> list\n\ +\n\ +Return a list of the results of applying the function to the items of\n\ +the argument sequence(s). If more than one sequence is given, the\n\ +function is called with an argument list consisting of the corresponding\n\ +item of each sequence, substituting None for missing values when not all\n\ +sequences have the same length. If the function is None, return a list of\n\ +the items of the sequence (or a list of tuples if more than one sequence)."); + + +static PyObject * +builtin_next(PyObject *self, PyObject *args) +{ + PyObject *it, *res; + PyObject *def = NULL; + + if (!PyArg_UnpackTuple(args, "next", 1, 2, &it, &def)) + return NULL; + if (!PyIter_Check(it)) { + PyErr_Format(PyExc_TypeError, + "%.200s object is not an iterator", + it->ob_type->tp_name); + return NULL; + } + + res = (*it->ob_type->tp_iternext)(it); + if (res != NULL) { + return res; + } else if (def != NULL) { + if (PyErr_Occurred()) { + if (!PyErr_ExceptionMatches(PyExc_StopIteration)) + return NULL; + PyErr_Clear(); + } + Py_INCREF(def); + return def; + } else if (PyErr_Occurred()) { + return NULL; + } else { + PyErr_SetNone(PyExc_StopIteration); + return NULL; + } +} + +PyDoc_STRVAR(next_doc, +"next(iterator[, default])\n\ +\n\ +Return the next item from the iterator. If default is given and the iterator\n\ +is exhausted, it is returned instead of raising StopIteration."); + + +static PyObject * +builtin_setattr(PyObject *self, PyObject *args) +{ + PyObject *v; + PyObject *name; + PyObject *value; + + if (!PyArg_UnpackTuple(args, "setattr", 3, 3, &v, &name, &value)) + return NULL; + if (PyObject_SetAttr(v, name, value) != 0) + return NULL; + Py_INCREF(Py_None); + return Py_None; +} + +PyDoc_STRVAR(setattr_doc, +"setattr(object, name, value)\n\ +\n\ +Set a named attribute on an object; setattr(x, 'y', v) is equivalent to\n\ +``x.y = v''."); + + +static PyObject * +builtin_delattr(PyObject *self, PyObject *args) +{ + PyObject *v; + PyObject *name; + + if (!PyArg_UnpackTuple(args, "delattr", 2, 2, &v, &name)) + return NULL; + if (PyObject_SetAttr(v, name, (PyObject *)NULL) != 0) + return NULL; + Py_INCREF(Py_None); + return Py_None; +} + +PyDoc_STRVAR(delattr_doc, +"delattr(object, name)\n\ +\n\ +Delete a named attribute on an object; delattr(x, 'y') is equivalent to\n\ +``del x.y''."); + + +static PyObject * +builtin_hash(PyObject *self, PyObject *v) +{ + long x; + + x = PyObject_Hash(v); + if (x == -1) + return NULL; + return PyInt_FromLong(x); +} + +PyDoc_STRVAR(hash_doc, +"hash(object) -> integer\n\ +\n\ +Return a hash value for the object. Two objects with the same value have\n\ +the same hash value. The reverse is not necessarily true, but likely."); + + +static PyObject * +builtin_hex(PyObject *self, PyObject *v) +{ + PyNumberMethods *nb; + PyObject *res; + + if ((nb = v->ob_type->tp_as_number) == NULL || + nb->nb_hex == NULL) { + PyErr_SetString(PyExc_TypeError, + "hex() argument can't be converted to hex"); + return NULL; + } + res = (*nb->nb_hex)(v); + if (res && !PyString_Check(res)) { + PyErr_Format(PyExc_TypeError, + "__hex__ returned non-string (type %.200s)", + res->ob_type->tp_name); + Py_DECREF(res); + return NULL; + } + return res; +} + +PyDoc_STRVAR(hex_doc, +"hex(number) -> string\n\ +\n\ +Return the hexadecimal representation of an integer or long integer."); + + +static PyObject *builtin_raw_input(PyObject *, PyObject *); + +static PyObject * +builtin_input(PyObject *self, PyObject *args) +{ + PyObject *line; + char *str; + PyObject *res; + PyObject *globals, *locals; + PyCompilerFlags cf; + + line = builtin_raw_input(self, args); + if (line == NULL) + return line; + if (!PyArg_Parse(line, "s;embedded '\\0' in input line", &str)) + return NULL; + while (*str == ' ' || *str == '\t') + str++; + globals = PyEval_GetGlobals(); + locals = PyEval_GetLocals(); + if (PyDict_GetItemString(globals, "__builtins__") == NULL) { + if (PyDict_SetItemString(globals, "__builtins__", + PyEval_GetBuiltins()) != 0) + return NULL; + } + cf.cf_flags = 0; + PyEval_MergeCompilerFlags(&cf); + res = PyRun_StringFlags(str, Py_eval_input, globals, locals, &cf); + Py_DECREF(line); + return res; +} + +PyDoc_STRVAR(input_doc, +"input([prompt]) -> value\n\ +\n\ +Equivalent to eval(raw_input(prompt))."); + + +static PyObject * +builtin_intern(PyObject *self, PyObject *args) +{ + PyObject *s; + if (!PyArg_ParseTuple(args, "S:intern", &s)) + return NULL; + if (!PyString_CheckExact(s)) { + PyErr_SetString(PyExc_TypeError, + "can't intern subclass of string"); + return NULL; + } + Py_INCREF(s); + PyString_InternInPlace(&s); + return s; +} + +PyDoc_STRVAR(intern_doc, +"intern(string) -> string\n\ +\n\ +``Intern'' the given string. This enters the string in the (global)\n\ +table of interned strings whose purpose is to speed up dictionary lookups.\n\ +Return the string itself or the previously interned string object with the\n\ +same value."); + + +static PyObject * +builtin_iter(PyObject *self, PyObject *args) +{ + PyObject *v, *w = NULL; + + if (!PyArg_UnpackTuple(args, "iter", 1, 2, &v, &w)) + return NULL; + if (w == NULL) + return PyObject_GetIter(v); + if (!PyCallable_Check(v)) { + PyErr_SetString(PyExc_TypeError, + "iter(v, w): v must be callable"); + return NULL; + } + return PyCallIter_New(v, w); +} + +PyDoc_STRVAR(iter_doc, +"iter(collection) -> iterator\n\ +iter(callable, sentinel) -> iterator\n\ +\n\ +Get an iterator from an object. In the first form, the argument must\n\ +supply its own iterator, or be a sequence.\n\ +In the second form, the callable is called until it returns the sentinel."); + + +static PyObject * +builtin_len(PyObject *self, PyObject *v) +{ + Py_ssize_t res; + + res = PyObject_Size(v); + if (res < 0 && PyErr_Occurred()) + return NULL; + return PyInt_FromSsize_t(res); +} + +PyDoc_STRVAR(len_doc, +"len(object) -> integer\n\ +\n\ +Return the number of items of a sequence or collection."); + + +static PyObject * +builtin_locals(PyObject *self) +{ + PyObject *d; + + d = PyEval_GetLocals(); + Py_XINCREF(d); + return d; +} + +PyDoc_STRVAR(locals_doc, +"locals() -> dictionary\n\ +\n\ +Update and return a dictionary containing the current scope's local variables."); + + +static PyObject * +min_max(PyObject *args, PyObject *kwds, int op) +{ + PyObject *v, *it, *item, *val, *maxitem, *maxval, *keyfunc=NULL; + const char *name = op == Py_LT ? "min" : "max"; + + if (PyTuple_Size(args) > 1) + v = args; + else if (!PyArg_UnpackTuple(args, (char *)name, 1, 1, &v)) + return NULL; + + if (kwds != NULL && PyDict_Check(kwds) && PyDict_Size(kwds)) { + keyfunc = PyDict_GetItemString(kwds, "key"); + if (PyDict_Size(kwds)!=1 || keyfunc == NULL) { + PyErr_Format(PyExc_TypeError, + "%s() got an unexpected keyword argument", name); + return NULL; + } + Py_INCREF(keyfunc); + } + + it = PyObject_GetIter(v); + if (it == NULL) { + Py_XDECREF(keyfunc); + return NULL; + } + + maxitem = NULL; /* the result */ + maxval = NULL; /* the value associated with the result */ + while (( item = PyIter_Next(it) )) { + /* get the value from the key function */ + if (keyfunc != NULL) { + val = PyObject_CallFunctionObjArgs(keyfunc, item, NULL); + if (val == NULL) + goto Fail_it_item; + } + /* no key function; the value is the item */ + else { + val = item; + Py_INCREF(val); + } + + /* maximum value and item are unset; set them */ + if (maxval == NULL) { + maxitem = item; + maxval = val; + } + /* maximum value and item are set; update them as necessary */ + else { + int cmp = PyObject_RichCompareBool(val, maxval, op); + if (cmp < 0) + goto Fail_it_item_and_val; + else if (cmp > 0) { + Py_DECREF(maxval); + Py_DECREF(maxitem); + maxval = val; + maxitem = item; + } + else { + Py_DECREF(item); + Py_DECREF(val); + } + } + } + if (PyErr_Occurred()) + goto Fail_it; + if (maxval == NULL) { + PyErr_Format(PyExc_ValueError, + "%s() arg is an empty sequence", name); + assert(maxitem == NULL); + } + else + Py_DECREF(maxval); + Py_DECREF(it); + Py_XDECREF(keyfunc); + return maxitem; + +Fail_it_item_and_val: + Py_DECREF(val); +Fail_it_item: + Py_DECREF(item); +Fail_it: + Py_XDECREF(maxval); + Py_XDECREF(maxitem); + Py_DECREF(it); + Py_XDECREF(keyfunc); + return NULL; +} + +static PyObject * +builtin_min(PyObject *self, PyObject *args, PyObject *kwds) +{ + return min_max(args, kwds, Py_LT); +} + +PyDoc_STRVAR(min_doc, +"min(iterable[, key=func]) -> value\n\ +min(a, b, c, ...[, key=func]) -> value\n\ +\n\ +With a single iterable argument, return its smallest item.\n\ +With two or more arguments, return the smallest argument."); + + +static PyObject * +builtin_max(PyObject *self, PyObject *args, PyObject *kwds) +{ + return min_max(args, kwds, Py_GT); +} + +PyDoc_STRVAR(max_doc, +"max(iterable[, key=func]) -> value\n\ +max(a, b, c, ...[, key=func]) -> value\n\ +\n\ +With a single iterable argument, return its largest item.\n\ +With two or more arguments, return the largest argument."); + + +static PyObject * +builtin_oct(PyObject *self, PyObject *v) +{ + PyNumberMethods *nb; + PyObject *res; + + if (v == NULL || (nb = v->ob_type->tp_as_number) == NULL || + nb->nb_oct == NULL) { + PyErr_SetString(PyExc_TypeError, + "oct() argument can't be converted to oct"); + return NULL; + } + res = (*nb->nb_oct)(v); + if (res && !PyString_Check(res)) { + PyErr_Format(PyExc_TypeError, + "__oct__ returned non-string (type %.200s)", + res->ob_type->tp_name); + Py_DECREF(res); + return NULL; + } + return res; +} + +PyDoc_STRVAR(oct_doc, +"oct(number) -> string\n\ +\n\ +Return the octal representation of an integer or long integer."); + + +static PyObject * +builtin_open(PyObject *self, PyObject *args, PyObject *kwds) +{ + return PyObject_Call((PyObject*)&PyFile_Type, args, kwds); +} + +PyDoc_STRVAR(open_doc, +"open(name[, mode[, buffering]]) -> file object\n\ +\n\ +Open a file using the file() type, returns a file object. This is the\n\ +preferred way to open a file. See file.__doc__ for further information."); + + +static PyObject * +builtin_ord(PyObject *self, PyObject* obj) +{ + long ord; + Py_ssize_t size; + + if (PyString_Check(obj)) { + size = PyString_GET_SIZE(obj); + if (size == 1) { + ord = (long)((unsigned char)*PyString_AS_STRING(obj)); + return PyInt_FromLong(ord); + } + } else if (PyByteArray_Check(obj)) { + size = PyByteArray_GET_SIZE(obj); + if (size == 1) { + ord = (long)((unsigned char)*PyByteArray_AS_STRING(obj)); + return PyInt_FromLong(ord); + } + +#ifdef Py_USING_UNICODE + } else if (PyUnicode_Check(obj)) { + size = PyUnicode_GET_SIZE(obj); + if (size == 1) { + ord = (long)*PyUnicode_AS_UNICODE(obj); + return PyInt_FromLong(ord); + } +#endif + } else { + PyErr_Format(PyExc_TypeError, + "ord() expected string of length 1, but " \ + "%.200s found", obj->ob_type->tp_name); + return NULL; + } + + PyErr_Format(PyExc_TypeError, + "ord() expected a character, " + "but string of length %zd found", + size); + return NULL; +} + +PyDoc_STRVAR(ord_doc, +"ord(c) -> integer\n\ +\n\ +Return the integer ordinal of a one-character string."); + + +static PyObject * +builtin_pow(PyObject *self, PyObject *args) +{ + PyObject *v, *w, *z = Py_None; + + if (!PyArg_UnpackTuple(args, "pow", 2, 3, &v, &w, &z)) + return NULL; + return PyNumber_Power(v, w, z); +} + +PyDoc_STRVAR(pow_doc, +"pow(x, y[, z]) -> number\n\ +\n\ +With two arguments, equivalent to x**y. With three arguments,\n\ +equivalent to (x**y) % z, but may be more efficient (e.g. for longs)."); + + +static PyObject * +builtin_print(PyObject *self, PyObject *args, PyObject *kwds) +{ + static char *kwlist[] = {"sep", "end", "file", 0}; + static PyObject *dummy_args = NULL; + static PyObject *unicode_newline = NULL, *unicode_space = NULL; + static PyObject *str_newline = NULL, *str_space = NULL; + PyObject *newline, *space; + PyObject *sep = NULL, *end = NULL, *file = NULL; + int i, err, use_unicode = 0; + + if (dummy_args == NULL) { + if (!(dummy_args = PyTuple_New(0))) + return NULL; + } + if (str_newline == NULL) { + str_newline = PyString_FromString("\n"); + if (str_newline == NULL) + return NULL; + str_space = PyString_FromString(" "); + if (str_space == NULL) { + Py_CLEAR(str_newline); + return NULL; + } +#ifdef Py_USING_UNICODE + unicode_newline = PyUnicode_FromString("\n"); + if (unicode_newline == NULL) { + Py_CLEAR(str_newline); + Py_CLEAR(str_space); + return NULL; + } + unicode_space = PyUnicode_FromString(" "); + if (unicode_space == NULL) { + Py_CLEAR(str_newline); + Py_CLEAR(str_space); + Py_CLEAR(unicode_space); + return NULL; + } +#endif + } + if (!PyArg_ParseTupleAndKeywords(dummy_args, kwds, "|OOO:print", + kwlist, &sep, &end, &file)) + return NULL; + if (file == NULL || file == Py_None) { + file = PySys_GetObject("stdout"); + /* sys.stdout may be None when FILE* stdout isn't connected */ + if (file == Py_None) + Py_RETURN_NONE; + } + if (sep == Py_None) { + sep = NULL; + } + else if (sep) { + if (PyUnicode_Check(sep)) { + use_unicode = 1; + } + else if (!PyString_Check(sep)) { + PyErr_Format(PyExc_TypeError, + "sep must be None, str or unicode, not %.200s", + sep->ob_type->tp_name); + return NULL; + } + } + if (end == Py_None) + end = NULL; + else if (end) { + if (PyUnicode_Check(end)) { + use_unicode = 1; + } + else if (!PyString_Check(end)) { + PyErr_Format(PyExc_TypeError, + "end must be None, str or unicode, not %.200s", + end->ob_type->tp_name); + return NULL; + } + } + + if (!use_unicode) { + for (i = 0; i < PyTuple_Size(args); i++) { + if (PyUnicode_Check(PyTuple_GET_ITEM(args, i))) { + use_unicode = 1; + break; + } + } + } + if (use_unicode) { + newline = unicode_newline; + space = unicode_space; + } + else { + newline = str_newline; + space = str_space; + } + + for (i = 0; i < PyTuple_Size(args); i++) { + if (i > 0) { + if (sep == NULL) + err = PyFile_WriteObject(space, file, + Py_PRINT_RAW); + else + err = PyFile_WriteObject(sep, file, + Py_PRINT_RAW); + if (err) + return NULL; + } + err = PyFile_WriteObject(PyTuple_GetItem(args, i), file, + Py_PRINT_RAW); + if (err) + return NULL; + } + + if (end == NULL) + err = PyFile_WriteObject(newline, file, Py_PRINT_RAW); + else + err = PyFile_WriteObject(end, file, Py_PRINT_RAW); + if (err) + return NULL; + + Py_RETURN_NONE; +} + +PyDoc_STRVAR(print_doc, +"print(value, ..., sep=' ', end='\\n', file=sys.stdout)\n\ +\n\ +Prints the values to a stream, or to sys.stdout by default.\n\ +Optional keyword arguments:\n\ +file: a file-like object (stream); defaults to the current sys.stdout.\n\ +sep: string inserted between values, default a space.\n\ +end: string appended after the last value, default a newline."); + + +/* Return number of items in range (lo, hi, step), when arguments are + * PyInt or PyLong objects. step > 0 required. Return a value < 0 if + * & only if the true value is too large to fit in a signed long. + * Arguments MUST return 1 with either PyInt_Check() or + * PyLong_Check(). Return -1 when there is an error. + */ +static long +get_len_of_range_longs(PyObject *lo, PyObject *hi, PyObject *step) +{ + /* ------------------------------------------------------------- + Algorithm is equal to that of get_len_of_range(), but it operates + on PyObjects (which are assumed to be PyLong or PyInt objects). + ---------------------------------------------------------------*/ + long n; + PyObject *diff = NULL; + PyObject *one = NULL; + PyObject *tmp1 = NULL, *tmp2 = NULL, *tmp3 = NULL; + /* holds sub-expression evaluations */ + + /* if (lo >= hi), return length of 0. */ + if (PyObject_Compare(lo, hi) >= 0) + return 0; + + if ((one = PyLong_FromLong(1L)) == NULL) + goto Fail; + + if ((tmp1 = PyNumber_Subtract(hi, lo)) == NULL) + goto Fail; + + if ((diff = PyNumber_Subtract(tmp1, one)) == NULL) + goto Fail; + + if ((tmp2 = PyNumber_FloorDivide(diff, step)) == NULL) + goto Fail; + + if ((tmp3 = PyNumber_Add(tmp2, one)) == NULL) + goto Fail; + + n = PyLong_AsLong(tmp3); + if (PyErr_Occurred()) { /* Check for Overflow */ + PyErr_Clear(); + goto Fail; + } + + Py_DECREF(tmp3); + Py_DECREF(tmp2); + Py_DECREF(diff); + Py_DECREF(tmp1); + Py_DECREF(one); + return n; + + Fail: + Py_XDECREF(tmp3); + Py_XDECREF(tmp2); + Py_XDECREF(diff); + Py_XDECREF(tmp1); + Py_XDECREF(one); + return -1; +} + +/* Helper function for handle_range_longs. If arg is int or long + object, returns it with incremented reference count. If arg is + float, raises type error. As a last resort, creates a new int by + calling arg type's nb_int method if it is defined. Returns NULL + and sets exception on error. + + Returns a new reference to an int object. */ +static PyObject * +get_range_long_argument(PyObject *arg, const char *name) +{ + PyObject *v; + PyNumberMethods *nb; + if (PyInt_Check(arg) || PyLong_Check(arg)) { + Py_INCREF(arg); + return arg; + } + if (PyFloat_Check(arg) || + (nb = Py_TYPE(arg)->tp_as_number) == NULL || + nb->nb_int == NULL) { + PyErr_Format(PyExc_TypeError, + "range() integer %s argument expected, got %s.", + name, arg->ob_type->tp_name); + return NULL; + } + v = nb->nb_int(arg); + if (v == NULL) + return NULL; + if (PyInt_Check(v) || PyLong_Check(v)) + return v; + Py_DECREF(v); + PyErr_SetString(PyExc_TypeError, + "__int__ should return int object"); + return NULL; +} + +/* An extension of builtin_range() that handles the case when PyLong + * arguments are given. */ +static PyObject * +handle_range_longs(PyObject *self, PyObject *args) +{ + PyObject *ilow = NULL; + PyObject *ihigh = NULL; + PyObject *istep = NULL; + + PyObject *low = NULL; + PyObject *high = NULL; + PyObject *step = NULL; + + PyObject *curnum = NULL; + PyObject *v = NULL; + long bign; + Py_ssize_t i, n; + int cmp_result; + + PyObject *zero = PyLong_FromLong(0); + + if (zero == NULL) + return NULL; + + if (!PyArg_UnpackTuple(args, "range", 1, 3, &ilow, &ihigh, &istep)) { + Py_DECREF(zero); + return NULL; + } + + /* Figure out which way we were called, supply defaults, and be + * sure to incref everything so that the decrefs at the end + * are correct. NB: ilow, ihigh and istep are borrowed references. + */ + assert(ilow != NULL); + if (ihigh == NULL) { + /* only 1 arg -- it's the upper limit */ + ihigh = ilow; + ilow = NULL; + } + + /* convert ihigh if necessary */ + assert(ihigh != NULL); + high = get_range_long_argument(ihigh, "end"); + if (high == NULL) + goto Fail; + + /* ihigh correct now; do ilow */ + if (ilow == NULL) { + Py_INCREF(zero); + low = zero; + } + else { + low = get_range_long_argument(ilow, "start"); + if (low == NULL) + goto Fail; + } + + /* ilow and ihigh correct now; do istep */ + if (istep == NULL) + step = PyLong_FromLong(1); + else + step = get_range_long_argument(istep, "step"); + if (step == NULL) + goto Fail; + + if (PyObject_Cmp(step, zero, &cmp_result) == -1) + goto Fail; + + if (cmp_result == 0) { + PyErr_SetString(PyExc_ValueError, + "range() step argument must not be zero"); + goto Fail; + } + + if (cmp_result > 0) + bign = get_len_of_range_longs(low, high, step); + else { + PyObject *neg_step = PyNumber_Negative(step); + if (neg_step == NULL) + goto Fail; + bign = get_len_of_range_longs(high, low, neg_step); + Py_DECREF(neg_step); + } + + n = (Py_ssize_t)bign; + if (bign < 0 || (long)n != bign) { + PyErr_SetString(PyExc_OverflowError, + "range() result has too many items"); + goto Fail; + } + + v = PyList_New(n); + if (v == NULL) + goto Fail; + + curnum = low; + Py_INCREF(curnum); + + for (i = 0; i < n; i++) { + PyObject *w = PyNumber_Long(curnum); + PyObject *tmp_num; + if (w == NULL) + goto Fail; + + PyList_SET_ITEM(v, i, w); + + tmp_num = PyNumber_Add(curnum, step); + if (tmp_num == NULL) + goto Fail; + + Py_DECREF(curnum); + curnum = tmp_num; + } + Py_DECREF(low); + Py_DECREF(high); + Py_DECREF(step); + Py_DECREF(zero); + Py_DECREF(curnum); + return v; + + Fail: + Py_XDECREF(low); + Py_XDECREF(high); + Py_XDECREF(step); + Py_DECREF(zero); + Py_XDECREF(curnum); + Py_XDECREF(v); + return NULL; +} + +/* Return number of items in range/xrange (lo, hi, step). step > 0 + * required. Return a value < 0 if & only if the true value is too + * large to fit in a signed long. + */ +static long +get_len_of_range(long lo, long hi, long step) +{ + /* ------------------------------------------------------------- + If lo >= hi, the range is empty. + Else if n values are in the range, the last one is + lo + (n-1)*step, which must be <= hi-1. Rearranging, + n <= (hi - lo - 1)/step + 1, so taking the floor of the RHS gives + the proper value. Since lo < hi in this case, hi-lo-1 >= 0, so + the RHS is non-negative and so truncation is the same as the + floor. Letting M be the largest positive long, the worst case + for the RHS numerator is hi=M, lo=-M-1, and then + hi-lo-1 = M-(-M-1)-1 = 2*M. Therefore unsigned long has enough + precision to compute the RHS exactly. + ---------------------------------------------------------------*/ + long n = 0; + if (lo < hi) { + unsigned long uhi = (unsigned long)hi; + unsigned long ulo = (unsigned long)lo; + unsigned long diff = uhi - ulo - 1; + n = (long)(diff / (unsigned long)step + 1); + } + return n; +} + +static PyObject * +builtin_range(PyObject *self, PyObject *args) +{ + long ilow = 0, ihigh = 0, istep = 1; + long bign; + Py_ssize_t i, n; + + PyObject *v; + + if (PyTuple_Size(args) <= 1) { + if (!PyArg_ParseTuple(args, + "l;range() requires 1-3 int arguments", + &ihigh)) { + PyErr_Clear(); + return handle_range_longs(self, args); + } + } + else { + if (!PyArg_ParseTuple(args, + "ll|l;range() requires 1-3 int arguments", + &ilow, &ihigh, &istep)) { + PyErr_Clear(); + return handle_range_longs(self, args); + } + } + if (istep == 0) { + PyErr_SetString(PyExc_ValueError, + "range() step argument must not be zero"); + return NULL; + } + if (istep > 0) + bign = get_len_of_range(ilow, ihigh, istep); + else + bign = get_len_of_range(ihigh, ilow, -istep); + n = (Py_ssize_t)bign; + if (bign < 0 || (long)n != bign) { + PyErr_SetString(PyExc_OverflowError, + "range() result has too many items"); + return NULL; + } + v = PyList_New(n); + if (v == NULL) + return NULL; + for (i = 0; i < n; i++) { + PyObject *w = PyInt_FromLong(ilow); + if (w == NULL) { + Py_DECREF(v); + return NULL; + } + PyList_SET_ITEM(v, i, w); + ilow += istep; + } + return v; +} + +PyDoc_STRVAR(range_doc, +"range(stop) -> list of integers\n\ +range(start, stop[, step]) -> list of integers\n\ +\n\ +Return a list containing an arithmetic progression of integers.\n\ +range(i, j) returns [i, i+1, i+2, ..., j-1]; start (!) defaults to 0.\n\ +When step is given, it specifies the increment (or decrement).\n\ +For example, range(4) returns [0, 1, 2, 3]. The end point is omitted!\n\ +These are exactly the valid indices for a list of 4 elements."); + + +static PyObject * +builtin_raw_input(PyObject *self, PyObject *args) +{ + PyObject *v = NULL; + PyObject *fin = PySys_GetObject("stdin"); + PyObject *fout = PySys_GetObject("stdout"); + + if (!PyArg_UnpackTuple(args, "[raw_]input", 0, 1, &v)) + return NULL; + + if (fin == NULL) { + PyErr_SetString(PyExc_RuntimeError, "[raw_]input: lost sys.stdin"); + return NULL; + } + if (fout == NULL) { + PyErr_SetString(PyExc_RuntimeError, "[raw_]input: lost sys.stdout"); + return NULL; + } + if (PyFile_SoftSpace(fout, 0)) { + if (PyFile_WriteString(" ", fout) != 0) + return NULL; + } + if (PyFile_AsFile(fin) && PyFile_AsFile(fout) + && isatty(fileno(PyFile_AsFile(fin))) + && isatty(fileno(PyFile_AsFile(fout)))) { + PyObject *po; + char *prompt; + char *s; + PyObject *result; + if (v != NULL) { + po = PyObject_Str(v); + if (po == NULL) + return NULL; + prompt = PyString_AsString(po); + if (prompt == NULL) + return NULL; + } + else { + po = NULL; + prompt = ""; + } + s = PyOS_Readline(PyFile_AsFile(fin), PyFile_AsFile(fout), + prompt); + Py_XDECREF(po); + if (s == NULL) { + if (!PyErr_Occurred()) + PyErr_SetNone(PyExc_KeyboardInterrupt); + return NULL; + } + if (*s == '\0') { + PyErr_SetNone(PyExc_EOFError); + result = NULL; + } + else { /* strip trailing '\n' */ + size_t len = strlen(s); + if (len > PY_SSIZE_T_MAX) { + PyErr_SetString(PyExc_OverflowError, + "[raw_]input: input too long"); + result = NULL; + } + else { + result = PyString_FromStringAndSize(s, len-1); + } + } + PyMem_FREE(s); + return result; + } + if (v != NULL) { + if (PyFile_WriteObject(v, fout, Py_PRINT_RAW) != 0) + return NULL; + } + return PyFile_GetLine(fin, -1); +} + +PyDoc_STRVAR(raw_input_doc, +"raw_input([prompt]) -> string\n\ +\n\ +Read a string from standard input. The trailing newline is stripped.\n\ +If the user hits EOF (Unix: Ctl-D, Windows: Ctl-Z+Return), raise EOFError.\n\ +On Unix, GNU readline is used if enabled. The prompt string, if given,\n\ +is printed without a trailing newline before reading."); + + +static PyObject * +builtin_reduce(PyObject *self, PyObject *args) +{ + static PyObject *functools_reduce = NULL; + + if (PyErr_WarnPy3k("reduce() not supported in 3.x; " + "use functools.reduce()", 1) < 0) + return NULL; + + if (functools_reduce == NULL) { + PyObject *functools = PyImport_ImportModule("functools"); + if (functools == NULL) + return NULL; + functools_reduce = PyObject_GetAttrString(functools, "reduce"); + Py_DECREF(functools); + if (functools_reduce == NULL) + return NULL; + } + return PyObject_Call(functools_reduce, args, NULL); +} + +PyDoc_STRVAR(reduce_doc, +"reduce(function, sequence[, initial]) -> value\n\ +\n\ +Apply a function of two arguments cumulatively to the items of a sequence,\n\ +from left to right, so as to reduce the sequence to a single value.\n\ +For example, reduce(lambda x, y: x+y, [1, 2, 3, 4, 5]) calculates\n\ +((((1+2)+3)+4)+5). If initial is present, it is placed before the items\n\ +of the sequence in the calculation, and serves as a default when the\n\ +sequence is empty."); + + +static PyObject * +builtin_reload(PyObject *self, PyObject *v) +{ + if (PyErr_WarnPy3k("In 3.x, reload() is renamed to imp.reload()", + 1) < 0) + return NULL; + + return PyImport_ReloadModule(v); +} + +PyDoc_STRVAR(reload_doc, +"reload(module) -> module\n\ +\n\ +Reload the module. The module must have been successfully imported before."); + + +static PyObject * +builtin_repr(PyObject *self, PyObject *v) +{ + return PyObject_Repr(v); +} + +PyDoc_STRVAR(repr_doc, +"repr(object) -> string\n\ +\n\ +Return the canonical string representation of the object.\n\ +For most object types, eval(repr(object)) == object."); + + +static PyObject * +builtin_round(PyObject *self, PyObject *args, PyObject *kwds) +{ + double x; + PyObject *o_ndigits = NULL; + Py_ssize_t ndigits; + static char *kwlist[] = {"number", "ndigits", 0}; + + if (!PyArg_ParseTupleAndKeywords(args, kwds, "d|O:round", + kwlist, &x, &o_ndigits)) + return NULL; + + if (o_ndigits == NULL) { + /* second argument defaults to 0 */ + ndigits = 0; + } + else { + /* interpret 2nd argument as a Py_ssize_t; clip on overflow */ + ndigits = PyNumber_AsSsize_t(o_ndigits, NULL); + if (ndigits == -1 && PyErr_Occurred()) + return NULL; + } + + /* nans, infinities and zeros round to themselves */ + if (!Py_IS_FINITE(x) || x == 0.0) + return PyFloat_FromDouble(x); + + /* Deal with extreme values for ndigits. For ndigits > NDIGITS_MAX, x + always rounds to itself. For ndigits < NDIGITS_MIN, x always + rounds to +-0.0. Here 0.30103 is an upper bound for log10(2). */ +#define NDIGITS_MAX ((int)((DBL_MANT_DIG-DBL_MIN_EXP) * 0.30103)) +#define NDIGITS_MIN (-(int)((DBL_MAX_EXP + 1) * 0.30103)) + if (ndigits > NDIGITS_MAX) + /* return x */ + return PyFloat_FromDouble(x); + else if (ndigits < NDIGITS_MIN) + /* return 0.0, but with sign of x */ + return PyFloat_FromDouble(0.0*x); + else + /* finite x, and ndigits is not unreasonably large */ + /* _Py_double_round is defined in floatobject.c */ + return _Py_double_round(x, (int)ndigits); +#undef NDIGITS_MAX +#undef NDIGITS_MIN +} + +PyDoc_STRVAR(round_doc, +"round(number[, ndigits]) -> floating point number\n\ +\n\ +Round a number to a given precision in decimal digits (default 0 digits).\n\ +This always returns a floating point number. Precision may be negative."); + +static PyObject * +builtin_sorted(PyObject *self, PyObject *args, PyObject *kwds) +{ + PyObject *newlist, *v, *seq, *compare=NULL, *keyfunc=NULL, *newargs; + PyObject *callable; + static char *kwlist[] = {"iterable", "cmp", "key", "reverse", 0}; + int reverse; + + /* args 1-4 should match listsort in Objects/listobject.c */ + if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|OOi:sorted", + kwlist, &seq, &compare, &keyfunc, &reverse)) + return NULL; + + newlist = PySequence_List(seq); + if (newlist == NULL) + return NULL; + + callable = PyObject_GetAttrString(newlist, "sort"); + if (callable == NULL) { + Py_DECREF(newlist); + return NULL; + } + + newargs = PyTuple_GetSlice(args, 1, 4); + if (newargs == NULL) { + Py_DECREF(newlist); + Py_DECREF(callable); + return NULL; + } + + v = PyObject_Call(callable, newargs, kwds); + Py_DECREF(newargs); + Py_DECREF(callable); + if (v == NULL) { + Py_DECREF(newlist); + return NULL; + } + Py_DECREF(v); + return newlist; +} + +PyDoc_STRVAR(sorted_doc, +"sorted(iterable, cmp=None, key=None, reverse=False) --> new sorted list"); + +static PyObject * +builtin_vars(PyObject *self, PyObject *args) +{ + PyObject *v = NULL; + PyObject *d; + + if (!PyArg_UnpackTuple(args, "vars", 0, 1, &v)) + return NULL; + if (v == NULL) { + d = PyEval_GetLocals(); + if (d == NULL) { + if (!PyErr_Occurred()) + PyErr_SetString(PyExc_SystemError, + "vars(): no locals!?"); + } + else + Py_INCREF(d); + } + else { + d = PyObject_GetAttrString(v, "__dict__"); + if (d == NULL) { + PyErr_SetString(PyExc_TypeError, + "vars() argument must have __dict__ attribute"); + return NULL; + } + } + return d; +} + +PyDoc_STRVAR(vars_doc, +"vars([object]) -> dictionary\n\ +\n\ +Without arguments, equivalent to locals().\n\ +With an argument, equivalent to object.__dict__."); + + +static PyObject* +builtin_sum(PyObject *self, PyObject *args) +{ + PyObject *seq; + PyObject *result = NULL; + PyObject *temp, *item, *iter; + + if (!PyArg_UnpackTuple(args, "sum", 1, 2, &seq, &result)) + return NULL; + + iter = PyObject_GetIter(seq); + if (iter == NULL) + return NULL; + + if (result == NULL) { + result = PyInt_FromLong(0); + if (result == NULL) { + Py_DECREF(iter); + return NULL; + } + } else { + /* reject string values for 'start' parameter */ + if (PyObject_TypeCheck(result, &PyBaseString_Type)) { + PyErr_SetString(PyExc_TypeError, + "sum() can't sum strings [use ''.join(seq) instead]"); + Py_DECREF(iter); + return NULL; + } + Py_INCREF(result); + } + +#ifndef SLOW_SUM + /* Fast addition by keeping temporary sums in C instead of new Python objects. + Assumes all inputs are the same type. If the assumption fails, default + to the more general routine. + */ + if (PyInt_CheckExact(result)) { + long i_result = PyInt_AS_LONG(result); + Py_DECREF(result); + result = NULL; + while(result == NULL) { + item = PyIter_Next(iter); + if (item == NULL) { + Py_DECREF(iter); + if (PyErr_Occurred()) + return NULL; + return PyInt_FromLong(i_result); + } + if (PyInt_CheckExact(item)) { + long b = PyInt_AS_LONG(item); + long x = i_result + b; + if ((x^i_result) >= 0 || (x^b) >= 0) { + i_result = x; + Py_DECREF(item); + continue; + } + } + /* Either overflowed or is not an int. Restore real objects and process normally */ + result = PyInt_FromLong(i_result); + temp = PyNumber_Add(result, item); + Py_DECREF(result); + Py_DECREF(item); + result = temp; + if (result == NULL) { + Py_DECREF(iter); + return NULL; + } + } + } + + if (PyFloat_CheckExact(result)) { + double f_result = PyFloat_AS_DOUBLE(result); + Py_DECREF(result); + result = NULL; + while(result == NULL) { + item = PyIter_Next(iter); + if (item == NULL) { + Py_DECREF(iter); + if (PyErr_Occurred()) + return NULL; + return PyFloat_FromDouble(f_result); + } + if (PyFloat_CheckExact(item)) { + PyFPE_START_PROTECT("add", Py_DECREF(item); Py_DECREF(iter); return 0) + f_result += PyFloat_AS_DOUBLE(item); + PyFPE_END_PROTECT(f_result) + Py_DECREF(item); + continue; + } + if (PyInt_CheckExact(item)) { + PyFPE_START_PROTECT("add", Py_DECREF(item); Py_DECREF(iter); return 0) + f_result += (double)PyInt_AS_LONG(item); + PyFPE_END_PROTECT(f_result) + Py_DECREF(item); + continue; + } + result = PyFloat_FromDouble(f_result); + temp = PyNumber_Add(result, item); + Py_DECREF(result); + Py_DECREF(item); + result = temp; + if (result == NULL) { + Py_DECREF(iter); + return NULL; + } + } + } +#endif + + for(;;) { + item = PyIter_Next(iter); + if (item == NULL) { + /* error, or end-of-sequence */ + if (PyErr_Occurred()) { + Py_DECREF(result); + result = NULL; + } + break; + } + /* It's tempting to use PyNumber_InPlaceAdd instead of + PyNumber_Add here, to avoid quadratic running time + when doing 'sum(list_of_lists, [])'. However, this + would produce a change in behaviour: a snippet like + + empty = [] + sum([[x] for x in range(10)], empty) + + would change the value of empty. */ + temp = PyNumber_Add(result, item); + Py_DECREF(result); + Py_DECREF(item); + result = temp; + if (result == NULL) + break; + } + Py_DECREF(iter); + return result; +} + +PyDoc_STRVAR(sum_doc, +"sum(sequence[, start]) -> value\n\ +\n\ +Return the sum of a sequence of numbers (NOT strings) plus the value\n\ +of parameter 'start' (which defaults to 0). When the sequence is\n\ +empty, return start."); + + +static PyObject * +builtin_isinstance(PyObject *self, PyObject *args) +{ + PyObject *inst; + PyObject *cls; + int retval; + + if (!PyArg_UnpackTuple(args, "isinstance", 2, 2, &inst, &cls)) + return NULL; + + retval = PyObject_IsInstance(inst, cls); + if (retval < 0) + return NULL; + return PyBool_FromLong(retval); +} + +PyDoc_STRVAR(isinstance_doc, +"isinstance(object, class-or-type-or-tuple) -> bool\n\ +\n\ +Return whether an object is an instance of a class or of a subclass thereof.\n\ +With a type as second argument, return whether that is the object's type.\n\ +The form using a tuple, isinstance(x, (A, B, ...)), is a shortcut for\n\ +isinstance(x, A) or isinstance(x, B) or ... (etc.)."); + + +static PyObject * +builtin_issubclass(PyObject *self, PyObject *args) +{ + PyObject *derived; + PyObject *cls; + int retval; + + if (!PyArg_UnpackTuple(args, "issubclass", 2, 2, &derived, &cls)) + return NULL; + + retval = PyObject_IsSubclass(derived, cls); + if (retval < 0) + return NULL; + return PyBool_FromLong(retval); +} + +PyDoc_STRVAR(issubclass_doc, +"issubclass(C, B) -> bool\n\ +\n\ +Return whether class C is a subclass (i.e., a derived class) of class B.\n\ +When using a tuple as the second argument issubclass(X, (A, B, ...)),\n\ +is a shortcut for issubclass(X, A) or issubclass(X, B) or ... (etc.)."); + + +static PyObject* +builtin_zip(PyObject *self, PyObject *args) +{ + PyObject *ret; + const Py_ssize_t itemsize = PySequence_Length(args); + Py_ssize_t i; + PyObject *itlist; /* tuple of iterators */ + Py_ssize_t len; /* guess at result length */ + + if (itemsize == 0) + return PyList_New(0); + + /* args must be a tuple */ + assert(PyTuple_Check(args)); + + /* Guess at result length: the shortest of the input lengths. + If some argument refuses to say, we refuse to guess too, lest + an argument like xrange(sys.maxint) lead us astray.*/ + len = -1; /* unknown */ + for (i = 0; i < itemsize; ++i) { + PyObject *item = PyTuple_GET_ITEM(args, i); + Py_ssize_t thislen = _PyObject_LengthHint(item, -2); + if (thislen < 0) { + if (thislen == -1) + return NULL; + len = -1; + break; + } + else if (len < 0 || thislen < len) + len = thislen; + } + + /* allocate result list */ + if (len < 0) + len = 10; /* arbitrary */ + if ((ret = PyList_New(len)) == NULL) + return NULL; + + /* obtain iterators */ + itlist = PyTuple_New(itemsize); + if (itlist == NULL) + goto Fail_ret; + for (i = 0; i < itemsize; ++i) { + PyObject *item = PyTuple_GET_ITEM(args, i); + PyObject *it = PyObject_GetIter(item); + if (it == NULL) { + if (PyErr_ExceptionMatches(PyExc_TypeError)) + PyErr_Format(PyExc_TypeError, + "zip argument #%zd must support iteration", + i+1); + goto Fail_ret_itlist; + } + PyTuple_SET_ITEM(itlist, i, it); + } + + /* build result into ret list */ + for (i = 0; ; ++i) { + int j; + PyObject *next = PyTuple_New(itemsize); + if (!next) + goto Fail_ret_itlist; + + for (j = 0; j < itemsize; j++) { + PyObject *it = PyTuple_GET_ITEM(itlist, j); + PyObject *item = PyIter_Next(it); + if (!item) { + if (PyErr_Occurred()) { + Py_DECREF(ret); + ret = NULL; + } + Py_DECREF(next); + Py_DECREF(itlist); + goto Done; + } + PyTuple_SET_ITEM(next, j, item); + } + + if (i < len) + PyList_SET_ITEM(ret, i, next); + else { + int status = PyList_Append(ret, next); + Py_DECREF(next); + ++len; + if (status < 0) + goto Fail_ret_itlist; + } + } + +Done: + if (ret != NULL && i < len) { + /* The list is too big. */ + if (PyList_SetSlice(ret, i, len, NULL) < 0) + return NULL; + } + return ret; + +Fail_ret_itlist: + Py_DECREF(itlist); +Fail_ret: + Py_DECREF(ret); + return NULL; +} + + +PyDoc_STRVAR(zip_doc, +"zip(seq1 [, seq2 [...]]) -> [(seq1[0], seq2[0] ...), (...)]\n\ +\n\ +Return a list of tuples, where each tuple contains the i-th element\n\ +from each of the argument sequences. The returned list is truncated\n\ +in length to the length of the shortest argument sequence."); + + +static PyMethodDef builtin_methods[] = { + {"__import__", (PyCFunction)builtin___import__, METH_VARARGS | METH_KEYWORDS, import_doc}, + {"abs", builtin_abs, METH_O, abs_doc}, + {"all", builtin_all, METH_O, all_doc}, + {"any", builtin_any, METH_O, any_doc}, + {"apply", builtin_apply, METH_VARARGS, apply_doc}, + {"bin", builtin_bin, METH_O, bin_doc}, + {"callable", builtin_callable, METH_O, callable_doc}, + {"chr", builtin_chr, METH_VARARGS, chr_doc}, + {"cmp", builtin_cmp, METH_VARARGS, cmp_doc}, + {"coerce", builtin_coerce, METH_VARARGS, coerce_doc}, + {"compile", (PyCFunction)builtin_compile, METH_VARARGS | METH_KEYWORDS, compile_doc}, + {"delattr", builtin_delattr, METH_VARARGS, delattr_doc}, + {"dir", builtin_dir, METH_VARARGS, dir_doc}, + {"divmod", builtin_divmod, METH_VARARGS, divmod_doc}, + {"eval", builtin_eval, METH_VARARGS, eval_doc}, + {"execfile", builtin_execfile, METH_VARARGS, execfile_doc}, + {"filter", builtin_filter, METH_VARARGS, filter_doc}, + {"format", builtin_format, METH_VARARGS, format_doc}, + {"getattr", builtin_getattr, METH_VARARGS, getattr_doc}, + {"globals", (PyCFunction)builtin_globals, METH_NOARGS, globals_doc}, + {"hasattr", builtin_hasattr, METH_VARARGS, hasattr_doc}, + {"hash", builtin_hash, METH_O, hash_doc}, + {"hex", builtin_hex, METH_O, hex_doc}, + {"id", builtin_id, METH_O, id_doc}, + {"input", builtin_input, METH_VARARGS, input_doc}, + {"intern", builtin_intern, METH_VARARGS, intern_doc}, + {"isinstance", builtin_isinstance, METH_VARARGS, isinstance_doc}, + {"issubclass", builtin_issubclass, METH_VARARGS, issubclass_doc}, + {"iter", builtin_iter, METH_VARARGS, iter_doc}, + {"len", builtin_len, METH_O, len_doc}, + {"locals", (PyCFunction)builtin_locals, METH_NOARGS, locals_doc}, + {"map", builtin_map, METH_VARARGS, map_doc}, + {"max", (PyCFunction)builtin_max, METH_VARARGS | METH_KEYWORDS, max_doc}, + {"min", (PyCFunction)builtin_min, METH_VARARGS | METH_KEYWORDS, min_doc}, + {"next", builtin_next, METH_VARARGS, next_doc}, + {"oct", builtin_oct, METH_O, oct_doc}, + {"open", (PyCFunction)builtin_open, METH_VARARGS | METH_KEYWORDS, open_doc}, + {"ord", builtin_ord, METH_O, ord_doc}, + {"pow", builtin_pow, METH_VARARGS, pow_doc}, + {"print", (PyCFunction)builtin_print, METH_VARARGS | METH_KEYWORDS, print_doc}, + {"range", builtin_range, METH_VARARGS, range_doc}, + {"raw_input", builtin_raw_input, METH_VARARGS, raw_input_doc}, + {"reduce", builtin_reduce, METH_VARARGS, reduce_doc}, + {"reload", builtin_reload, METH_O, reload_doc}, + {"repr", builtin_repr, METH_O, repr_doc}, + {"round", (PyCFunction)builtin_round, METH_VARARGS | METH_KEYWORDS, round_doc}, + {"setattr", builtin_setattr, METH_VARARGS, setattr_doc}, + {"sorted", (PyCFunction)builtin_sorted, METH_VARARGS | METH_KEYWORDS, sorted_doc}, + {"sum", builtin_sum, METH_VARARGS, sum_doc}, +#ifdef Py_USING_UNICODE + {"unichr", builtin_unichr, METH_VARARGS, unichr_doc}, +#endif + {"vars", builtin_vars, METH_VARARGS, vars_doc}, + {"zip", builtin_zip, METH_VARARGS, zip_doc}, + {NULL, NULL}, +}; + +PyDoc_STRVAR(builtin_doc, +"Built-in functions, exceptions, and other objects.\n\ +\n\ +Noteworthy: None is the `nil' object; Ellipsis represents `...' in slices."); + +PyObject * +_PyBuiltin_Init(void) +{ + PyObject *mod, *dict, *debug; + mod = Py_InitModule4("__builtin__", builtin_methods, + builtin_doc, (PyObject *)NULL, + PYTHON_API_VERSION); + if (mod == NULL) + return NULL; + dict = PyModule_GetDict(mod); + +#ifdef Py_TRACE_REFS + /* __builtin__ exposes a number of statically allocated objects + * that, before this code was added in 2.3, never showed up in + * the list of "all objects" maintained by Py_TRACE_REFS. As a + * result, programs leaking references to None and False (etc) + * couldn't be diagnosed by examining sys.getobjects(0). + */ +#define ADD_TO_ALL(OBJECT) _Py_AddToAllObjects((PyObject *)(OBJECT), 0) +#else +#define ADD_TO_ALL(OBJECT) (void)0 +#endif + +#define SETBUILTIN(NAME, OBJECT) \ + if (PyDict_SetItemString(dict, NAME, (PyObject *)OBJECT) < 0) \ + return NULL; \ + ADD_TO_ALL(OBJECT) + + SETBUILTIN("None", Py_None); + SETBUILTIN("Ellipsis", Py_Ellipsis); + SETBUILTIN("NotImplemented", Py_NotImplemented); + SETBUILTIN("False", Py_False); + SETBUILTIN("True", Py_True); + SETBUILTIN("basestring", &PyBaseString_Type); + SETBUILTIN("bool", &PyBool_Type); + SETBUILTIN("memoryview", &PyMemoryView_Type); + SETBUILTIN("bytearray", &PyByteArray_Type); + SETBUILTIN("bytes", &PyString_Type); + SETBUILTIN("buffer", &PyBuffer_Type); + SETBUILTIN("classmethod", &PyClassMethod_Type); +#ifndef WITHOUT_COMPLEX + SETBUILTIN("complex", &PyComplex_Type); +#endif + SETBUILTIN("dict", &PyDict_Type); + SETBUILTIN("enumerate", &PyEnum_Type); + SETBUILTIN("file", &PyFile_Type); + SETBUILTIN("float", &PyFloat_Type); + SETBUILTIN("frozenset", &PyFrozenSet_Type); + SETBUILTIN("property", &PyProperty_Type); + SETBUILTIN("int", &PyInt_Type); + SETBUILTIN("list", &PyList_Type); + SETBUILTIN("long", &PyLong_Type); + SETBUILTIN("object", &PyBaseObject_Type); + SETBUILTIN("reversed", &PyReversed_Type); + SETBUILTIN("set", &PySet_Type); + SETBUILTIN("slice", &PySlice_Type); + SETBUILTIN("staticmethod", &PyStaticMethod_Type); + SETBUILTIN("str", &PyString_Type); + SETBUILTIN("super", &PySuper_Type); + SETBUILTIN("tuple", &PyTuple_Type); + SETBUILTIN("type", &PyType_Type); + SETBUILTIN("xrange", &PyRange_Type); +#ifdef Py_USING_UNICODE + SETBUILTIN("unicode", &PyUnicode_Type); +#endif + debug = PyBool_FromLong(Py_OptimizeFlag == 0); + if (PyDict_SetItemString(dict, "__debug__", debug) < 0) { + Py_XDECREF(debug); + return NULL; + } + Py_XDECREF(debug); + + return mod; +#undef ADD_TO_ALL +#undef SETBUILTIN +} + +/* Helper for filter(): filter a tuple through a function */ + +static PyObject * +filtertuple(PyObject *func, PyObject *tuple) +{ + PyObject *result; + Py_ssize_t i, j; + Py_ssize_t len = PyTuple_Size(tuple); + + if (len == 0) { + if (PyTuple_CheckExact(tuple)) + Py_INCREF(tuple); + else + tuple = PyTuple_New(0); + return tuple; + } + + if ((result = PyTuple_New(len)) == NULL) + return NULL; + + for (i = j = 0; i < len; ++i) { + PyObject *item, *good; + int ok; + + if (tuple->ob_type->tp_as_sequence && + tuple->ob_type->tp_as_sequence->sq_item) { + item = tuple->ob_type->tp_as_sequence->sq_item(tuple, i); + if (item == NULL) + goto Fail_1; + } else { + PyErr_SetString(PyExc_TypeError, "filter(): unsubscriptable tuple"); + goto Fail_1; + } + if (func == Py_None) { + Py_INCREF(item); + good = item; + } + else { + PyObject *arg = PyTuple_Pack(1, item); + if (arg == NULL) { + Py_DECREF(item); + goto Fail_1; + } + good = PyEval_CallObject(func, arg); + Py_DECREF(arg); + if (good == NULL) { + Py_DECREF(item); + goto Fail_1; + } + } + ok = PyObject_IsTrue(good); + Py_DECREF(good); + if (ok > 0) { + if (PyTuple_SetItem(result, j++, item) < 0) + goto Fail_1; + } + else { + Py_DECREF(item); + if (ok < 0) + goto Fail_1; + } + } + + if (_PyTuple_Resize(&result, j) < 0) + return NULL; + + return result; + +Fail_1: + Py_DECREF(result); + return NULL; +} + + +/* Helper for filter(): filter a string through a function */ + +static PyObject * +filterstring(PyObject *func, PyObject *strobj) +{ + PyObject *result; + Py_ssize_t i, j; + Py_ssize_t len = PyString_Size(strobj); + Py_ssize_t outlen = len; + + if (func == Py_None) { + /* If it's a real string we can return the original, + * as no character is ever false and __getitem__ + * does return this character. If it's a subclass + * we must go through the __getitem__ loop */ + if (PyString_CheckExact(strobj)) { + Py_INCREF(strobj); + return strobj; + } + } + if ((result = PyString_FromStringAndSize(NULL, len)) == NULL) + return NULL; + + for (i = j = 0; i < len; ++i) { + PyObject *item; + int ok; + + item = (*strobj->ob_type->tp_as_sequence->sq_item)(strobj, i); + if (item == NULL) + goto Fail_1; + if (func==Py_None) { + ok = 1; + } else { + PyObject *arg, *good; + arg = PyTuple_Pack(1, item); + if (arg == NULL) { + Py_DECREF(item); + goto Fail_1; + } + good = PyEval_CallObject(func, arg); + Py_DECREF(arg); + if (good == NULL) { + Py_DECREF(item); + goto Fail_1; + } + ok = PyObject_IsTrue(good); + Py_DECREF(good); + } + if (ok > 0) { + Py_ssize_t reslen; + if (!PyString_Check(item)) { + PyErr_SetString(PyExc_TypeError, "can't filter str to str:" + " __getitem__ returned different type"); + Py_DECREF(item); + goto Fail_1; + } + reslen = PyString_GET_SIZE(item); + if (reslen == 1) { + PyString_AS_STRING(result)[j++] = + PyString_AS_STRING(item)[0]; + } else { + /* do we need more space? */ + Py_ssize_t need = j; + + /* calculate space requirements while checking for overflow */ + if (need > PY_SSIZE_T_MAX - reslen) { + Py_DECREF(item); + goto Fail_1; + } + + need += reslen; + + if (need > PY_SSIZE_T_MAX - len) { + Py_DECREF(item); + goto Fail_1; + } + + need += len; + + if (need <= i) { + Py_DECREF(item); + goto Fail_1; + } + + need = need - i - 1; + + assert(need >= 0); + assert(outlen >= 0); + + if (need > outlen) { + /* overallocate, to avoid reallocations */ + if (outlen > PY_SSIZE_T_MAX / 2) { + Py_DECREF(item); + return NULL; + } + + if (need<2*outlen) { + need = 2*outlen; + } + if (_PyString_Resize(&result, need)) { + Py_DECREF(item); + return NULL; + } + outlen = need; + } + memcpy( + PyString_AS_STRING(result) + j, + PyString_AS_STRING(item), + reslen + ); + j += reslen; + } + } + Py_DECREF(item); + if (ok < 0) + goto Fail_1; + } + + if (j < outlen) + _PyString_Resize(&result, j); + + return result; + +Fail_1: + Py_DECREF(result); + return NULL; +} + +#ifdef Py_USING_UNICODE +/* Helper for filter(): filter a Unicode object through a function */ + +static PyObject * +filterunicode(PyObject *func, PyObject *strobj) +{ + PyObject *result; + register Py_ssize_t i, j; + Py_ssize_t len = PyUnicode_GetSize(strobj); + Py_ssize_t outlen = len; + + if (func == Py_None) { + /* If it's a real string we can return the original, + * as no character is ever false and __getitem__ + * does return this character. If it's a subclass + * we must go through the __getitem__ loop */ + if (PyUnicode_CheckExact(strobj)) { + Py_INCREF(strobj); + return strobj; + } + } + if ((result = PyUnicode_FromUnicode(NULL, len)) == NULL) + return NULL; + + for (i = j = 0; i < len; ++i) { + PyObject *item, *arg, *good; + int ok; + + item = (*strobj->ob_type->tp_as_sequence->sq_item)(strobj, i); + if (item == NULL) + goto Fail_1; + if (func == Py_None) { + ok = 1; + } else { + arg = PyTuple_Pack(1, item); + if (arg == NULL) { + Py_DECREF(item); + goto Fail_1; + } + good = PyEval_CallObject(func, arg); + Py_DECREF(arg); + if (good == NULL) { + Py_DECREF(item); + goto Fail_1; + } + ok = PyObject_IsTrue(good); + Py_DECREF(good); + } + if (ok > 0) { + Py_ssize_t reslen; + if (!PyUnicode_Check(item)) { + PyErr_SetString(PyExc_TypeError, + "can't filter unicode to unicode:" + " __getitem__ returned different type"); + Py_DECREF(item); + goto Fail_1; + } + reslen = PyUnicode_GET_SIZE(item); + if (reslen == 1) + PyUnicode_AS_UNICODE(result)[j++] = + PyUnicode_AS_UNICODE(item)[0]; + else { + /* do we need more space? */ + Py_ssize_t need = j + reslen + len - i - 1; + + /* check that didnt overflow */ + if ((j > PY_SSIZE_T_MAX - reslen) || + ((j + reslen) > PY_SSIZE_T_MAX - len) || + ((j + reslen + len) < i) || + ((j + reslen + len - i) <= 0)) { + Py_DECREF(item); + return NULL; + } + + assert(need >= 0); + assert(outlen >= 0); + + if (need > outlen) { + /* overallocate, + to avoid reallocations */ + if (need < 2 * outlen) { + if (outlen > PY_SSIZE_T_MAX / 2) { + Py_DECREF(item); + return NULL; + } else { + need = 2 * outlen; + } + } + + if (PyUnicode_Resize( + &result, need) < 0) { + Py_DECREF(item); + goto Fail_1; + } + outlen = need; + } + memcpy(PyUnicode_AS_UNICODE(result) + j, + PyUnicode_AS_UNICODE(item), + reslen*sizeof(Py_UNICODE)); + j += reslen; + } + } + Py_DECREF(item); + if (ok < 0) + goto Fail_1; + } + + if (j < outlen) + PyUnicode_Resize(&result, j); + + return result; + +Fail_1: + Py_DECREF(result); + return NULL; +} +#endif diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/ceval.c b/AppPkg/Applications/Python/Python-2.7.10/Python/ceval.c new file mode 100644 index 0000000000..7e1237436a --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/ceval.c @@ -0,0 +1,4917 @@ + +/* Execute compiled code */ + +/* XXX TO DO: + XXX speed up searching for keywords by using a dictionary + XXX document it! + */ + +/* enable more aggressive intra-module optimizations, where available */ +#define PY_LOCAL_AGGRESSIVE + +#include "Python.h" + +#include "code.h" +#include "frameobject.h" +#include "eval.h" +#include "opcode.h" +#include "structmember.h" + +#include + +#ifndef WITH_TSC + +#define READ_TIMESTAMP(var) + +#else + +typedef unsigned long long uint64; + +/* PowerPC support. + "__ppc__" appears to be the preprocessor definition to detect on OS X, whereas + "__powerpc__" appears to be the correct one for Linux with GCC +*/ +#if defined(__ppc__) || defined (__powerpc__) + +#define READ_TIMESTAMP(var) ppc_getcounter(&var) + +static void +ppc_getcounter(uint64 *v) +{ + register unsigned long tbu, tb, tbu2; + + loop: + asm volatile ("mftbu %0" : "=r" (tbu) ); + asm volatile ("mftb %0" : "=r" (tb) ); + asm volatile ("mftbu %0" : "=r" (tbu2)); + if (__builtin_expect(tbu != tbu2, 0)) goto loop; + + /* The slightly peculiar way of writing the next lines is + compiled better by GCC than any other way I tried. */ + ((long*)(v))[0] = tbu; + ((long*)(v))[1] = tb; +} + +#elif defined(__i386__) + +/* this is for linux/x86 (and probably any other GCC/x86 combo) */ + +#define READ_TIMESTAMP(val) \ + __asm__ __volatile__("rdtsc" : "=A" (val)) + +#elif defined(__x86_64__) + +/* for gcc/x86_64, the "A" constraint in DI mode means *either* rax *or* rdx; + not edx:eax as it does for i386. Since rdtsc puts its result in edx:eax + even in 64-bit mode, we need to use "a" and "d" for the lower and upper + 32-bit pieces of the result. */ + +#define READ_TIMESTAMP(val) do { \ + unsigned int h, l; \ + __asm__ __volatile__("rdtsc" : "=a" (l), "=d" (h)); \ + (val) = ((uint64)l) | (((uint64)h) << 32); \ + } while(0) + + +#else + +#error "Don't know how to implement timestamp counter for this architecture" + +#endif + +void dump_tsc(int opcode, int ticked, uint64 inst0, uint64 inst1, + uint64 loop0, uint64 loop1, uint64 intr0, uint64 intr1) +{ + uint64 intr, inst, loop; + PyThreadState *tstate = PyThreadState_Get(); + if (!tstate->interp->tscdump) + return; + intr = intr1 - intr0; + inst = inst1 - inst0 - intr; + loop = loop1 - loop0 - intr; + fprintf(stderr, "opcode=%03d t=%d inst=%06lld loop=%06lld\n", + opcode, ticked, inst, loop); +} + +#endif + +/* Turn this on if your compiler chokes on the big switch: */ +/* #define CASE_TOO_BIG 1 */ + +#ifdef Py_DEBUG +/* For debugging the interpreter: */ +#define LLTRACE 1 /* Low-level trace feature */ +#define CHECKEXC 1 /* Double-check exception checking */ +#endif + +typedef PyObject *(*callproc)(PyObject *, PyObject *, PyObject *); + +/* Forward declarations */ +#ifdef WITH_TSC +static PyObject * call_function(PyObject ***, int, uint64*, uint64*); +#else +static PyObject * call_function(PyObject ***, int); +#endif +static PyObject * fast_function(PyObject *, PyObject ***, int, int, int); +static PyObject * do_call(PyObject *, PyObject ***, int, int); +static PyObject * ext_do_call(PyObject *, PyObject ***, int, int, int); +static PyObject * update_keyword_args(PyObject *, int, PyObject ***, + PyObject *); +static PyObject * update_star_args(int, int, PyObject *, PyObject ***); +static PyObject * load_args(PyObject ***, int); +#define CALL_FLAG_VAR 1 +#define CALL_FLAG_KW 2 + +#ifdef LLTRACE +static int lltrace; +static int prtrace(PyObject *, char *); +#endif +static int call_trace(Py_tracefunc, PyObject *, PyFrameObject *, + int, PyObject *); +static int call_trace_protected(Py_tracefunc, PyObject *, + PyFrameObject *, int, PyObject *); +static void call_exc_trace(Py_tracefunc, PyObject *, PyFrameObject *); +static int maybe_call_line_trace(Py_tracefunc, PyObject *, + PyFrameObject *, int *, int *, int *); + +static PyObject * apply_slice(PyObject *, PyObject *, PyObject *); +static int assign_slice(PyObject *, PyObject *, + PyObject *, PyObject *); +static PyObject * cmp_outcome(int, PyObject *, PyObject *); +static PyObject * import_from(PyObject *, PyObject *); +static int import_all_from(PyObject *, PyObject *); +static PyObject * build_class(PyObject *, PyObject *, PyObject *); +static int exec_statement(PyFrameObject *, + PyObject *, PyObject *, PyObject *); +static void set_exc_info(PyThreadState *, PyObject *, PyObject *, PyObject *); +static void reset_exc_info(PyThreadState *); +static void format_exc_check_arg(PyObject *, char *, PyObject *); +static PyObject * string_concatenate(PyObject *, PyObject *, + PyFrameObject *, unsigned char *); +static PyObject * kwd_as_string(PyObject *); +static PyObject * special_lookup(PyObject *, char *, PyObject **); + +#define NAME_ERROR_MSG \ + "name '%.200s' is not defined" +#define GLOBAL_NAME_ERROR_MSG \ + "global name '%.200s' is not defined" +#define UNBOUNDLOCAL_ERROR_MSG \ + "local variable '%.200s' referenced before assignment" +#define UNBOUNDFREE_ERROR_MSG \ + "free variable '%.200s' referenced before assignment" \ + " in enclosing scope" + +/* Dynamic execution profile */ +#ifdef DYNAMIC_EXECUTION_PROFILE +#ifdef DXPAIRS +static long dxpairs[257][256]; +#define dxp dxpairs[256] +#else +static long dxp[256]; +#endif +#endif + +/* Function call profile */ +#ifdef CALL_PROFILE +#define PCALL_NUM 11 +static int pcall[PCALL_NUM]; + +#define PCALL_ALL 0 +#define PCALL_FUNCTION 1 +#define PCALL_FAST_FUNCTION 2 +#define PCALL_FASTER_FUNCTION 3 +#define PCALL_METHOD 4 +#define PCALL_BOUND_METHOD 5 +#define PCALL_CFUNCTION 6 +#define PCALL_TYPE 7 +#define PCALL_GENERATOR 8 +#define PCALL_OTHER 9 +#define PCALL_POP 10 + +/* Notes about the statistics + + PCALL_FAST stats + + FAST_FUNCTION means no argument tuple needs to be created. + FASTER_FUNCTION means that the fast-path frame setup code is used. + + If there is a method call where the call can be optimized by changing + the argument tuple and calling the function directly, it gets recorded + twice. + + As a result, the relationship among the statistics appears to be + PCALL_ALL == PCALL_FUNCTION + PCALL_METHOD - PCALL_BOUND_METHOD + + PCALL_CFUNCTION + PCALL_TYPE + PCALL_GENERATOR + PCALL_OTHER + PCALL_FUNCTION > PCALL_FAST_FUNCTION > PCALL_FASTER_FUNCTION + PCALL_METHOD > PCALL_BOUND_METHOD +*/ + +#define PCALL(POS) pcall[POS]++ + +PyObject * +PyEval_GetCallStats(PyObject *self) +{ + return Py_BuildValue("iiiiiiiiiii", + pcall[0], pcall[1], pcall[2], pcall[3], + pcall[4], pcall[5], pcall[6], pcall[7], + pcall[8], pcall[9], pcall[10]); +} +#else +#define PCALL(O) + +PyObject * +PyEval_GetCallStats(PyObject *self) +{ + Py_INCREF(Py_None); + return Py_None; +} +#endif + + +#ifdef WITH_THREAD + +#ifdef HAVE_ERRNO_H +#include +#endif +#include "pythread.h" + +static PyThread_type_lock interpreter_lock = 0; /* This is the GIL */ +static PyThread_type_lock pending_lock = 0; /* for pending calls */ +static long main_thread = 0; + +int +PyEval_ThreadsInitialized(void) +{ + return interpreter_lock != 0; +} + +void +PyEval_InitThreads(void) +{ + if (interpreter_lock) + return; + interpreter_lock = PyThread_allocate_lock(); + PyThread_acquire_lock(interpreter_lock, 1); + main_thread = PyThread_get_thread_ident(); +} + +void +PyEval_AcquireLock(void) +{ + PyThread_acquire_lock(interpreter_lock, 1); +} + +void +PyEval_ReleaseLock(void) +{ + PyThread_release_lock(interpreter_lock); +} + +void +PyEval_AcquireThread(PyThreadState *tstate) +{ + if (tstate == NULL) + Py_FatalError("PyEval_AcquireThread: NULL new thread state"); + /* Check someone has called PyEval_InitThreads() to create the lock */ + assert(interpreter_lock); + PyThread_acquire_lock(interpreter_lock, 1); + if (PyThreadState_Swap(tstate) != NULL) + Py_FatalError( + "PyEval_AcquireThread: non-NULL old thread state"); +} + +void +PyEval_ReleaseThread(PyThreadState *tstate) +{ + if (tstate == NULL) + Py_FatalError("PyEval_ReleaseThread: NULL thread state"); + if (PyThreadState_Swap(NULL) != tstate) + Py_FatalError("PyEval_ReleaseThread: wrong thread state"); + PyThread_release_lock(interpreter_lock); +} + +/* This function is called from PyOS_AfterFork to ensure that newly + created child processes don't hold locks referring to threads which + are not running in the child process. (This could also be done using + pthread_atfork mechanism, at least for the pthreads implementation.) */ + +void +PyEval_ReInitThreads(void) +{ + PyObject *threading, *result; + PyThreadState *tstate; + + if (!interpreter_lock) + return; + /*XXX Can't use PyThread_free_lock here because it does too + much error-checking. Doing this cleanly would require + adding a new function to each thread_*.h. Instead, just + create a new lock and waste a little bit of memory */ + interpreter_lock = PyThread_allocate_lock(); + pending_lock = PyThread_allocate_lock(); + PyThread_acquire_lock(interpreter_lock, 1); + main_thread = PyThread_get_thread_ident(); + + /* Update the threading module with the new state. + */ + tstate = PyThreadState_GET(); + threading = PyMapping_GetItemString(tstate->interp->modules, + "threading"); + if (threading == NULL) { + /* threading not imported */ + PyErr_Clear(); + return; + } + result = PyObject_CallMethod(threading, "_after_fork", NULL); + if (result == NULL) + PyErr_WriteUnraisable(threading); + else + Py_DECREF(result); + Py_DECREF(threading); +} +#endif + +/* Functions save_thread and restore_thread are always defined so + dynamically loaded modules needn't be compiled separately for use + with and without threads: */ + +PyThreadState * +PyEval_SaveThread(void) +{ + PyThreadState *tstate = PyThreadState_Swap(NULL); + if (tstate == NULL) + Py_FatalError("PyEval_SaveThread: NULL tstate"); +#ifdef WITH_THREAD + if (interpreter_lock) + PyThread_release_lock(interpreter_lock); +#endif + return tstate; +} + +void +PyEval_RestoreThread(PyThreadState *tstate) +{ + if (tstate == NULL) + Py_FatalError("PyEval_RestoreThread: NULL tstate"); +#ifdef WITH_THREAD + if (interpreter_lock) { + int err = errno; + PyThread_acquire_lock(interpreter_lock, 1); + errno = err; + } +#endif + PyThreadState_Swap(tstate); +} + + +/* Mechanism whereby asynchronously executing callbacks (e.g. UNIX + signal handlers or Mac I/O completion routines) can schedule calls + to a function to be called synchronously. + The synchronous function is called with one void* argument. + It should return 0 for success or -1 for failure -- failure should + be accompanied by an exception. + + If registry succeeds, the registry function returns 0; if it fails + (e.g. due to too many pending calls) it returns -1 (without setting + an exception condition). + + Note that because registry may occur from within signal handlers, + or other asynchronous events, calling malloc() is unsafe! + +#ifdef WITH_THREAD + Any thread can schedule pending calls, but only the main thread + will execute them. + There is no facility to schedule calls to a particular thread, but + that should be easy to change, should that ever be required. In + that case, the static variables here should go into the python + threadstate. +#endif +*/ + +#ifdef WITH_THREAD + +/* The WITH_THREAD implementation is thread-safe. It allows + scheduling to be made from any thread, and even from an executing + callback. + */ + +#define NPENDINGCALLS 32 +static struct { + int (*func)(void *); + void *arg; +} pendingcalls[NPENDINGCALLS]; +static int pendingfirst = 0; +static int pendinglast = 0; +static volatile int pendingcalls_to_do = 1; /* trigger initialization of lock */ +static char pendingbusy = 0; + +int +Py_AddPendingCall(int (*func)(void *), void *arg) +{ + int i, j, result=0; + PyThread_type_lock lock = pending_lock; + + /* try a few times for the lock. Since this mechanism is used + * for signal handling (on the main thread), there is a (slim) + * chance that a signal is delivered on the same thread while we + * hold the lock during the Py_MakePendingCalls() function. + * This avoids a deadlock in that case. + * Note that signals can be delivered on any thread. In particular, + * on Windows, a SIGINT is delivered on a system-created worker + * thread. + * We also check for lock being NULL, in the unlikely case that + * this function is called before any bytecode evaluation takes place. + */ + if (lock != NULL) { + for (i = 0; i<100; i++) { + if (PyThread_acquire_lock(lock, NOWAIT_LOCK)) + break; + } + if (i == 100) + return -1; + } + + i = pendinglast; + j = (i + 1) % NPENDINGCALLS; + if (j == pendingfirst) { + result = -1; /* Queue full */ + } else { + pendingcalls[i].func = func; + pendingcalls[i].arg = arg; + pendinglast = j; + } + /* signal main loop */ + _Py_Ticker = 0; + pendingcalls_to_do = 1; + if (lock != NULL) + PyThread_release_lock(lock); + return result; +} + +int +Py_MakePendingCalls(void) +{ + int i; + int r = 0; + + if (!pending_lock) { + /* initial allocation of the lock */ + pending_lock = PyThread_allocate_lock(); + if (pending_lock == NULL) + return -1; + } + + /* only service pending calls on main thread */ + if (main_thread && PyThread_get_thread_ident() != main_thread) + return 0; + /* don't perform recursive pending calls */ + if (pendingbusy) + return 0; + pendingbusy = 1; + /* perform a bounded number of calls, in case of recursion */ + for (i=0; irecursion_depth; + PyErr_SetString(PyExc_MemoryError, "Stack overflow"); + return -1; + } +#endif + if (tstate->recursion_depth > recursion_limit) { + --tstate->recursion_depth; + PyErr_Format(PyExc_RuntimeError, + "maximum recursion depth exceeded%s", + where); + return -1; + } + _Py_CheckRecursionLimit = recursion_limit; + return 0; +} + +/* Status code for main loop (reason for stack unwind) */ +enum why_code { + WHY_NOT = 0x0001, /* No error */ + WHY_EXCEPTION = 0x0002, /* Exception occurred */ + WHY_RERAISE = 0x0004, /* Exception re-raised by 'finally' */ + WHY_RETURN = 0x0008, /* 'return' statement */ + WHY_BREAK = 0x0010, /* 'break' statement */ + WHY_CONTINUE = 0x0020, /* 'continue' statement */ + WHY_YIELD = 0x0040 /* 'yield' operator */ +}; + +static enum why_code do_raise(PyObject *, PyObject *, PyObject *); +static int unpack_iterable(PyObject *, int, PyObject **); + +/* Records whether tracing is on for any thread. Counts the number of + threads for which tstate->c_tracefunc is non-NULL, so if the value + is 0, we know we don't have to check this thread's c_tracefunc. + This speeds up the if statement in PyEval_EvalFrameEx() after + fast_next_opcode*/ +static int _Py_TracingPossible = 0; + +/* for manipulating the thread switch and periodic "stuff" - used to be + per thread, now just a pair o' globals */ +int _Py_CheckInterval = 100; +volatile int _Py_Ticker = 0; /* so that we hit a "tick" first thing */ + +PyObject * +PyEval_EvalCode(PyCodeObject *co, PyObject *globals, PyObject *locals) +{ + return PyEval_EvalCodeEx(co, + globals, locals, + (PyObject **)NULL, 0, + (PyObject **)NULL, 0, + (PyObject **)NULL, 0, + NULL); +} + + +/* Interpreter main loop */ + +PyObject * +PyEval_EvalFrame(PyFrameObject *f) { + /* This is for backward compatibility with extension modules that + used this API; core interpreter code should call + PyEval_EvalFrameEx() */ + return PyEval_EvalFrameEx(f, 0); +} + +PyObject * +PyEval_EvalFrameEx(PyFrameObject *f, int throwflag) +{ +#ifdef DXPAIRS + int lastopcode = 0; +#endif + register PyObject **stack_pointer; /* Next free slot in value stack */ + register unsigned char *next_instr; + register int opcode; /* Current opcode */ + register int oparg; /* Current opcode argument, if any */ + register enum why_code why; /* Reason for block stack unwind */ + register int err; /* Error status -- nonzero if error */ + register PyObject *x; /* Result object -- NULL if error */ + register PyObject *v; /* Temporary objects popped off stack */ + register PyObject *w; + register PyObject *u; + register PyObject *t; + register PyObject *stream = NULL; /* for PRINT opcodes */ + register PyObject **fastlocals, **freevars; + PyObject *retval = NULL; /* Return value */ + PyThreadState *tstate = PyThreadState_GET(); + PyCodeObject *co; + + /* when tracing we set things up so that + + not (instr_lb <= current_bytecode_offset < instr_ub) + + is true when the line being executed has changed. The + initial values are such as to make this false the first + time it is tested. */ + int instr_ub = -1, instr_lb = 0, instr_prev = -1; + + unsigned char *first_instr; + PyObject *names; + PyObject *consts; +#if defined(Py_DEBUG) || defined(LLTRACE) + /* Make it easier to find out where we are with a debugger */ + char *filename; +#endif + +/* Tuple access macros */ + +#ifndef Py_DEBUG +#define GETITEM(v, i) PyTuple_GET_ITEM((PyTupleObject *)(v), (i)) +#else +#define GETITEM(v, i) PyTuple_GetItem((v), (i)) +#endif + +#ifdef WITH_TSC +/* Use Pentium timestamp counter to mark certain events: + inst0 -- beginning of switch statement for opcode dispatch + inst1 -- end of switch statement (may be skipped) + loop0 -- the top of the mainloop + loop1 -- place where control returns again to top of mainloop + (may be skipped) + intr1 -- beginning of long interruption + intr2 -- end of long interruption + + Many opcodes call out to helper C functions. In some cases, the + time in those functions should be counted towards the time for the + opcode, but not in all cases. For example, a CALL_FUNCTION opcode + calls another Python function; there's no point in charge all the + bytecode executed by the called function to the caller. + + It's hard to make a useful judgement statically. In the presence + of operator overloading, it's impossible to tell if a call will + execute new Python code or not. + + It's a case-by-case judgement. I'll use intr1 for the following + cases: + + EXEC_STMT + IMPORT_STAR + IMPORT_FROM + CALL_FUNCTION (and friends) + + */ + uint64 inst0, inst1, loop0, loop1, intr0 = 0, intr1 = 0; + int ticked = 0; + + READ_TIMESTAMP(inst0); + READ_TIMESTAMP(inst1); + READ_TIMESTAMP(loop0); + READ_TIMESTAMP(loop1); + + /* shut up the compiler */ + opcode = 0; +#endif + +/* Code access macros */ + +#define INSTR_OFFSET() ((int)(next_instr - first_instr)) +#define NEXTOP() (*next_instr++) +#define NEXTARG() (next_instr += 2, (next_instr[-1]<<8) + next_instr[-2]) +#define PEEKARG() ((next_instr[2]<<8) + next_instr[1]) +#define JUMPTO(x) (next_instr = first_instr + (x)) +#define JUMPBY(x) (next_instr += (x)) + +/* OpCode prediction macros + Some opcodes tend to come in pairs thus making it possible to + predict the second code when the first is run. For example, + GET_ITER is often followed by FOR_ITER. And FOR_ITER is often + followed by STORE_FAST or UNPACK_SEQUENCE. + + Verifying the prediction costs a single high-speed test of a register + variable against a constant. If the pairing was good, then the + processor's own internal branch predication has a high likelihood of + success, resulting in a nearly zero-overhead transition to the + next opcode. A successful prediction saves a trip through the eval-loop + including its two unpredictable branches, the HAS_ARG test and the + switch-case. Combined with the processor's internal branch prediction, + a successful PREDICT has the effect of making the two opcodes run as if + they were a single new opcode with the bodies combined. + + If collecting opcode statistics, your choices are to either keep the + predictions turned-on and interpret the results as if some opcodes + had been combined or turn-off predictions so that the opcode frequency + counter updates for both opcodes. +*/ + +#ifdef DYNAMIC_EXECUTION_PROFILE +#define PREDICT(op) if (0) goto PRED_##op +#else +#define PREDICT(op) if (*next_instr == op) goto PRED_##op +#endif + +#define PREDICTED(op) PRED_##op: next_instr++ +#define PREDICTED_WITH_ARG(op) PRED_##op: oparg = PEEKARG(); next_instr += 3 + +/* Stack manipulation macros */ + +/* The stack can grow at most MAXINT deep, as co_nlocals and + co_stacksize are ints. */ +#define STACK_LEVEL() ((int)(stack_pointer - f->f_valuestack)) +#define EMPTY() (STACK_LEVEL() == 0) +#define TOP() (stack_pointer[-1]) +#define SECOND() (stack_pointer[-2]) +#define THIRD() (stack_pointer[-3]) +#define FOURTH() (stack_pointer[-4]) +#define PEEK(n) (stack_pointer[-(n)]) +#define SET_TOP(v) (stack_pointer[-1] = (v)) +#define SET_SECOND(v) (stack_pointer[-2] = (v)) +#define SET_THIRD(v) (stack_pointer[-3] = (v)) +#define SET_FOURTH(v) (stack_pointer[-4] = (v)) +#define SET_VALUE(n, v) (stack_pointer[-(n)] = (v)) +#define BASIC_STACKADJ(n) (stack_pointer += n) +#define BASIC_PUSH(v) (*stack_pointer++ = (v)) +#define BASIC_POP() (*--stack_pointer) + +#ifdef LLTRACE +#define PUSH(v) { (void)(BASIC_PUSH(v), \ + lltrace && prtrace(TOP(), "push")); \ + assert(STACK_LEVEL() <= co->co_stacksize); } +#define POP() ((void)(lltrace && prtrace(TOP(), "pop")), \ + BASIC_POP()) +#define STACKADJ(n) { (void)(BASIC_STACKADJ(n), \ + lltrace && prtrace(TOP(), "stackadj")); \ + assert(STACK_LEVEL() <= co->co_stacksize); } +#define EXT_POP(STACK_POINTER) ((void)(lltrace && \ + prtrace((STACK_POINTER)[-1], "ext_pop")), \ + *--(STACK_POINTER)) +#else +#define PUSH(v) BASIC_PUSH(v) +#define POP() BASIC_POP() +#define STACKADJ(n) BASIC_STACKADJ(n) +#define EXT_POP(STACK_POINTER) (*--(STACK_POINTER)) +#endif + +/* Local variable macros */ + +#define GETLOCAL(i) (fastlocals[i]) + +/* The SETLOCAL() macro must not DECREF the local variable in-place and + then store the new value; it must copy the old value to a temporary + value, then store the new value, and then DECREF the temporary value. + This is because it is possible that during the DECREF the frame is + accessed by other code (e.g. a __del__ method or gc.collect()) and the + variable would be pointing to already-freed memory. */ +#define SETLOCAL(i, value) do { PyObject *tmp = GETLOCAL(i); \ + GETLOCAL(i) = value; \ + Py_XDECREF(tmp); } while (0) + +/* Start of code */ + + if (f == NULL) + return NULL; + + /* push frame */ + if (Py_EnterRecursiveCall("")) + return NULL; + + tstate->frame = f; + + if (tstate->use_tracing) { + if (tstate->c_tracefunc != NULL) { + /* tstate->c_tracefunc, if defined, is a + function that will be called on *every* entry + to a code block. Its return value, if not + None, is a function that will be called at + the start of each executed line of code. + (Actually, the function must return itself + in order to continue tracing.) The trace + functions are called with three arguments: + a pointer to the current frame, a string + indicating why the function is called, and + an argument which depends on the situation. + The global trace function is also called + whenever an exception is detected. */ + if (call_trace_protected(tstate->c_tracefunc, + tstate->c_traceobj, + f, PyTrace_CALL, Py_None)) { + /* Trace function raised an error */ + goto exit_eval_frame; + } + } + if (tstate->c_profilefunc != NULL) { + /* Similar for c_profilefunc, except it needn't + return itself and isn't called for "line" events */ + if (call_trace_protected(tstate->c_profilefunc, + tstate->c_profileobj, + f, PyTrace_CALL, Py_None)) { + /* Profile function raised an error */ + goto exit_eval_frame; + } + } + } + + co = f->f_code; + names = co->co_names; + consts = co->co_consts; + fastlocals = f->f_localsplus; + freevars = f->f_localsplus + co->co_nlocals; + first_instr = (unsigned char*) PyString_AS_STRING(co->co_code); + /* An explanation is in order for the next line. + + f->f_lasti now refers to the index of the last instruction + executed. You might think this was obvious from the name, but + this wasn't always true before 2.3! PyFrame_New now sets + f->f_lasti to -1 (i.e. the index *before* the first instruction) + and YIELD_VALUE doesn't fiddle with f_lasti any more. So this + does work. Promise. + + When the PREDICT() macros are enabled, some opcode pairs follow in + direct succession without updating f->f_lasti. A successful + prediction effectively links the two codes together as if they + were a single new opcode; accordingly,f->f_lasti will point to + the first code in the pair (for instance, GET_ITER followed by + FOR_ITER is effectively a single opcode and f->f_lasti will point + at to the beginning of the combined pair.) + */ + next_instr = first_instr + f->f_lasti + 1; + stack_pointer = f->f_stacktop; + assert(stack_pointer != NULL); + f->f_stacktop = NULL; /* remains NULL unless yield suspends frame */ + +#ifdef LLTRACE + lltrace = PyDict_GetItemString(f->f_globals, "__lltrace__") != NULL; +#endif +#if defined(Py_DEBUG) || defined(LLTRACE) + filename = PyString_AsString(co->co_filename); +#endif + + why = WHY_NOT; + err = 0; + x = Py_None; /* Not a reference, just anything non-NULL */ + w = NULL; + + if (throwflag) { /* support for generator.throw() */ + why = WHY_EXCEPTION; + goto on_error; + } + + for (;;) { +#ifdef WITH_TSC + if (inst1 == 0) { + /* Almost surely, the opcode executed a break + or a continue, preventing inst1 from being set + on the way out of the loop. + */ + READ_TIMESTAMP(inst1); + loop1 = inst1; + } + dump_tsc(opcode, ticked, inst0, inst1, loop0, loop1, + intr0, intr1); + ticked = 0; + inst1 = 0; + intr0 = 0; + intr1 = 0; + READ_TIMESTAMP(loop0); +#endif + assert(stack_pointer >= f->f_valuestack); /* else underflow */ + assert(STACK_LEVEL() <= co->co_stacksize); /* else overflow */ + + /* Do periodic things. Doing this every time through + the loop would add too much overhead, so we do it + only every Nth instruction. We also do it if + ``pendingcalls_to_do'' is set, i.e. when an asynchronous + event needs attention (e.g. a signal handler or + async I/O handler); see Py_AddPendingCall() and + Py_MakePendingCalls() above. */ + + if (--_Py_Ticker < 0) { + if (*next_instr == SETUP_FINALLY) { + /* Make the last opcode before + a try: finally: block uninterruptible. */ + goto fast_next_opcode; + } + _Py_Ticker = _Py_CheckInterval; + tstate->tick_counter++; +#ifdef WITH_TSC + ticked = 1; +#endif + if (pendingcalls_to_do) { + if (Py_MakePendingCalls() < 0) { + why = WHY_EXCEPTION; + goto on_error; + } + if (pendingcalls_to_do) + /* MakePendingCalls() didn't succeed. + Force early re-execution of this + "periodic" code, possibly after + a thread switch */ + _Py_Ticker = 0; + } +#ifdef WITH_THREAD + if (interpreter_lock) { + /* Give another thread a chance */ + + if (PyThreadState_Swap(NULL) != tstate) + Py_FatalError("ceval: tstate mix-up"); + PyThread_release_lock(interpreter_lock); + + /* Other threads may run now */ + + PyThread_acquire_lock(interpreter_lock, 1); + + if (PyThreadState_Swap(tstate) != NULL) + Py_FatalError("ceval: orphan tstate"); + + /* Check for thread interrupts */ + + if (tstate->async_exc != NULL) { + x = tstate->async_exc; + tstate->async_exc = NULL; + PyErr_SetNone(x); + Py_DECREF(x); + why = WHY_EXCEPTION; + goto on_error; + } + } +#endif + } + + fast_next_opcode: + f->f_lasti = INSTR_OFFSET(); + + /* line-by-line tracing support */ + + if (_Py_TracingPossible && + tstate->c_tracefunc != NULL && !tstate->tracing) { + /* see maybe_call_line_trace + for expository comments */ + f->f_stacktop = stack_pointer; + + err = maybe_call_line_trace(tstate->c_tracefunc, + tstate->c_traceobj, + f, &instr_lb, &instr_ub, + &instr_prev); + /* Reload possibly changed frame fields */ + JUMPTO(f->f_lasti); + if (f->f_stacktop != NULL) { + stack_pointer = f->f_stacktop; + f->f_stacktop = NULL; + } + if (err) { + /* trace function raised an exception */ + goto on_error; + } + } + + /* Extract opcode and argument */ + + opcode = NEXTOP(); + oparg = 0; /* allows oparg to be stored in a register because + it doesn't have to be remembered across a full loop */ + if (HAS_ARG(opcode)) + oparg = NEXTARG(); + dispatch_opcode: +#ifdef DYNAMIC_EXECUTION_PROFILE +#ifdef DXPAIRS + dxpairs[lastopcode][opcode]++; + lastopcode = opcode; +#endif + dxp[opcode]++; +#endif + +#ifdef LLTRACE + /* Instruction tracing */ + + if (lltrace) { + if (HAS_ARG(opcode)) { + printf("%d: %d, %d\n", + f->f_lasti, opcode, oparg); + } + else { + printf("%d: %d\n", + f->f_lasti, opcode); + } + } +#endif + + /* Main switch on opcode */ + READ_TIMESTAMP(inst0); + + switch (opcode) { + + /* BEWARE! + It is essential that any operation that fails sets either + x to NULL, err to nonzero, or why to anything but WHY_NOT, + and that no operation that succeeds does this! */ + + /* case STOP_CODE: this is an error! */ + + case NOP: + goto fast_next_opcode; + + case LOAD_FAST: + x = GETLOCAL(oparg); + if (x != NULL) { + Py_INCREF(x); + PUSH(x); + goto fast_next_opcode; + } + format_exc_check_arg(PyExc_UnboundLocalError, + UNBOUNDLOCAL_ERROR_MSG, + PyTuple_GetItem(co->co_varnames, oparg)); + break; + + case LOAD_CONST: + x = GETITEM(consts, oparg); + Py_INCREF(x); + PUSH(x); + goto fast_next_opcode; + + PREDICTED_WITH_ARG(STORE_FAST); + case STORE_FAST: + v = POP(); + SETLOCAL(oparg, v); + goto fast_next_opcode; + + case POP_TOP: + v = POP(); + Py_DECREF(v); + goto fast_next_opcode; + + case ROT_TWO: + v = TOP(); + w = SECOND(); + SET_TOP(w); + SET_SECOND(v); + goto fast_next_opcode; + + case ROT_THREE: + v = TOP(); + w = SECOND(); + x = THIRD(); + SET_TOP(w); + SET_SECOND(x); + SET_THIRD(v); + goto fast_next_opcode; + + case ROT_FOUR: + u = TOP(); + v = SECOND(); + w = THIRD(); + x = FOURTH(); + SET_TOP(v); + SET_SECOND(w); + SET_THIRD(x); + SET_FOURTH(u); + goto fast_next_opcode; + + case DUP_TOP: + v = TOP(); + Py_INCREF(v); + PUSH(v); + goto fast_next_opcode; + + case DUP_TOPX: + if (oparg == 2) { + x = TOP(); + Py_INCREF(x); + w = SECOND(); + Py_INCREF(w); + STACKADJ(2); + SET_TOP(x); + SET_SECOND(w); + goto fast_next_opcode; + } else if (oparg == 3) { + x = TOP(); + Py_INCREF(x); + w = SECOND(); + Py_INCREF(w); + v = THIRD(); + Py_INCREF(v); + STACKADJ(3); + SET_TOP(x); + SET_SECOND(w); + SET_THIRD(v); + goto fast_next_opcode; + } + Py_FatalError("invalid argument to DUP_TOPX" + " (bytecode corruption?)"); + /* Never returns, so don't bother to set why. */ + break; + + case UNARY_POSITIVE: + v = TOP(); + x = PyNumber_Positive(v); + Py_DECREF(v); + SET_TOP(x); + if (x != NULL) continue; + break; + + case UNARY_NEGATIVE: + v = TOP(); + x = PyNumber_Negative(v); + Py_DECREF(v); + SET_TOP(x); + if (x != NULL) continue; + break; + + case UNARY_NOT: + v = TOP(); + err = PyObject_IsTrue(v); + Py_DECREF(v); + if (err == 0) { + Py_INCREF(Py_True); + SET_TOP(Py_True); + continue; + } + else if (err > 0) { + Py_INCREF(Py_False); + SET_TOP(Py_False); + err = 0; + continue; + } + STACKADJ(-1); + break; + + case UNARY_CONVERT: + v = TOP(); + x = PyObject_Repr(v); + Py_DECREF(v); + SET_TOP(x); + if (x != NULL) continue; + break; + + case UNARY_INVERT: + v = TOP(); + x = PyNumber_Invert(v); + Py_DECREF(v); + SET_TOP(x); + if (x != NULL) continue; + break; + + case BINARY_POWER: + w = POP(); + v = TOP(); + x = PyNumber_Power(v, w, Py_None); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case BINARY_MULTIPLY: + w = POP(); + v = TOP(); + x = PyNumber_Multiply(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case BINARY_DIVIDE: + if (!_Py_QnewFlag) { + w = POP(); + v = TOP(); + x = PyNumber_Divide(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + } + /* -Qnew is in effect: fall through to + BINARY_TRUE_DIVIDE */ + case BINARY_TRUE_DIVIDE: + w = POP(); + v = TOP(); + x = PyNumber_TrueDivide(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case BINARY_FLOOR_DIVIDE: + w = POP(); + v = TOP(); + x = PyNumber_FloorDivide(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case BINARY_MODULO: + w = POP(); + v = TOP(); + if (PyString_CheckExact(v)) + x = PyString_Format(v, w); + else + x = PyNumber_Remainder(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case BINARY_ADD: + w = POP(); + v = TOP(); + if (PyInt_CheckExact(v) && PyInt_CheckExact(w)) { + /* INLINE: int + int */ + register long a, b, i; + a = PyInt_AS_LONG(v); + b = PyInt_AS_LONG(w); + /* cast to avoid undefined behaviour + on overflow */ + i = (long)((unsigned long)a + b); + if ((i^a) < 0 && (i^b) < 0) + goto slow_add; + x = PyInt_FromLong(i); + } + else if (PyString_CheckExact(v) && + PyString_CheckExact(w)) { + x = string_concatenate(v, w, f, next_instr); + /* string_concatenate consumed the ref to v */ + goto skip_decref_vx; + } + else { + slow_add: + x = PyNumber_Add(v, w); + } + Py_DECREF(v); + skip_decref_vx: + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case BINARY_SUBTRACT: + w = POP(); + v = TOP(); + if (PyInt_CheckExact(v) && PyInt_CheckExact(w)) { + /* INLINE: int - int */ + register long a, b, i; + a = PyInt_AS_LONG(v); + b = PyInt_AS_LONG(w); + /* cast to avoid undefined behaviour + on overflow */ + i = (long)((unsigned long)a - b); + if ((i^a) < 0 && (i^~b) < 0) + goto slow_sub; + x = PyInt_FromLong(i); + } + else { + slow_sub: + x = PyNumber_Subtract(v, w); + } + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case BINARY_SUBSCR: + w = POP(); + v = TOP(); + if (PyList_CheckExact(v) && PyInt_CheckExact(w)) { + /* INLINE: list[int] */ + Py_ssize_t i = PyInt_AsSsize_t(w); + if (i < 0) + i += PyList_GET_SIZE(v); + if (i >= 0 && i < PyList_GET_SIZE(v)) { + x = PyList_GET_ITEM(v, i); + Py_INCREF(x); + } + else + goto slow_get; + } + else + slow_get: + x = PyObject_GetItem(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case BINARY_LSHIFT: + w = POP(); + v = TOP(); + x = PyNumber_Lshift(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case BINARY_RSHIFT: + w = POP(); + v = TOP(); + x = PyNumber_Rshift(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case BINARY_AND: + w = POP(); + v = TOP(); + x = PyNumber_And(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case BINARY_XOR: + w = POP(); + v = TOP(); + x = PyNumber_Xor(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case BINARY_OR: + w = POP(); + v = TOP(); + x = PyNumber_Or(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case LIST_APPEND: + w = POP(); + v = PEEK(oparg); + err = PyList_Append(v, w); + Py_DECREF(w); + if (err == 0) { + PREDICT(JUMP_ABSOLUTE); + continue; + } + break; + + case SET_ADD: + w = POP(); + v = stack_pointer[-oparg]; + err = PySet_Add(v, w); + Py_DECREF(w); + if (err == 0) { + PREDICT(JUMP_ABSOLUTE); + continue; + } + break; + + case INPLACE_POWER: + w = POP(); + v = TOP(); + x = PyNumber_InPlacePower(v, w, Py_None); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case INPLACE_MULTIPLY: + w = POP(); + v = TOP(); + x = PyNumber_InPlaceMultiply(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case INPLACE_DIVIDE: + if (!_Py_QnewFlag) { + w = POP(); + v = TOP(); + x = PyNumber_InPlaceDivide(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + } + /* -Qnew is in effect: fall through to + INPLACE_TRUE_DIVIDE */ + case INPLACE_TRUE_DIVIDE: + w = POP(); + v = TOP(); + x = PyNumber_InPlaceTrueDivide(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case INPLACE_FLOOR_DIVIDE: + w = POP(); + v = TOP(); + x = PyNumber_InPlaceFloorDivide(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case INPLACE_MODULO: + w = POP(); + v = TOP(); + x = PyNumber_InPlaceRemainder(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case INPLACE_ADD: + w = POP(); + v = TOP(); + if (PyInt_CheckExact(v) && PyInt_CheckExact(w)) { + /* INLINE: int + int */ + register long a, b, i; + a = PyInt_AS_LONG(v); + b = PyInt_AS_LONG(w); + i = a + b; + if ((i^a) < 0 && (i^b) < 0) + goto slow_iadd; + x = PyInt_FromLong(i); + } + else if (PyString_CheckExact(v) && + PyString_CheckExact(w)) { + x = string_concatenate(v, w, f, next_instr); + /* string_concatenate consumed the ref to v */ + goto skip_decref_v; + } + else { + slow_iadd: + x = PyNumber_InPlaceAdd(v, w); + } + Py_DECREF(v); + skip_decref_v: + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case INPLACE_SUBTRACT: + w = POP(); + v = TOP(); + if (PyInt_CheckExact(v) && PyInt_CheckExact(w)) { + /* INLINE: int - int */ + register long a, b, i; + a = PyInt_AS_LONG(v); + b = PyInt_AS_LONG(w); + i = a - b; + if ((i^a) < 0 && (i^~b) < 0) + goto slow_isub; + x = PyInt_FromLong(i); + } + else { + slow_isub: + x = PyNumber_InPlaceSubtract(v, w); + } + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case INPLACE_LSHIFT: + w = POP(); + v = TOP(); + x = PyNumber_InPlaceLshift(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case INPLACE_RSHIFT: + w = POP(); + v = TOP(); + x = PyNumber_InPlaceRshift(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case INPLACE_AND: + w = POP(); + v = TOP(); + x = PyNumber_InPlaceAnd(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case INPLACE_XOR: + w = POP(); + v = TOP(); + x = PyNumber_InPlaceXor(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case INPLACE_OR: + w = POP(); + v = TOP(); + x = PyNumber_InPlaceOr(v, w); + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case SLICE+0: + case SLICE+1: + case SLICE+2: + case SLICE+3: + if ((opcode-SLICE) & 2) + w = POP(); + else + w = NULL; + if ((opcode-SLICE) & 1) + v = POP(); + else + v = NULL; + u = TOP(); + x = apply_slice(u, v, w); + Py_DECREF(u); + Py_XDECREF(v); + Py_XDECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case STORE_SLICE+0: + case STORE_SLICE+1: + case STORE_SLICE+2: + case STORE_SLICE+3: + if ((opcode-STORE_SLICE) & 2) + w = POP(); + else + w = NULL; + if ((opcode-STORE_SLICE) & 1) + v = POP(); + else + v = NULL; + u = POP(); + t = POP(); + err = assign_slice(u, v, w, t); /* u[v:w] = t */ + Py_DECREF(t); + Py_DECREF(u); + Py_XDECREF(v); + Py_XDECREF(w); + if (err == 0) continue; + break; + + case DELETE_SLICE+0: + case DELETE_SLICE+1: + case DELETE_SLICE+2: + case DELETE_SLICE+3: + if ((opcode-DELETE_SLICE) & 2) + w = POP(); + else + w = NULL; + if ((opcode-DELETE_SLICE) & 1) + v = POP(); + else + v = NULL; + u = POP(); + err = assign_slice(u, v, w, (PyObject *)NULL); + /* del u[v:w] */ + Py_DECREF(u); + Py_XDECREF(v); + Py_XDECREF(w); + if (err == 0) continue; + break; + + case STORE_SUBSCR: + w = TOP(); + v = SECOND(); + u = THIRD(); + STACKADJ(-3); + /* v[w] = u */ + err = PyObject_SetItem(v, w, u); + Py_DECREF(u); + Py_DECREF(v); + Py_DECREF(w); + if (err == 0) continue; + break; + + case DELETE_SUBSCR: + w = TOP(); + v = SECOND(); + STACKADJ(-2); + /* del v[w] */ + err = PyObject_DelItem(v, w); + Py_DECREF(v); + Py_DECREF(w); + if (err == 0) continue; + break; + + case PRINT_EXPR: + v = POP(); + w = PySys_GetObject("displayhook"); + if (w == NULL) { + PyErr_SetString(PyExc_RuntimeError, + "lost sys.displayhook"); + err = -1; + x = NULL; + } + if (err == 0) { + x = PyTuple_Pack(1, v); + if (x == NULL) + err = -1; + } + if (err == 0) { + w = PyEval_CallObject(w, x); + Py_XDECREF(w); + if (w == NULL) + err = -1; + } + Py_DECREF(v); + Py_XDECREF(x); + break; + + case PRINT_ITEM_TO: + w = stream = POP(); + /* fall through to PRINT_ITEM */ + + case PRINT_ITEM: + v = POP(); + if (stream == NULL || stream == Py_None) { + w = PySys_GetObject("stdout"); + if (w == NULL) { + PyErr_SetString(PyExc_RuntimeError, + "lost sys.stdout"); + err = -1; + } + } + /* PyFile_SoftSpace() can exececute arbitrary code + if sys.stdout is an instance with a __getattr__. + If __getattr__ raises an exception, w will + be freed, so we need to prevent that temporarily. */ + Py_XINCREF(w); + if (w != NULL && PyFile_SoftSpace(w, 0)) + err = PyFile_WriteString(" ", w); + if (err == 0) + err = PyFile_WriteObject(v, w, Py_PRINT_RAW); + if (err == 0) { + /* XXX move into writeobject() ? */ + if (PyString_Check(v)) { + char *s = PyString_AS_STRING(v); + Py_ssize_t len = PyString_GET_SIZE(v); + if (len == 0 || + !isspace(Py_CHARMASK(s[len-1])) || + s[len-1] == ' ') + PyFile_SoftSpace(w, 1); + } +#ifdef Py_USING_UNICODE + else if (PyUnicode_Check(v)) { + Py_UNICODE *s = PyUnicode_AS_UNICODE(v); + Py_ssize_t len = PyUnicode_GET_SIZE(v); + if (len == 0 || + !Py_UNICODE_ISSPACE(s[len-1]) || + s[len-1] == ' ') + PyFile_SoftSpace(w, 1); + } +#endif + else + PyFile_SoftSpace(w, 1); + } + Py_XDECREF(w); + Py_DECREF(v); + Py_XDECREF(stream); + stream = NULL; + if (err == 0) + continue; + break; + + case PRINT_NEWLINE_TO: + w = stream = POP(); + /* fall through to PRINT_NEWLINE */ + + case PRINT_NEWLINE: + if (stream == NULL || stream == Py_None) { + w = PySys_GetObject("stdout"); + if (w == NULL) { + PyErr_SetString(PyExc_RuntimeError, + "lost sys.stdout"); + why = WHY_EXCEPTION; + } + } + if (w != NULL) { + /* w.write() may replace sys.stdout, so we + * have to keep our reference to it */ + Py_INCREF(w); + err = PyFile_WriteString("\n", w); + if (err == 0) + PyFile_SoftSpace(w, 0); + Py_DECREF(w); + } + Py_XDECREF(stream); + stream = NULL; + break; + + +#ifdef CASE_TOO_BIG + default: switch (opcode) { +#endif + case RAISE_VARARGS: + u = v = w = NULL; + switch (oparg) { + case 3: + u = POP(); /* traceback */ + /* Fallthrough */ + case 2: + v = POP(); /* value */ + /* Fallthrough */ + case 1: + w = POP(); /* exc */ + case 0: /* Fallthrough */ + why = do_raise(w, v, u); + break; + default: + PyErr_SetString(PyExc_SystemError, + "bad RAISE_VARARGS oparg"); + why = WHY_EXCEPTION; + break; + } + break; + + case LOAD_LOCALS: + if ((x = f->f_locals) != NULL) { + Py_INCREF(x); + PUSH(x); + continue; + } + PyErr_SetString(PyExc_SystemError, "no locals"); + break; + + case RETURN_VALUE: + retval = POP(); + why = WHY_RETURN; + goto fast_block_end; + + case YIELD_VALUE: + retval = POP(); + f->f_stacktop = stack_pointer; + why = WHY_YIELD; + goto fast_yield; + + case EXEC_STMT: + w = TOP(); + v = SECOND(); + u = THIRD(); + STACKADJ(-3); + READ_TIMESTAMP(intr0); + err = exec_statement(f, u, v, w); + READ_TIMESTAMP(intr1); + Py_DECREF(u); + Py_DECREF(v); + Py_DECREF(w); + break; + + case POP_BLOCK: + { + PyTryBlock *b = PyFrame_BlockPop(f); + while (STACK_LEVEL() > b->b_level) { + v = POP(); + Py_DECREF(v); + } + } + continue; + + PREDICTED(END_FINALLY); + case END_FINALLY: + v = POP(); + if (PyInt_Check(v)) { + why = (enum why_code) PyInt_AS_LONG(v); + assert(why != WHY_YIELD); + if (why == WHY_RETURN || + why == WHY_CONTINUE) + retval = POP(); + } + else if (PyExceptionClass_Check(v) || + PyString_Check(v)) { + w = POP(); + u = POP(); + PyErr_Restore(v, w, u); + why = WHY_RERAISE; + break; + } + else if (v != Py_None) { + PyErr_SetString(PyExc_SystemError, + "'finally' pops bad exception"); + why = WHY_EXCEPTION; + } + Py_DECREF(v); + break; + + case BUILD_CLASS: + u = TOP(); + v = SECOND(); + w = THIRD(); + STACKADJ(-2); + x = build_class(u, v, w); + SET_TOP(x); + Py_DECREF(u); + Py_DECREF(v); + Py_DECREF(w); + break; + + case STORE_NAME: + w = GETITEM(names, oparg); + v = POP(); + if ((x = f->f_locals) != NULL) { + if (PyDict_CheckExact(x)) + err = PyDict_SetItem(x, w, v); + else + err = PyObject_SetItem(x, w, v); + Py_DECREF(v); + if (err == 0) continue; + break; + } + t = PyObject_Repr(w); + if (t == NULL) + break; + PyErr_Format(PyExc_SystemError, + "no locals found when storing %s", + PyString_AS_STRING(t)); + Py_DECREF(t); + break; + + case DELETE_NAME: + w = GETITEM(names, oparg); + if ((x = f->f_locals) != NULL) { + if ((err = PyObject_DelItem(x, w)) != 0) + format_exc_check_arg(PyExc_NameError, + NAME_ERROR_MSG, + w); + break; + } + t = PyObject_Repr(w); + if (t == NULL) + break; + PyErr_Format(PyExc_SystemError, + "no locals when deleting %s", + PyString_AS_STRING(w)); + Py_DECREF(t); + break; + + PREDICTED_WITH_ARG(UNPACK_SEQUENCE); + case UNPACK_SEQUENCE: + v = POP(); + if (PyTuple_CheckExact(v) && + PyTuple_GET_SIZE(v) == oparg) { + PyObject **items = \ + ((PyTupleObject *)v)->ob_item; + while (oparg--) { + w = items[oparg]; + Py_INCREF(w); + PUSH(w); + } + Py_DECREF(v); + continue; + } else if (PyList_CheckExact(v) && + PyList_GET_SIZE(v) == oparg) { + PyObject **items = \ + ((PyListObject *)v)->ob_item; + while (oparg--) { + w = items[oparg]; + Py_INCREF(w); + PUSH(w); + } + } else if (unpack_iterable(v, oparg, + stack_pointer + oparg)) { + STACKADJ(oparg); + } else { + /* unpack_iterable() raised an exception */ + why = WHY_EXCEPTION; + } + Py_DECREF(v); + break; + + case STORE_ATTR: + w = GETITEM(names, oparg); + v = TOP(); + u = SECOND(); + STACKADJ(-2); + err = PyObject_SetAttr(v, w, u); /* v.w = u */ + Py_DECREF(v); + Py_DECREF(u); + if (err == 0) continue; + break; + + case DELETE_ATTR: + w = GETITEM(names, oparg); + v = POP(); + err = PyObject_SetAttr(v, w, (PyObject *)NULL); + /* del v.w */ + Py_DECREF(v); + break; + + case STORE_GLOBAL: + w = GETITEM(names, oparg); + v = POP(); + err = PyDict_SetItem(f->f_globals, w, v); + Py_DECREF(v); + if (err == 0) continue; + break; + + case DELETE_GLOBAL: + w = GETITEM(names, oparg); + if ((err = PyDict_DelItem(f->f_globals, w)) != 0) + format_exc_check_arg( + PyExc_NameError, GLOBAL_NAME_ERROR_MSG, w); + break; + + case LOAD_NAME: + w = GETITEM(names, oparg); + if ((v = f->f_locals) == NULL) { + why = WHY_EXCEPTION; + t = PyObject_Repr(w); + if (t == NULL) + break; + PyErr_Format(PyExc_SystemError, + "no locals when loading %s", + PyString_AS_STRING(w)); + Py_DECREF(t); + break; + } + if (PyDict_CheckExact(v)) { + x = PyDict_GetItem(v, w); + Py_XINCREF(x); + } + else { + x = PyObject_GetItem(v, w); + if (x == NULL && PyErr_Occurred()) { + if (!PyErr_ExceptionMatches( + PyExc_KeyError)) + break; + PyErr_Clear(); + } + } + if (x == NULL) { + x = PyDict_GetItem(f->f_globals, w); + if (x == NULL) { + x = PyDict_GetItem(f->f_builtins, w); + if (x == NULL) { + format_exc_check_arg( + PyExc_NameError, + NAME_ERROR_MSG, w); + break; + } + } + Py_INCREF(x); + } + PUSH(x); + continue; + + case LOAD_GLOBAL: + w = GETITEM(names, oparg); + if (PyString_CheckExact(w)) { + /* Inline the PyDict_GetItem() calls. + WARNING: this is an extreme speed hack. + Do not try this at home. */ + long hash = ((PyStringObject *)w)->ob_shash; + if (hash != -1) { + PyDictObject *d; + PyDictEntry *e; + d = (PyDictObject *)(f->f_globals); + e = d->ma_lookup(d, w, hash); + if (e == NULL) { + x = NULL; + break; + } + x = e->me_value; + if (x != NULL) { + Py_INCREF(x); + PUSH(x); + continue; + } + d = (PyDictObject *)(f->f_builtins); + e = d->ma_lookup(d, w, hash); + if (e == NULL) { + x = NULL; + break; + } + x = e->me_value; + if (x != NULL) { + Py_INCREF(x); + PUSH(x); + continue; + } + goto load_global_error; + } + } + /* This is the un-inlined version of the code above */ + x = PyDict_GetItem(f->f_globals, w); + if (x == NULL) { + x = PyDict_GetItem(f->f_builtins, w); + if (x == NULL) { + load_global_error: + format_exc_check_arg( + PyExc_NameError, + GLOBAL_NAME_ERROR_MSG, w); + break; + } + } + Py_INCREF(x); + PUSH(x); + continue; + + case DELETE_FAST: + x = GETLOCAL(oparg); + if (x != NULL) { + SETLOCAL(oparg, NULL); + continue; + } + format_exc_check_arg( + PyExc_UnboundLocalError, + UNBOUNDLOCAL_ERROR_MSG, + PyTuple_GetItem(co->co_varnames, oparg) + ); + break; + + case LOAD_CLOSURE: + x = freevars[oparg]; + Py_INCREF(x); + PUSH(x); + if (x != NULL) continue; + break; + + case LOAD_DEREF: + x = freevars[oparg]; + w = PyCell_Get(x); + if (w != NULL) { + PUSH(w); + continue; + } + err = -1; + /* Don't stomp existing exception */ + if (PyErr_Occurred()) + break; + if (oparg < PyTuple_GET_SIZE(co->co_cellvars)) { + v = PyTuple_GET_ITEM(co->co_cellvars, + oparg); + format_exc_check_arg( + PyExc_UnboundLocalError, + UNBOUNDLOCAL_ERROR_MSG, + v); + } else { + v = PyTuple_GET_ITEM(co->co_freevars, oparg - + PyTuple_GET_SIZE(co->co_cellvars)); + format_exc_check_arg(PyExc_NameError, + UNBOUNDFREE_ERROR_MSG, v); + } + break; + + case STORE_DEREF: + w = POP(); + x = freevars[oparg]; + PyCell_Set(x, w); + Py_DECREF(w); + continue; + + case BUILD_TUPLE: + x = PyTuple_New(oparg); + if (x != NULL) { + for (; --oparg >= 0;) { + w = POP(); + PyTuple_SET_ITEM(x, oparg, w); + } + PUSH(x); + continue; + } + break; + + case BUILD_LIST: + x = PyList_New(oparg); + if (x != NULL) { + for (; --oparg >= 0;) { + w = POP(); + PyList_SET_ITEM(x, oparg, w); + } + PUSH(x); + continue; + } + break; + + case BUILD_SET: + x = PySet_New(NULL); + if (x != NULL) { + for (; --oparg >= 0;) { + w = POP(); + if (err == 0) + err = PySet_Add(x, w); + Py_DECREF(w); + } + if (err != 0) { + Py_DECREF(x); + break; + } + PUSH(x); + continue; + } + break; + + + case BUILD_MAP: + x = _PyDict_NewPresized((Py_ssize_t)oparg); + PUSH(x); + if (x != NULL) continue; + break; + + case STORE_MAP: + w = TOP(); /* key */ + u = SECOND(); /* value */ + v = THIRD(); /* dict */ + STACKADJ(-2); + assert (PyDict_CheckExact(v)); + err = PyDict_SetItem(v, w, u); /* v[w] = u */ + Py_DECREF(u); + Py_DECREF(w); + if (err == 0) continue; + break; + + case MAP_ADD: + w = TOP(); /* key */ + u = SECOND(); /* value */ + STACKADJ(-2); + v = stack_pointer[-oparg]; /* dict */ + assert (PyDict_CheckExact(v)); + err = PyDict_SetItem(v, w, u); /* v[w] = u */ + Py_DECREF(u); + Py_DECREF(w); + if (err == 0) { + PREDICT(JUMP_ABSOLUTE); + continue; + } + break; + + case LOAD_ATTR: + w = GETITEM(names, oparg); + v = TOP(); + x = PyObject_GetAttr(v, w); + Py_DECREF(v); + SET_TOP(x); + if (x != NULL) continue; + break; + + case COMPARE_OP: + w = POP(); + v = TOP(); + if (PyInt_CheckExact(w) && PyInt_CheckExact(v)) { + /* INLINE: cmp(int, int) */ + register long a, b; + register int res; + a = PyInt_AS_LONG(v); + b = PyInt_AS_LONG(w); + switch (oparg) { + case PyCmp_LT: res = a < b; break; + case PyCmp_LE: res = a <= b; break; + case PyCmp_EQ: res = a == b; break; + case PyCmp_NE: res = a != b; break; + case PyCmp_GT: res = a > b; break; + case PyCmp_GE: res = a >= b; break; + case PyCmp_IS: res = v == w; break; + case PyCmp_IS_NOT: res = v != w; break; + default: goto slow_compare; + } + x = res ? Py_True : Py_False; + Py_INCREF(x); + } + else { + slow_compare: + x = cmp_outcome(oparg, v, w); + } + Py_DECREF(v); + Py_DECREF(w); + SET_TOP(x); + if (x == NULL) break; + PREDICT(POP_JUMP_IF_FALSE); + PREDICT(POP_JUMP_IF_TRUE); + continue; + + case IMPORT_NAME: + w = GETITEM(names, oparg); + x = PyDict_GetItemString(f->f_builtins, "__import__"); + if (x == NULL) { + PyErr_SetString(PyExc_ImportError, + "__import__ not found"); + break; + } + Py_INCREF(x); + v = POP(); + u = TOP(); + if (PyInt_AsLong(u) != -1 || PyErr_Occurred()) + w = PyTuple_Pack(5, + w, + f->f_globals, + f->f_locals == NULL ? + Py_None : f->f_locals, + v, + u); + else + w = PyTuple_Pack(4, + w, + f->f_globals, + f->f_locals == NULL ? + Py_None : f->f_locals, + v); + Py_DECREF(v); + Py_DECREF(u); + if (w == NULL) { + u = POP(); + Py_DECREF(x); + x = NULL; + break; + } + READ_TIMESTAMP(intr0); + v = x; + x = PyEval_CallObject(v, w); + Py_DECREF(v); + READ_TIMESTAMP(intr1); + Py_DECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case IMPORT_STAR: + v = POP(); + PyFrame_FastToLocals(f); + if ((x = f->f_locals) == NULL) { + PyErr_SetString(PyExc_SystemError, + "no locals found during 'import *'"); + break; + } + READ_TIMESTAMP(intr0); + err = import_all_from(x, v); + READ_TIMESTAMP(intr1); + PyFrame_LocalsToFast(f, 0); + Py_DECREF(v); + if (err == 0) continue; + break; + + case IMPORT_FROM: + w = GETITEM(names, oparg); + v = TOP(); + READ_TIMESTAMP(intr0); + x = import_from(v, w); + READ_TIMESTAMP(intr1); + PUSH(x); + if (x != NULL) continue; + break; + + case JUMP_FORWARD: + JUMPBY(oparg); + goto fast_next_opcode; + + PREDICTED_WITH_ARG(POP_JUMP_IF_FALSE); + case POP_JUMP_IF_FALSE: + w = POP(); + if (w == Py_True) { + Py_DECREF(w); + goto fast_next_opcode; + } + if (w == Py_False) { + Py_DECREF(w); + JUMPTO(oparg); + goto fast_next_opcode; + } + err = PyObject_IsTrue(w); + Py_DECREF(w); + if (err > 0) + err = 0; + else if (err == 0) + JUMPTO(oparg); + else + break; + continue; + + PREDICTED_WITH_ARG(POP_JUMP_IF_TRUE); + case POP_JUMP_IF_TRUE: + w = POP(); + if (w == Py_False) { + Py_DECREF(w); + goto fast_next_opcode; + } + if (w == Py_True) { + Py_DECREF(w); + JUMPTO(oparg); + goto fast_next_opcode; + } + err = PyObject_IsTrue(w); + Py_DECREF(w); + if (err > 0) { + err = 0; + JUMPTO(oparg); + } + else if (err == 0) + ; + else + break; + continue; + + case JUMP_IF_FALSE_OR_POP: + w = TOP(); + if (w == Py_True) { + STACKADJ(-1); + Py_DECREF(w); + goto fast_next_opcode; + } + if (w == Py_False) { + JUMPTO(oparg); + goto fast_next_opcode; + } + err = PyObject_IsTrue(w); + if (err > 0) { + STACKADJ(-1); + Py_DECREF(w); + err = 0; + } + else if (err == 0) + JUMPTO(oparg); + else + break; + continue; + + case JUMP_IF_TRUE_OR_POP: + w = TOP(); + if (w == Py_False) { + STACKADJ(-1); + Py_DECREF(w); + goto fast_next_opcode; + } + if (w == Py_True) { + JUMPTO(oparg); + goto fast_next_opcode; + } + err = PyObject_IsTrue(w); + if (err > 0) { + err = 0; + JUMPTO(oparg); + } + else if (err == 0) { + STACKADJ(-1); + Py_DECREF(w); + } + else + break; + continue; + + PREDICTED_WITH_ARG(JUMP_ABSOLUTE); + case JUMP_ABSOLUTE: + JUMPTO(oparg); +#if FAST_LOOPS + /* Enabling this path speeds-up all while and for-loops by bypassing + the per-loop checks for signals. By default, this should be turned-off + because it prevents detection of a control-break in tight loops like + "while 1: pass". Compile with this option turned-on when you need + the speed-up and do not need break checking inside tight loops (ones + that contain only instructions ending with goto fast_next_opcode). + */ + goto fast_next_opcode; +#else + continue; +#endif + + case GET_ITER: + /* before: [obj]; after [getiter(obj)] */ + v = TOP(); + x = PyObject_GetIter(v); + Py_DECREF(v); + if (x != NULL) { + SET_TOP(x); + PREDICT(FOR_ITER); + continue; + } + STACKADJ(-1); + break; + + PREDICTED_WITH_ARG(FOR_ITER); + case FOR_ITER: + /* before: [iter]; after: [iter, iter()] *or* [] */ + v = TOP(); + x = (*v->ob_type->tp_iternext)(v); + if (x != NULL) { + PUSH(x); + PREDICT(STORE_FAST); + PREDICT(UNPACK_SEQUENCE); + continue; + } + if (PyErr_Occurred()) { + if (!PyErr_ExceptionMatches( + PyExc_StopIteration)) + break; + PyErr_Clear(); + } + /* iterator ended normally */ + x = v = POP(); + Py_DECREF(v); + JUMPBY(oparg); + continue; + + case BREAK_LOOP: + why = WHY_BREAK; + goto fast_block_end; + + case CONTINUE_LOOP: + retval = PyInt_FromLong(oparg); + if (!retval) { + x = NULL; + break; + } + why = WHY_CONTINUE; + goto fast_block_end; + + case SETUP_LOOP: + case SETUP_EXCEPT: + case SETUP_FINALLY: + /* NOTE: If you add any new block-setup opcodes that + are not try/except/finally handlers, you may need + to update the PyGen_NeedsFinalizing() function. + */ + + PyFrame_BlockSetup(f, opcode, INSTR_OFFSET() + oparg, + STACK_LEVEL()); + continue; + + case SETUP_WITH: + { + static PyObject *exit, *enter; + w = TOP(); + x = special_lookup(w, "__exit__", &exit); + if (!x) + break; + SET_TOP(x); + u = special_lookup(w, "__enter__", &enter); + Py_DECREF(w); + if (!u) { + x = NULL; + break; + } + x = PyObject_CallFunctionObjArgs(u, NULL); + Py_DECREF(u); + if (!x) + break; + /* Setup a finally block (SETUP_WITH as a block is + equivalent to SETUP_FINALLY except it normalizes + the exception) before pushing the result of + __enter__ on the stack. */ + PyFrame_BlockSetup(f, SETUP_WITH, INSTR_OFFSET() + oparg, + STACK_LEVEL()); + + PUSH(x); + continue; + } + + case WITH_CLEANUP: + { + /* At the top of the stack are 1-3 values indicating + how/why we entered the finally clause: + - TOP = None + - (TOP, SECOND) = (WHY_{RETURN,CONTINUE}), retval + - TOP = WHY_*; no retval below it + - (TOP, SECOND, THIRD) = exc_info() + Below them is EXIT, the context.__exit__ bound method. + In the last case, we must call + EXIT(TOP, SECOND, THIRD) + otherwise we must call + EXIT(None, None, None) + + In all cases, we remove EXIT from the stack, leaving + the rest in the same order. + + In addition, if the stack represents an exception, + *and* the function call returns a 'true' value, we + "zap" this information, to prevent END_FINALLY from + re-raising the exception. (But non-local gotos + should still be resumed.) + */ + + PyObject *exit_func; + + u = POP(); + if (u == Py_None) { + exit_func = TOP(); + SET_TOP(u); + v = w = Py_None; + } + else if (PyInt_Check(u)) { + switch(PyInt_AS_LONG(u)) { + case WHY_RETURN: + case WHY_CONTINUE: + /* Retval in TOP. */ + exit_func = SECOND(); + SET_SECOND(TOP()); + SET_TOP(u); + break; + default: + exit_func = TOP(); + SET_TOP(u); + break; + } + u = v = w = Py_None; + } + else { + v = TOP(); + w = SECOND(); + exit_func = THIRD(); + SET_TOP(u); + SET_SECOND(v); + SET_THIRD(w); + } + /* XXX Not the fastest way to call it... */ + x = PyObject_CallFunctionObjArgs(exit_func, u, v, w, + NULL); + Py_DECREF(exit_func); + if (x == NULL) + break; /* Go to error exit */ + + if (u != Py_None) + err = PyObject_IsTrue(x); + else + err = 0; + Py_DECREF(x); + + if (err < 0) + break; /* Go to error exit */ + else if (err > 0) { + err = 0; + /* There was an exception and a true return */ + STACKADJ(-2); + Py_INCREF(Py_None); + SET_TOP(Py_None); + Py_DECREF(u); + Py_DECREF(v); + Py_DECREF(w); + } else { + /* The stack was rearranged to remove EXIT + above. Let END_FINALLY do its thing */ + } + PREDICT(END_FINALLY); + break; + } + + case CALL_FUNCTION: + { + PyObject **sp; + PCALL(PCALL_ALL); + sp = stack_pointer; +#ifdef WITH_TSC + x = call_function(&sp, oparg, &intr0, &intr1); +#else + x = call_function(&sp, oparg); +#endif + stack_pointer = sp; + PUSH(x); + if (x != NULL) + continue; + break; + } + + case CALL_FUNCTION_VAR: + case CALL_FUNCTION_KW: + case CALL_FUNCTION_VAR_KW: + { + int na = oparg & 0xff; + int nk = (oparg>>8) & 0xff; + int flags = (opcode - CALL_FUNCTION) & 3; + int n = na + 2 * nk; + PyObject **pfunc, *func, **sp; + PCALL(PCALL_ALL); + if (flags & CALL_FLAG_VAR) + n++; + if (flags & CALL_FLAG_KW) + n++; + pfunc = stack_pointer - n - 1; + func = *pfunc; + + if (PyMethod_Check(func) + && PyMethod_GET_SELF(func) != NULL) { + PyObject *self = PyMethod_GET_SELF(func); + Py_INCREF(self); + func = PyMethod_GET_FUNCTION(func); + Py_INCREF(func); + Py_DECREF(*pfunc); + *pfunc = self; + na++; + } else + Py_INCREF(func); + sp = stack_pointer; + READ_TIMESTAMP(intr0); + x = ext_do_call(func, &sp, flags, na, nk); + READ_TIMESTAMP(intr1); + stack_pointer = sp; + Py_DECREF(func); + + while (stack_pointer > pfunc) { + w = POP(); + Py_DECREF(w); + } + PUSH(x); + if (x != NULL) + continue; + break; + } + + case MAKE_FUNCTION: + v = POP(); /* code object */ + x = PyFunction_New(v, f->f_globals); + Py_DECREF(v); + /* XXX Maybe this should be a separate opcode? */ + if (x != NULL && oparg > 0) { + v = PyTuple_New(oparg); + if (v == NULL) { + Py_DECREF(x); + x = NULL; + break; + } + while (--oparg >= 0) { + w = POP(); + PyTuple_SET_ITEM(v, oparg, w); + } + err = PyFunction_SetDefaults(x, v); + Py_DECREF(v); + } + PUSH(x); + break; + + case MAKE_CLOSURE: + { + v = POP(); /* code object */ + x = PyFunction_New(v, f->f_globals); + Py_DECREF(v); + if (x != NULL) { + v = POP(); + if (PyFunction_SetClosure(x, v) != 0) { + /* Can't happen unless bytecode is corrupt. */ + why = WHY_EXCEPTION; + } + Py_DECREF(v); + } + if (x != NULL && oparg > 0) { + v = PyTuple_New(oparg); + if (v == NULL) { + Py_DECREF(x); + x = NULL; + break; + } + while (--oparg >= 0) { + w = POP(); + PyTuple_SET_ITEM(v, oparg, w); + } + if (PyFunction_SetDefaults(x, v) != 0) { + /* Can't happen unless + PyFunction_SetDefaults changes. */ + why = WHY_EXCEPTION; + } + Py_DECREF(v); + } + PUSH(x); + break; + } + + case BUILD_SLICE: + if (oparg == 3) + w = POP(); + else + w = NULL; + v = POP(); + u = TOP(); + x = PySlice_New(u, v, w); + Py_DECREF(u); + Py_DECREF(v); + Py_XDECREF(w); + SET_TOP(x); + if (x != NULL) continue; + break; + + case EXTENDED_ARG: + opcode = NEXTOP(); + oparg = oparg<<16 | NEXTARG(); + goto dispatch_opcode; + + default: + fprintf(stderr, + "XXX lineno: %d, opcode: %d\n", + PyFrame_GetLineNumber(f), + opcode); + PyErr_SetString(PyExc_SystemError, "unknown opcode"); + why = WHY_EXCEPTION; + break; + +#ifdef CASE_TOO_BIG + } +#endif + + } /* switch */ + + on_error: + + READ_TIMESTAMP(inst1); + + /* Quickly continue if no error occurred */ + + if (why == WHY_NOT) { + if (err == 0 && x != NULL) { +#ifdef CHECKEXC + /* This check is expensive! */ + if (PyErr_Occurred()) + fprintf(stderr, + "XXX undetected error\n"); + else { +#endif + READ_TIMESTAMP(loop1); + continue; /* Normal, fast path */ +#ifdef CHECKEXC + } +#endif + } + why = WHY_EXCEPTION; + x = Py_None; + err = 0; + } + + /* Double-check exception status */ + + if (why == WHY_EXCEPTION || why == WHY_RERAISE) { + if (!PyErr_Occurred()) { + PyErr_SetString(PyExc_SystemError, + "error return without exception set"); + why = WHY_EXCEPTION; + } + } +#ifdef CHECKEXC + else { + /* This check is expensive! */ + if (PyErr_Occurred()) { + char buf[128]; + sprintf(buf, "Stack unwind with exception " + "set and why=%d", why); + Py_FatalError(buf); + } + } +#endif + + /* Log traceback info if this is a real exception */ + + if (why == WHY_EXCEPTION) { + PyTraceBack_Here(f); + + if (tstate->c_tracefunc != NULL) + call_exc_trace(tstate->c_tracefunc, + tstate->c_traceobj, f); + } + + /* For the rest, treat WHY_RERAISE as WHY_EXCEPTION */ + + if (why == WHY_RERAISE) + why = WHY_EXCEPTION; + + /* Unwind stacks if a (pseudo) exception occurred */ + +fast_block_end: + while (why != WHY_NOT && f->f_iblock > 0) { + /* Peek at the current block. */ + PyTryBlock *b = &f->f_blockstack[f->f_iblock - 1]; + + assert(why != WHY_YIELD); + if (b->b_type == SETUP_LOOP && why == WHY_CONTINUE) { + why = WHY_NOT; + JUMPTO(PyInt_AS_LONG(retval)); + Py_DECREF(retval); + break; + } + + /* Now we have to pop the block. */ + f->f_iblock--; + + while (STACK_LEVEL() > b->b_level) { + v = POP(); + Py_XDECREF(v); + } + if (b->b_type == SETUP_LOOP && why == WHY_BREAK) { + why = WHY_NOT; + JUMPTO(b->b_handler); + break; + } + if (b->b_type == SETUP_FINALLY || + (b->b_type == SETUP_EXCEPT && + why == WHY_EXCEPTION) || + b->b_type == SETUP_WITH) { + if (why == WHY_EXCEPTION) { + PyObject *exc, *val, *tb; + PyErr_Fetch(&exc, &val, &tb); + if (val == NULL) { + val = Py_None; + Py_INCREF(val); + } + /* Make the raw exception data + available to the handler, + so a program can emulate the + Python main loop. Don't do + this for 'finally'. */ + if (b->b_type == SETUP_EXCEPT || + b->b_type == SETUP_WITH) { + PyErr_NormalizeException( + &exc, &val, &tb); + set_exc_info(tstate, + exc, val, tb); + } + if (tb == NULL) { + Py_INCREF(Py_None); + PUSH(Py_None); + } else + PUSH(tb); + PUSH(val); + PUSH(exc); + } + else { + if (why & (WHY_RETURN | WHY_CONTINUE)) + PUSH(retval); + v = PyInt_FromLong((long)why); + PUSH(v); + } + why = WHY_NOT; + JUMPTO(b->b_handler); + break; + } + } /* unwind stack */ + + /* End the loop if we still have an error (or return) */ + + if (why != WHY_NOT) + break; + READ_TIMESTAMP(loop1); + + } /* main loop */ + + assert(why != WHY_YIELD); + /* Pop remaining stack entries. */ + while (!EMPTY()) { + v = POP(); + Py_XDECREF(v); + } + + if (why != WHY_RETURN) + retval = NULL; + +fast_yield: + if (tstate->use_tracing) { + if (tstate->c_tracefunc) { + if (why == WHY_RETURN || why == WHY_YIELD) { + if (call_trace(tstate->c_tracefunc, + tstate->c_traceobj, f, + PyTrace_RETURN, retval)) { + Py_XDECREF(retval); + retval = NULL; + why = WHY_EXCEPTION; + } + } + else if (why == WHY_EXCEPTION) { + call_trace_protected(tstate->c_tracefunc, + tstate->c_traceobj, f, + PyTrace_RETURN, NULL); + } + } + if (tstate->c_profilefunc) { + if (why == WHY_EXCEPTION) + call_trace_protected(tstate->c_profilefunc, + tstate->c_profileobj, f, + PyTrace_RETURN, NULL); + else if (call_trace(tstate->c_profilefunc, + tstate->c_profileobj, f, + PyTrace_RETURN, retval)) { + Py_XDECREF(retval); + retval = NULL; + why = WHY_EXCEPTION; + } + } + } + + if (tstate->frame->f_exc_type != NULL) + reset_exc_info(tstate); + else { + assert(tstate->frame->f_exc_value == NULL); + assert(tstate->frame->f_exc_traceback == NULL); + } + + /* pop frame */ +exit_eval_frame: + Py_LeaveRecursiveCall(); + tstate->frame = f->f_back; + + return retval; +} + +/* This is gonna seem *real weird*, but if you put some other code between + PyEval_EvalFrame() and PyEval_EvalCodeEx() you will need to adjust + the test in the if statements in Misc/gdbinit (pystack and pystackv). */ + +PyObject * +PyEval_EvalCodeEx(PyCodeObject *co, PyObject *globals, PyObject *locals, + PyObject **args, int argcount, PyObject **kws, int kwcount, + PyObject **defs, int defcount, PyObject *closure) +{ + register PyFrameObject *f; + register PyObject *retval = NULL; + register PyObject **fastlocals, **freevars; + PyThreadState *tstate = PyThreadState_GET(); + PyObject *x, *u; + + if (globals == NULL) { + PyErr_SetString(PyExc_SystemError, + "PyEval_EvalCodeEx: NULL globals"); + return NULL; + } + + assert(tstate != NULL); + assert(globals != NULL); + f = PyFrame_New(tstate, co, globals, locals); + if (f == NULL) + return NULL; + + fastlocals = f->f_localsplus; + freevars = f->f_localsplus + co->co_nlocals; + + if (co->co_argcount > 0 || + co->co_flags & (CO_VARARGS | CO_VARKEYWORDS)) { + int i; + int n = argcount; + PyObject *kwdict = NULL; + if (co->co_flags & CO_VARKEYWORDS) { + kwdict = PyDict_New(); + if (kwdict == NULL) + goto fail; + i = co->co_argcount; + if (co->co_flags & CO_VARARGS) + i++; + SETLOCAL(i, kwdict); + } + if (argcount > co->co_argcount) { + if (!(co->co_flags & CO_VARARGS)) { + PyErr_Format(PyExc_TypeError, + "%.200s() takes %s %d " + "argument%s (%d given)", + PyString_AsString(co->co_name), + defcount ? "at most" : "exactly", + co->co_argcount, + co->co_argcount == 1 ? "" : "s", + argcount + kwcount); + goto fail; + } + n = co->co_argcount; + } + for (i = 0; i < n; i++) { + x = args[i]; + Py_INCREF(x); + SETLOCAL(i, x); + } + if (co->co_flags & CO_VARARGS) { + u = PyTuple_New(argcount - n); + if (u == NULL) + goto fail; + SETLOCAL(co->co_argcount, u); + for (i = n; i < argcount; i++) { + x = args[i]; + Py_INCREF(x); + PyTuple_SET_ITEM(u, i-n, x); + } + } + for (i = 0; i < kwcount; i++) { + PyObject **co_varnames; + PyObject *keyword = kws[2*i]; + PyObject *value = kws[2*i + 1]; + int j; + if (keyword == NULL || !(PyString_Check(keyword) +#ifdef Py_USING_UNICODE + || PyUnicode_Check(keyword) +#endif + )) { + PyErr_Format(PyExc_TypeError, + "%.200s() keywords must be strings", + PyString_AsString(co->co_name)); + goto fail; + } + /* Speed hack: do raw pointer compares. As names are + normally interned this should almost always hit. */ + co_varnames = ((PyTupleObject *)(co->co_varnames))->ob_item; + for (j = 0; j < co->co_argcount; j++) { + PyObject *nm = co_varnames[j]; + if (nm == keyword) + goto kw_found; + } + /* Slow fallback, just in case */ + for (j = 0; j < co->co_argcount; j++) { + PyObject *nm = co_varnames[j]; + int cmp = PyObject_RichCompareBool( + keyword, nm, Py_EQ); + if (cmp > 0) + goto kw_found; + else if (cmp < 0) + goto fail; + } + if (kwdict == NULL) { + PyObject *kwd_str = kwd_as_string(keyword); + if (kwd_str) { + PyErr_Format(PyExc_TypeError, + "%.200s() got an unexpected " + "keyword argument '%.400s'", + PyString_AsString(co->co_name), + PyString_AsString(kwd_str)); + Py_DECREF(kwd_str); + } + goto fail; + } + PyDict_SetItem(kwdict, keyword, value); + continue; + kw_found: + if (GETLOCAL(j) != NULL) { + PyObject *kwd_str = kwd_as_string(keyword); + if (kwd_str) { + PyErr_Format(PyExc_TypeError, + "%.200s() got multiple " + "values for keyword " + "argument '%.400s'", + PyString_AsString(co->co_name), + PyString_AsString(kwd_str)); + Py_DECREF(kwd_str); + } + goto fail; + } + Py_INCREF(value); + SETLOCAL(j, value); + } + if (argcount < co->co_argcount) { + int m = co->co_argcount - defcount; + for (i = argcount; i < m; i++) { + if (GETLOCAL(i) == NULL) { + int j, given = 0; + for (j = 0; j < co->co_argcount; j++) + if (GETLOCAL(j)) + given++; + PyErr_Format(PyExc_TypeError, + "%.200s() takes %s %d " + "argument%s (%d given)", + PyString_AsString(co->co_name), + ((co->co_flags & CO_VARARGS) || + defcount) ? "at least" + : "exactly", + m, m == 1 ? "" : "s", given); + goto fail; + } + } + if (n > m) + i = n - m; + else + i = 0; + for (; i < defcount; i++) { + if (GETLOCAL(m+i) == NULL) { + PyObject *def = defs[i]; + Py_INCREF(def); + SETLOCAL(m+i, def); + } + } + } + } + else if (argcount > 0 || kwcount > 0) { + PyErr_Format(PyExc_TypeError, + "%.200s() takes no arguments (%d given)", + PyString_AsString(co->co_name), + argcount + kwcount); + goto fail; + } + /* Allocate and initialize storage for cell vars, and copy free + vars into frame. This isn't too efficient right now. */ + if (PyTuple_GET_SIZE(co->co_cellvars)) { + int i, j, nargs, found; + char *cellname, *argname; + PyObject *c; + + nargs = co->co_argcount; + if (co->co_flags & CO_VARARGS) + nargs++; + if (co->co_flags & CO_VARKEYWORDS) + nargs++; + + /* Initialize each cell var, taking into account + cell vars that are initialized from arguments. + + Should arrange for the compiler to put cellvars + that are arguments at the beginning of the cellvars + list so that we can march over it more efficiently? + */ + for (i = 0; i < PyTuple_GET_SIZE(co->co_cellvars); ++i) { + cellname = PyString_AS_STRING( + PyTuple_GET_ITEM(co->co_cellvars, i)); + found = 0; + for (j = 0; j < nargs; j++) { + argname = PyString_AS_STRING( + PyTuple_GET_ITEM(co->co_varnames, j)); + if (strcmp(cellname, argname) == 0) { + c = PyCell_New(GETLOCAL(j)); + if (c == NULL) + goto fail; + GETLOCAL(co->co_nlocals + i) = c; + found = 1; + break; + } + } + if (found == 0) { + c = PyCell_New(NULL); + if (c == NULL) + goto fail; + SETLOCAL(co->co_nlocals + i, c); + } + } + } + if (PyTuple_GET_SIZE(co->co_freevars)) { + int i; + for (i = 0; i < PyTuple_GET_SIZE(co->co_freevars); ++i) { + PyObject *o = PyTuple_GET_ITEM(closure, i); + Py_INCREF(o); + freevars[PyTuple_GET_SIZE(co->co_cellvars) + i] = o; + } + } + + if (co->co_flags & CO_GENERATOR) { + /* Don't need to keep the reference to f_back, it will be set + * when the generator is resumed. */ + Py_CLEAR(f->f_back); + + PCALL(PCALL_GENERATOR); + + /* Create a new generator that owns the ready to run frame + * and return that as the value. */ + return PyGen_New(f); + } + + retval = PyEval_EvalFrameEx(f,0); + +fail: /* Jump here from prelude on failure */ + + /* decref'ing the frame can cause __del__ methods to get invoked, + which can call back into Python. While we're done with the + current Python frame (f), the associated C stack is still in use, + so recursion_depth must be boosted for the duration. + */ + assert(tstate != NULL); + ++tstate->recursion_depth; + Py_DECREF(f); + --tstate->recursion_depth; + return retval; +} + + +static PyObject * +special_lookup(PyObject *o, char *meth, PyObject **cache) +{ + PyObject *res; + if (PyInstance_Check(o)) { + if (!*cache) + return PyObject_GetAttrString(o, meth); + else + return PyObject_GetAttr(o, *cache); + } + res = _PyObject_LookupSpecial(o, meth, cache); + if (res == NULL && !PyErr_Occurred()) { + PyErr_SetObject(PyExc_AttributeError, *cache); + return NULL; + } + return res; +} + + +static PyObject * +kwd_as_string(PyObject *kwd) { +#ifdef Py_USING_UNICODE + if (PyString_Check(kwd)) { +#else + assert(PyString_Check(kwd)); +#endif + Py_INCREF(kwd); + return kwd; +#ifdef Py_USING_UNICODE + } + return _PyUnicode_AsDefaultEncodedString(kwd, "replace"); +#endif +} + + +/* Implementation notes for set_exc_info() and reset_exc_info(): + +- Below, 'exc_ZZZ' stands for 'exc_type', 'exc_value' and + 'exc_traceback'. These always travel together. + +- tstate->curexc_ZZZ is the "hot" exception that is set by + PyErr_SetString(), cleared by PyErr_Clear(), and so on. + +- Once an exception is caught by an except clause, it is transferred + from tstate->curexc_ZZZ to tstate->exc_ZZZ, from which sys.exc_info() + can pick it up. This is the primary task of set_exc_info(). + XXX That can't be right: set_exc_info() doesn't look at tstate->curexc_ZZZ. + +- Now let me explain the complicated dance with frame->f_exc_ZZZ. + + Long ago, when none of this existed, there were just a few globals: + one set corresponding to the "hot" exception, and one set + corresponding to sys.exc_ZZZ. (Actually, the latter weren't C + globals; they were simply stored as sys.exc_ZZZ. For backwards + compatibility, they still are!) The problem was that in code like + this: + + try: + "something that may fail" + except "some exception": + "do something else first" + "print the exception from sys.exc_ZZZ." + + if "do something else first" invoked something that raised and caught + an exception, sys.exc_ZZZ were overwritten. That was a frequent + cause of subtle bugs. I fixed this by changing the semantics as + follows: + + - Within one frame, sys.exc_ZZZ will hold the last exception caught + *in that frame*. + + - But initially, and as long as no exception is caught in a given + frame, sys.exc_ZZZ will hold the last exception caught in the + previous frame (or the frame before that, etc.). + + The first bullet fixed the bug in the above example. The second + bullet was for backwards compatibility: it was (and is) common to + have a function that is called when an exception is caught, and to + have that function access the caught exception via sys.exc_ZZZ. + (Example: traceback.print_exc()). + + At the same time I fixed the problem that sys.exc_ZZZ weren't + thread-safe, by introducing sys.exc_info() which gets it from tstate; + but that's really a separate improvement. + + The reset_exc_info() function in ceval.c restores the tstate->exc_ZZZ + variables to what they were before the current frame was called. The + set_exc_info() function saves them on the frame so that + reset_exc_info() can restore them. The invariant is that + frame->f_exc_ZZZ is NULL iff the current frame never caught an + exception (where "catching" an exception applies only to successful + except clauses); and if the current frame ever caught an exception, + frame->f_exc_ZZZ is the exception that was stored in tstate->exc_ZZZ + at the start of the current frame. + +*/ + +static void +set_exc_info(PyThreadState *tstate, + PyObject *type, PyObject *value, PyObject *tb) +{ + PyFrameObject *frame = tstate->frame; + PyObject *tmp_type, *tmp_value, *tmp_tb; + + assert(type != NULL); + assert(frame != NULL); + if (frame->f_exc_type == NULL) { + assert(frame->f_exc_value == NULL); + assert(frame->f_exc_traceback == NULL); + /* This frame didn't catch an exception before. */ + /* Save previous exception of this thread in this frame. */ + if (tstate->exc_type == NULL) { + /* XXX Why is this set to Py_None? */ + Py_INCREF(Py_None); + tstate->exc_type = Py_None; + } + Py_INCREF(tstate->exc_type); + Py_XINCREF(tstate->exc_value); + Py_XINCREF(tstate->exc_traceback); + frame->f_exc_type = tstate->exc_type; + frame->f_exc_value = tstate->exc_value; + frame->f_exc_traceback = tstate->exc_traceback; + } + /* Set new exception for this thread. */ + tmp_type = tstate->exc_type; + tmp_value = tstate->exc_value; + tmp_tb = tstate->exc_traceback; + Py_INCREF(type); + Py_XINCREF(value); + Py_XINCREF(tb); + tstate->exc_type = type; + tstate->exc_value = value; + tstate->exc_traceback = tb; + Py_XDECREF(tmp_type); + Py_XDECREF(tmp_value); + Py_XDECREF(tmp_tb); + /* For b/w compatibility */ + PySys_SetObject("exc_type", type); + PySys_SetObject("exc_value", value); + PySys_SetObject("exc_traceback", tb); +} + +static void +reset_exc_info(PyThreadState *tstate) +{ + PyFrameObject *frame; + PyObject *tmp_type, *tmp_value, *tmp_tb; + + /* It's a precondition that the thread state's frame caught an + * exception -- verify in a debug build. + */ + assert(tstate != NULL); + frame = tstate->frame; + assert(frame != NULL); + assert(frame->f_exc_type != NULL); + + /* Copy the frame's exception info back to the thread state. */ + tmp_type = tstate->exc_type; + tmp_value = tstate->exc_value; + tmp_tb = tstate->exc_traceback; + Py_INCREF(frame->f_exc_type); + Py_XINCREF(frame->f_exc_value); + Py_XINCREF(frame->f_exc_traceback); + tstate->exc_type = frame->f_exc_type; + tstate->exc_value = frame->f_exc_value; + tstate->exc_traceback = frame->f_exc_traceback; + Py_XDECREF(tmp_type); + Py_XDECREF(tmp_value); + Py_XDECREF(tmp_tb); + + /* For b/w compatibility */ + PySys_SetObject("exc_type", frame->f_exc_type); + PySys_SetObject("exc_value", frame->f_exc_value); + PySys_SetObject("exc_traceback", frame->f_exc_traceback); + + /* Clear the frame's exception info. */ + tmp_type = frame->f_exc_type; + tmp_value = frame->f_exc_value; + tmp_tb = frame->f_exc_traceback; + frame->f_exc_type = NULL; + frame->f_exc_value = NULL; + frame->f_exc_traceback = NULL; + Py_DECREF(tmp_type); + Py_XDECREF(tmp_value); + Py_XDECREF(tmp_tb); +} + +/* Logic for the raise statement (too complicated for inlining). + This *consumes* a reference count to each of its arguments. */ +static enum why_code +do_raise(PyObject *type, PyObject *value, PyObject *tb) +{ + if (type == NULL) { + /* Reraise */ + PyThreadState *tstate = PyThreadState_GET(); + type = tstate->exc_type == NULL ? Py_None : tstate->exc_type; + value = tstate->exc_value; + tb = tstate->exc_traceback; + Py_XINCREF(type); + Py_XINCREF(value); + Py_XINCREF(tb); + } + + /* We support the following forms of raise: + raise , + raise , + raise , None + raise , + raise , None + raise , + raise , None + + An omitted second argument is the same as None. + + In addition, raise , is the same as + raising the tuple's first item (and it better have one!); + this rule is applied recursively. + + Finally, an optional third argument can be supplied, which + gives the traceback to be substituted (useful when + re-raising an exception after examining it). */ + + /* First, check the traceback argument, replacing None with + NULL. */ + if (tb == Py_None) { + Py_DECREF(tb); + tb = NULL; + } + else if (tb != NULL && !PyTraceBack_Check(tb)) { + PyErr_SetString(PyExc_TypeError, + "raise: arg 3 must be a traceback or None"); + goto raise_error; + } + + /* Next, replace a missing value with None */ + if (value == NULL) { + value = Py_None; + Py_INCREF(value); + } + + /* Next, repeatedly, replace a tuple exception with its first item */ + while (PyTuple_Check(type) && PyTuple_Size(type) > 0) { + PyObject *tmp = type; + type = PyTuple_GET_ITEM(type, 0); + Py_INCREF(type); + Py_DECREF(tmp); + } + + if (PyExceptionClass_Check(type)) { + PyErr_NormalizeException(&type, &value, &tb); + if (!PyExceptionInstance_Check(value)) { + PyErr_Format(PyExc_TypeError, + "calling %s() should have returned an instance of " + "BaseException, not '%s'", + ((PyTypeObject *)type)->tp_name, + Py_TYPE(value)->tp_name); + goto raise_error; + } + } + else if (PyExceptionInstance_Check(type)) { + /* Raising an instance. The value should be a dummy. */ + if (value != Py_None) { + PyErr_SetString(PyExc_TypeError, + "instance exception may not have a separate value"); + goto raise_error; + } + else { + /* Normalize to raise , */ + Py_DECREF(value); + value = type; + type = PyExceptionInstance_Class(type); + Py_INCREF(type); + } + } + else { + /* Not something you can raise. You get an exception + anyway, just not what you specified :-) */ + PyErr_Format(PyExc_TypeError, + "exceptions must be old-style classes or " + "derived from BaseException, not %s", + type->ob_type->tp_name); + goto raise_error; + } + + assert(PyExceptionClass_Check(type)); + if (Py_Py3kWarningFlag && PyClass_Check(type)) { + if (PyErr_WarnEx(PyExc_DeprecationWarning, + "exceptions must derive from BaseException " + "in 3.x", 1) < 0) + goto raise_error; + } + + PyErr_Restore(type, value, tb); + if (tb == NULL) + return WHY_EXCEPTION; + else + return WHY_RERAISE; + raise_error: + Py_XDECREF(value); + Py_XDECREF(type); + Py_XDECREF(tb); + return WHY_EXCEPTION; +} + +/* Iterate v argcnt times and store the results on the stack (via decreasing + sp). Return 1 for success, 0 if error. */ + +static int +unpack_iterable(PyObject *v, int argcnt, PyObject **sp) +{ + int i = 0; + PyObject *it; /* iter(v) */ + PyObject *w; + + assert(v != NULL); + + it = PyObject_GetIter(v); + if (it == NULL) + goto Error; + + for (; i < argcnt; i++) { + w = PyIter_Next(it); + if (w == NULL) { + /* Iterator done, via error or exhaustion. */ + if (!PyErr_Occurred()) { + PyErr_Format(PyExc_ValueError, + "need more than %d value%s to unpack", + i, i == 1 ? "" : "s"); + } + goto Error; + } + *--sp = w; + } + + /* We better have exhausted the iterator now. */ + w = PyIter_Next(it); + if (w == NULL) { + if (PyErr_Occurred()) + goto Error; + Py_DECREF(it); + return 1; + } + Py_DECREF(w); + PyErr_SetString(PyExc_ValueError, "too many values to unpack"); + /* fall through */ +Error: + for (; i > 0; i--, sp++) + Py_DECREF(*sp); + Py_XDECREF(it); + return 0; +} + + +#ifdef LLTRACE +static int +prtrace(PyObject *v, char *str) +{ + printf("%s ", str); + if (PyObject_Print(v, stdout, 0) != 0) + PyErr_Clear(); /* Don't know what else to do */ + printf("\n"); + return 1; +} +#endif + +static void +call_exc_trace(Py_tracefunc func, PyObject *self, PyFrameObject *f) +{ + PyObject *type, *value, *traceback, *arg; + int err; + PyErr_Fetch(&type, &value, &traceback); + if (value == NULL) { + value = Py_None; + Py_INCREF(value); + } + arg = PyTuple_Pack(3, type, value, traceback); + if (arg == NULL) { + PyErr_Restore(type, value, traceback); + return; + } + err = call_trace(func, self, f, PyTrace_EXCEPTION, arg); + Py_DECREF(arg); + if (err == 0) + PyErr_Restore(type, value, traceback); + else { + Py_XDECREF(type); + Py_XDECREF(value); + Py_XDECREF(traceback); + } +} + +static int +call_trace_protected(Py_tracefunc func, PyObject *obj, PyFrameObject *frame, + int what, PyObject *arg) +{ + PyObject *type, *value, *traceback; + int err; + PyErr_Fetch(&type, &value, &traceback); + err = call_trace(func, obj, frame, what, arg); + if (err == 0) + { + PyErr_Restore(type, value, traceback); + return 0; + } + else { + Py_XDECREF(type); + Py_XDECREF(value); + Py_XDECREF(traceback); + return -1; + } +} + +static int +call_trace(Py_tracefunc func, PyObject *obj, PyFrameObject *frame, + int what, PyObject *arg) +{ + register PyThreadState *tstate = frame->f_tstate; + int result; + if (tstate->tracing) + return 0; + tstate->tracing++; + tstate->use_tracing = 0; + result = func(obj, frame, what, arg); + tstate->use_tracing = ((tstate->c_tracefunc != NULL) + || (tstate->c_profilefunc != NULL)); + tstate->tracing--; + return result; +} + +PyObject * +_PyEval_CallTracing(PyObject *func, PyObject *args) +{ + PyFrameObject *frame = PyEval_GetFrame(); + PyThreadState *tstate = frame->f_tstate; + int save_tracing = tstate->tracing; + int save_use_tracing = tstate->use_tracing; + PyObject *result; + + tstate->tracing = 0; + tstate->use_tracing = ((tstate->c_tracefunc != NULL) + || (tstate->c_profilefunc != NULL)); + result = PyObject_Call(func, args, NULL); + tstate->tracing = save_tracing; + tstate->use_tracing = save_use_tracing; + return result; +} + +/* See Objects/lnotab_notes.txt for a description of how tracing works. */ +static int +maybe_call_line_trace(Py_tracefunc func, PyObject *obj, + PyFrameObject *frame, int *instr_lb, int *instr_ub, + int *instr_prev) +{ + int result = 0; + int line = frame->f_lineno; + + /* If the last instruction executed isn't in the current + instruction window, reset the window. + */ + if (frame->f_lasti < *instr_lb || frame->f_lasti >= *instr_ub) { + PyAddrPair bounds; + line = _PyCode_CheckLineNumber(frame->f_code, frame->f_lasti, + &bounds); + *instr_lb = bounds.ap_lower; + *instr_ub = bounds.ap_upper; + } + /* If the last instruction falls at the start of a line or if + it represents a jump backwards, update the frame's line + number and call the trace function. */ + if (frame->f_lasti == *instr_lb || frame->f_lasti < *instr_prev) { + frame->f_lineno = line; + result = call_trace(func, obj, frame, PyTrace_LINE, Py_None); + } + *instr_prev = frame->f_lasti; + return result; +} + +void +PyEval_SetProfile(Py_tracefunc func, PyObject *arg) +{ + PyThreadState *tstate = PyThreadState_GET(); + PyObject *temp = tstate->c_profileobj; + Py_XINCREF(arg); + tstate->c_profilefunc = NULL; + tstate->c_profileobj = NULL; + /* Must make sure that tracing is not ignored if 'temp' is freed */ + tstate->use_tracing = tstate->c_tracefunc != NULL; + Py_XDECREF(temp); + tstate->c_profilefunc = func; + tstate->c_profileobj = arg; + /* Flag that tracing or profiling is turned on */ + tstate->use_tracing = (func != NULL) || (tstate->c_tracefunc != NULL); +} + +void +PyEval_SetTrace(Py_tracefunc func, PyObject *arg) +{ + PyThreadState *tstate = PyThreadState_GET(); + PyObject *temp = tstate->c_traceobj; + _Py_TracingPossible += (func != NULL) - (tstate->c_tracefunc != NULL); + Py_XINCREF(arg); + tstate->c_tracefunc = NULL; + tstate->c_traceobj = NULL; + /* Must make sure that profiling is not ignored if 'temp' is freed */ + tstate->use_tracing = tstate->c_profilefunc != NULL; + Py_XDECREF(temp); + tstate->c_tracefunc = func; + tstate->c_traceobj = arg; + /* Flag that tracing or profiling is turned on */ + tstate->use_tracing = ((func != NULL) + || (tstate->c_profilefunc != NULL)); +} + +PyObject * +PyEval_GetBuiltins(void) +{ + PyFrameObject *current_frame = PyEval_GetFrame(); + if (current_frame == NULL) + return PyThreadState_GET()->interp->builtins; + else + return current_frame->f_builtins; +} + +PyObject * +PyEval_GetLocals(void) +{ + PyFrameObject *current_frame = PyEval_GetFrame(); + if (current_frame == NULL) + return NULL; + PyFrame_FastToLocals(current_frame); + return current_frame->f_locals; +} + +PyObject * +PyEval_GetGlobals(void) +{ + PyFrameObject *current_frame = PyEval_GetFrame(); + if (current_frame == NULL) + return NULL; + else + return current_frame->f_globals; +} + +PyFrameObject * +PyEval_GetFrame(void) +{ + PyThreadState *tstate = PyThreadState_GET(); + return _PyThreadState_GetFrame(tstate); +} + +int +PyEval_GetRestricted(void) +{ + PyFrameObject *current_frame = PyEval_GetFrame(); + return current_frame == NULL ? 0 : PyFrame_IsRestricted(current_frame); +} + +int +PyEval_MergeCompilerFlags(PyCompilerFlags *cf) +{ + PyFrameObject *current_frame = PyEval_GetFrame(); + int result = cf->cf_flags != 0; + + if (current_frame != NULL) { + const int codeflags = current_frame->f_code->co_flags; + const int compilerflags = codeflags & PyCF_MASK; + if (compilerflags) { + result = 1; + cf->cf_flags |= compilerflags; + } +#if 0 /* future keyword */ + if (codeflags & CO_GENERATOR_ALLOWED) { + result = 1; + cf->cf_flags |= CO_GENERATOR_ALLOWED; + } +#endif + } + return result; +} + +int +Py_FlushLine(void) +{ + PyObject *f = PySys_GetObject("stdout"); + if (f == NULL) + return 0; + if (!PyFile_SoftSpace(f, 0)) + return 0; + return PyFile_WriteString("\n", f); +} + + +/* External interface to call any callable object. + The arg must be a tuple or NULL. The kw must be a dict or NULL. */ + +PyObject * +PyEval_CallObjectWithKeywords(PyObject *func, PyObject *arg, PyObject *kw) +{ + PyObject *result; + + if (arg == NULL) { + arg = PyTuple_New(0); + if (arg == NULL) + return NULL; + } + else if (!PyTuple_Check(arg)) { + PyErr_SetString(PyExc_TypeError, + "argument list must be a tuple"); + return NULL; + } + else + Py_INCREF(arg); + + if (kw != NULL && !PyDict_Check(kw)) { + PyErr_SetString(PyExc_TypeError, + "keyword list must be a dictionary"); + Py_DECREF(arg); + return NULL; + } + + result = PyObject_Call(func, arg, kw); + Py_DECREF(arg); + return result; +} + +const char * +PyEval_GetFuncName(PyObject *func) +{ + if (PyMethod_Check(func)) + return PyEval_GetFuncName(PyMethod_GET_FUNCTION(func)); + else if (PyFunction_Check(func)) + return PyString_AsString(((PyFunctionObject*)func)->func_name); + else if (PyCFunction_Check(func)) + return ((PyCFunctionObject*)func)->m_ml->ml_name; + else if (PyClass_Check(func)) + return PyString_AsString(((PyClassObject*)func)->cl_name); + else if (PyInstance_Check(func)) { + return PyString_AsString( + ((PyInstanceObject*)func)->in_class->cl_name); + } else { + return func->ob_type->tp_name; + } +} + +const char * +PyEval_GetFuncDesc(PyObject *func) +{ + if (PyMethod_Check(func)) + return "()"; + else if (PyFunction_Check(func)) + return "()"; + else if (PyCFunction_Check(func)) + return "()"; + else if (PyClass_Check(func)) + return " constructor"; + else if (PyInstance_Check(func)) { + return " instance"; + } else { + return " object"; + } +} + +static void +err_args(PyObject *func, int flags, int nargs) +{ + if (flags & METH_NOARGS) + PyErr_Format(PyExc_TypeError, + "%.200s() takes no arguments (%d given)", + ((PyCFunctionObject *)func)->m_ml->ml_name, + nargs); + else + PyErr_Format(PyExc_TypeError, + "%.200s() takes exactly one argument (%d given)", + ((PyCFunctionObject *)func)->m_ml->ml_name, + nargs); +} + +#define C_TRACE(x, call) \ +if (tstate->use_tracing && tstate->c_profilefunc) { \ + if (call_trace(tstate->c_profilefunc, \ + tstate->c_profileobj, \ + tstate->frame, PyTrace_C_CALL, \ + func)) { \ + x = NULL; \ + } \ + else { \ + x = call; \ + if (tstate->c_profilefunc != NULL) { \ + if (x == NULL) { \ + call_trace_protected(tstate->c_profilefunc, \ + tstate->c_profileobj, \ + tstate->frame, PyTrace_C_EXCEPTION, \ + func); \ + /* XXX should pass (type, value, tb) */ \ + } else { \ + if (call_trace(tstate->c_profilefunc, \ + tstate->c_profileobj, \ + tstate->frame, PyTrace_C_RETURN, \ + func)) { \ + Py_DECREF(x); \ + x = NULL; \ + } \ + } \ + } \ + } \ +} else { \ + x = call; \ + } + +static PyObject * +call_function(PyObject ***pp_stack, int oparg +#ifdef WITH_TSC + , uint64* pintr0, uint64* pintr1 +#endif + ) +{ + int na = oparg & 0xff; + int nk = (oparg>>8) & 0xff; + int n = na + 2 * nk; + PyObject **pfunc = (*pp_stack) - n - 1; + PyObject *func = *pfunc; + PyObject *x, *w; + + /* Always dispatch PyCFunction first, because these are + presumed to be the most frequent callable object. + */ + if (PyCFunction_Check(func) && nk == 0) { + int flags = PyCFunction_GET_FLAGS(func); + PyThreadState *tstate = PyThreadState_GET(); + + PCALL(PCALL_CFUNCTION); + if (flags & (METH_NOARGS | METH_O)) { + PyCFunction meth = PyCFunction_GET_FUNCTION(func); + PyObject *self = PyCFunction_GET_SELF(func); + if (flags & METH_NOARGS && na == 0) { + C_TRACE(x, (*meth)(self,NULL)); + } + else if (flags & METH_O && na == 1) { + PyObject *arg = EXT_POP(*pp_stack); + C_TRACE(x, (*meth)(self,arg)); + Py_DECREF(arg); + } + else { + err_args(func, flags, na); + x = NULL; + } + } + else { + PyObject *callargs; + callargs = load_args(pp_stack, na); + READ_TIMESTAMP(*pintr0); + C_TRACE(x, PyCFunction_Call(func,callargs,NULL)); + READ_TIMESTAMP(*pintr1); + Py_XDECREF(callargs); + } + } else { + if (PyMethod_Check(func) && PyMethod_GET_SELF(func) != NULL) { + /* optimize access to bound methods */ + PyObject *self = PyMethod_GET_SELF(func); + PCALL(PCALL_METHOD); + PCALL(PCALL_BOUND_METHOD); + Py_INCREF(self); + func = PyMethod_GET_FUNCTION(func); + Py_INCREF(func); + Py_DECREF(*pfunc); + *pfunc = self; + na++; + n++; + } else + Py_INCREF(func); + READ_TIMESTAMP(*pintr0); + if (PyFunction_Check(func)) + x = fast_function(func, pp_stack, n, na, nk); + else + x = do_call(func, pp_stack, na, nk); + READ_TIMESTAMP(*pintr1); + Py_DECREF(func); + } + + /* Clear the stack of the function object. Also removes + the arguments in case they weren't consumed already + (fast_function() and err_args() leave them on the stack). + */ + while ((*pp_stack) > pfunc) { + w = EXT_POP(*pp_stack); + Py_DECREF(w); + PCALL(PCALL_POP); + } + return x; +} + +/* The fast_function() function optimize calls for which no argument + tuple is necessary; the objects are passed directly from the stack. + For the simplest case -- a function that takes only positional + arguments and is called with only positional arguments -- it + inlines the most primitive frame setup code from + PyEval_EvalCodeEx(), which vastly reduces the checks that must be + done before evaluating the frame. +*/ + +static PyObject * +fast_function(PyObject *func, PyObject ***pp_stack, int n, int na, int nk) +{ + PyCodeObject *co = (PyCodeObject *)PyFunction_GET_CODE(func); + PyObject *globals = PyFunction_GET_GLOBALS(func); + PyObject *argdefs = PyFunction_GET_DEFAULTS(func); + PyObject **d = NULL; + int nd = 0; + + PCALL(PCALL_FUNCTION); + PCALL(PCALL_FAST_FUNCTION); + if (argdefs == NULL && co->co_argcount == n && nk==0 && + co->co_flags == (CO_OPTIMIZED | CO_NEWLOCALS | CO_NOFREE)) { + PyFrameObject *f; + PyObject *retval = NULL; + PyThreadState *tstate = PyThreadState_GET(); + PyObject **fastlocals, **stack; + int i; + + PCALL(PCALL_FASTER_FUNCTION); + assert(globals != NULL); + /* XXX Perhaps we should create a specialized + PyFrame_New() that doesn't take locals, but does + take builtins without sanity checking them. + */ + assert(tstate != NULL); + f = PyFrame_New(tstate, co, globals, NULL); + if (f == NULL) + return NULL; + + fastlocals = f->f_localsplus; + stack = (*pp_stack) - n; + + for (i = 0; i < n; i++) { + Py_INCREF(*stack); + fastlocals[i] = *stack++; + } + retval = PyEval_EvalFrameEx(f,0); + ++tstate->recursion_depth; + Py_DECREF(f); + --tstate->recursion_depth; + return retval; + } + if (argdefs != NULL) { + d = &PyTuple_GET_ITEM(argdefs, 0); + nd = Py_SIZE(argdefs); + } + return PyEval_EvalCodeEx(co, globals, + (PyObject *)NULL, (*pp_stack)-n, na, + (*pp_stack)-2*nk, nk, d, nd, + PyFunction_GET_CLOSURE(func)); +} + +static PyObject * +update_keyword_args(PyObject *orig_kwdict, int nk, PyObject ***pp_stack, + PyObject *func) +{ + PyObject *kwdict = NULL; + if (orig_kwdict == NULL) + kwdict = PyDict_New(); + else { + kwdict = PyDict_Copy(orig_kwdict); + Py_DECREF(orig_kwdict); + } + if (kwdict == NULL) + return NULL; + while (--nk >= 0) { + int err; + PyObject *value = EXT_POP(*pp_stack); + PyObject *key = EXT_POP(*pp_stack); + if (PyDict_GetItem(kwdict, key) != NULL) { + PyErr_Format(PyExc_TypeError, + "%.200s%s got multiple values " + "for keyword argument '%.200s'", + PyEval_GetFuncName(func), + PyEval_GetFuncDesc(func), + PyString_AsString(key)); + Py_DECREF(key); + Py_DECREF(value); + Py_DECREF(kwdict); + return NULL; + } + err = PyDict_SetItem(kwdict, key, value); + Py_DECREF(key); + Py_DECREF(value); + if (err) { + Py_DECREF(kwdict); + return NULL; + } + } + return kwdict; +} + +static PyObject * +update_star_args(int nstack, int nstar, PyObject *stararg, + PyObject ***pp_stack) +{ + PyObject *callargs, *w; + + callargs = PyTuple_New(nstack + nstar); + if (callargs == NULL) { + return NULL; + } + if (nstar) { + int i; + for (i = 0; i < nstar; i++) { + PyObject *a = PyTuple_GET_ITEM(stararg, i); + Py_INCREF(a); + PyTuple_SET_ITEM(callargs, nstack + i, a); + } + } + while (--nstack >= 0) { + w = EXT_POP(*pp_stack); + PyTuple_SET_ITEM(callargs, nstack, w); + } + return callargs; +} + +static PyObject * +load_args(PyObject ***pp_stack, int na) +{ + PyObject *args = PyTuple_New(na); + PyObject *w; + + if (args == NULL) + return NULL; + while (--na >= 0) { + w = EXT_POP(*pp_stack); + PyTuple_SET_ITEM(args, na, w); + } + return args; +} + +static PyObject * +do_call(PyObject *func, PyObject ***pp_stack, int na, int nk) +{ + PyObject *callargs = NULL; + PyObject *kwdict = NULL; + PyObject *result = NULL; + + if (nk > 0) { + kwdict = update_keyword_args(NULL, nk, pp_stack, func); + if (kwdict == NULL) + goto call_fail; + } + callargs = load_args(pp_stack, na); + if (callargs == NULL) + goto call_fail; +#ifdef CALL_PROFILE + /* At this point, we have to look at the type of func to + update the call stats properly. Do it here so as to avoid + exposing the call stats machinery outside ceval.c + */ + if (PyFunction_Check(func)) + PCALL(PCALL_FUNCTION); + else if (PyMethod_Check(func)) + PCALL(PCALL_METHOD); + else if (PyType_Check(func)) + PCALL(PCALL_TYPE); + else if (PyCFunction_Check(func)) + PCALL(PCALL_CFUNCTION); + else + PCALL(PCALL_OTHER); +#endif + if (PyCFunction_Check(func)) { + PyThreadState *tstate = PyThreadState_GET(); + C_TRACE(result, PyCFunction_Call(func, callargs, kwdict)); + } + else + result = PyObject_Call(func, callargs, kwdict); + call_fail: + Py_XDECREF(callargs); + Py_XDECREF(kwdict); + return result; +} + +static PyObject * +ext_do_call(PyObject *func, PyObject ***pp_stack, int flags, int na, int nk) +{ + int nstar = 0; + PyObject *callargs = NULL; + PyObject *stararg = NULL; + PyObject *kwdict = NULL; + PyObject *result = NULL; + + if (flags & CALL_FLAG_KW) { + kwdict = EXT_POP(*pp_stack); + if (!PyDict_Check(kwdict)) { + PyObject *d; + d = PyDict_New(); + if (d == NULL) + goto ext_call_fail; + if (PyDict_Update(d, kwdict) != 0) { + Py_DECREF(d); + /* PyDict_Update raises attribute + * error (percolated from an attempt + * to get 'keys' attribute) instead of + * a type error if its second argument + * is not a mapping. + */ + if (PyErr_ExceptionMatches(PyExc_AttributeError)) { + PyErr_Format(PyExc_TypeError, + "%.200s%.200s argument after ** " + "must be a mapping, not %.200s", + PyEval_GetFuncName(func), + PyEval_GetFuncDesc(func), + kwdict->ob_type->tp_name); + } + goto ext_call_fail; + } + Py_DECREF(kwdict); + kwdict = d; + } + } + if (flags & CALL_FLAG_VAR) { + stararg = EXT_POP(*pp_stack); + if (!PyTuple_Check(stararg)) { + PyObject *t = NULL; + t = PySequence_Tuple(stararg); + if (t == NULL) { + if (PyErr_ExceptionMatches(PyExc_TypeError)) { + PyErr_Format(PyExc_TypeError, + "%.200s%.200s argument after * " + "must be a sequence, not %200s", + PyEval_GetFuncName(func), + PyEval_GetFuncDesc(func), + stararg->ob_type->tp_name); + } + goto ext_call_fail; + } + Py_DECREF(stararg); + stararg = t; + } + nstar = PyTuple_GET_SIZE(stararg); + } + if (nk > 0) { + kwdict = update_keyword_args(kwdict, nk, pp_stack, func); + if (kwdict == NULL) + goto ext_call_fail; + } + callargs = update_star_args(na, nstar, stararg, pp_stack); + if (callargs == NULL) + goto ext_call_fail; +#ifdef CALL_PROFILE + /* At this point, we have to look at the type of func to + update the call stats properly. Do it here so as to avoid + exposing the call stats machinery outside ceval.c + */ + if (PyFunction_Check(func)) + PCALL(PCALL_FUNCTION); + else if (PyMethod_Check(func)) + PCALL(PCALL_METHOD); + else if (PyType_Check(func)) + PCALL(PCALL_TYPE); + else if (PyCFunction_Check(func)) + PCALL(PCALL_CFUNCTION); + else + PCALL(PCALL_OTHER); +#endif + if (PyCFunction_Check(func)) { + PyThreadState *tstate = PyThreadState_GET(); + C_TRACE(result, PyCFunction_Call(func, callargs, kwdict)); + } + else + result = PyObject_Call(func, callargs, kwdict); +ext_call_fail: + Py_XDECREF(callargs); + Py_XDECREF(kwdict); + Py_XDECREF(stararg); + return result; +} + +/* Extract a slice index from a PyInt or PyLong or an object with the + nb_index slot defined, and store in *pi. + Silently reduce values larger than PY_SSIZE_T_MAX to PY_SSIZE_T_MAX, + and silently boost values less than -PY_SSIZE_T_MAX-1 to -PY_SSIZE_T_MAX-1. + Return 0 on error, 1 on success. +*/ +/* Note: If v is NULL, return success without storing into *pi. This + is because_PyEval_SliceIndex() is called by apply_slice(), which can be + called by the SLICE opcode with v and/or w equal to NULL. +*/ +int +_PyEval_SliceIndex(PyObject *v, Py_ssize_t *pi) +{ + if (v != NULL) { + Py_ssize_t x; + if (PyInt_Check(v)) { + /* XXX(nnorwitz): I think PyInt_AS_LONG is correct, + however, it looks like it should be AsSsize_t. + There should be a comment here explaining why. + */ + x = PyInt_AS_LONG(v); + } + else if (PyIndex_Check(v)) { + x = PyNumber_AsSsize_t(v, NULL); + if (x == -1 && PyErr_Occurred()) + return 0; + } + else { + PyErr_SetString(PyExc_TypeError, + "slice indices must be integers or " + "None or have an __index__ method"); + return 0; + } + *pi = x; + } + return 1; +} + +#undef ISINDEX +#define ISINDEX(x) ((x) == NULL || \ + PyInt_Check(x) || PyLong_Check(x) || PyIndex_Check(x)) + +static PyObject * +apply_slice(PyObject *u, PyObject *v, PyObject *w) /* return u[v:w] */ +{ + PyTypeObject *tp = u->ob_type; + PySequenceMethods *sq = tp->tp_as_sequence; + + if (sq && sq->sq_slice && ISINDEX(v) && ISINDEX(w)) { + Py_ssize_t ilow = 0, ihigh = PY_SSIZE_T_MAX; + if (!_PyEval_SliceIndex(v, &ilow)) + return NULL; + if (!_PyEval_SliceIndex(w, &ihigh)) + return NULL; + return PySequence_GetSlice(u, ilow, ihigh); + } + else { + PyObject *slice = PySlice_New(v, w, NULL); + if (slice != NULL) { + PyObject *res = PyObject_GetItem(u, slice); + Py_DECREF(slice); + return res; + } + else + return NULL; + } +} + +static int +assign_slice(PyObject *u, PyObject *v, PyObject *w, PyObject *x) + /* u[v:w] = x */ +{ + PyTypeObject *tp = u->ob_type; + PySequenceMethods *sq = tp->tp_as_sequence; + + if (sq && sq->sq_ass_slice && ISINDEX(v) && ISINDEX(w)) { + Py_ssize_t ilow = 0, ihigh = PY_SSIZE_T_MAX; + if (!_PyEval_SliceIndex(v, &ilow)) + return -1; + if (!_PyEval_SliceIndex(w, &ihigh)) + return -1; + if (x == NULL) + return PySequence_DelSlice(u, ilow, ihigh); + else + return PySequence_SetSlice(u, ilow, ihigh, x); + } + else { + PyObject *slice = PySlice_New(v, w, NULL); + if (slice != NULL) { + int res; + if (x != NULL) + res = PyObject_SetItem(u, slice, x); + else + res = PyObject_DelItem(u, slice); + Py_DECREF(slice); + return res; + } + else + return -1; + } +} + +#define Py3kExceptionClass_Check(x) \ + (PyType_Check((x)) && \ + PyType_FastSubclass((PyTypeObject*)(x), Py_TPFLAGS_BASE_EXC_SUBCLASS)) + +#define CANNOT_CATCH_MSG "catching classes that don't inherit from " \ + "BaseException is not allowed in 3.x" + +static PyObject * +cmp_outcome(int op, register PyObject *v, register PyObject *w) +{ + int res = 0; + switch (op) { + case PyCmp_IS: + res = (v == w); + break; + case PyCmp_IS_NOT: + res = (v != w); + break; + case PyCmp_IN: + res = PySequence_Contains(w, v); + if (res < 0) + return NULL; + break; + case PyCmp_NOT_IN: + res = PySequence_Contains(w, v); + if (res < 0) + return NULL; + res = !res; + break; + case PyCmp_EXC_MATCH: + if (PyTuple_Check(w)) { + Py_ssize_t i, length; + length = PyTuple_Size(w); + for (i = 0; i < length; i += 1) { + PyObject *exc = PyTuple_GET_ITEM(w, i); + if (PyString_Check(exc)) { + int ret_val; + ret_val = PyErr_WarnEx( + PyExc_DeprecationWarning, + "catching of string " + "exceptions is deprecated", 1); + if (ret_val < 0) + return NULL; + } + else if (Py_Py3kWarningFlag && + !PyTuple_Check(exc) && + !Py3kExceptionClass_Check(exc)) + { + int ret_val; + ret_val = PyErr_WarnEx( + PyExc_DeprecationWarning, + CANNOT_CATCH_MSG, 1); + if (ret_val < 0) + return NULL; + } + } + } + else { + if (PyString_Check(w)) { + int ret_val; + ret_val = PyErr_WarnEx( + PyExc_DeprecationWarning, + "catching of string " + "exceptions is deprecated", 1); + if (ret_val < 0) + return NULL; + } + else if (Py_Py3kWarningFlag && + !PyTuple_Check(w) && + !Py3kExceptionClass_Check(w)) + { + int ret_val; + ret_val = PyErr_WarnEx( + PyExc_DeprecationWarning, + CANNOT_CATCH_MSG, 1); + if (ret_val < 0) + return NULL; + } + } + res = PyErr_GivenExceptionMatches(v, w); + break; + default: + return PyObject_RichCompare(v, w, op); + } + v = res ? Py_True : Py_False; + Py_INCREF(v); + return v; +} + +static PyObject * +import_from(PyObject *v, PyObject *name) +{ + PyObject *x; + + x = PyObject_GetAttr(v, name); + if (x == NULL && PyErr_ExceptionMatches(PyExc_AttributeError)) { + PyErr_Format(PyExc_ImportError, + "cannot import name %.230s", + PyString_AsString(name)); + } + return x; +} + +static int +import_all_from(PyObject *locals, PyObject *v) +{ + PyObject *all = PyObject_GetAttrString(v, "__all__"); + PyObject *dict, *name, *value; + int skip_leading_underscores = 0; + int pos, err; + + if (all == NULL) { + if (!PyErr_ExceptionMatches(PyExc_AttributeError)) + return -1; /* Unexpected error */ + PyErr_Clear(); + dict = PyObject_GetAttrString(v, "__dict__"); + if (dict == NULL) { + if (!PyErr_ExceptionMatches(PyExc_AttributeError)) + return -1; + PyErr_SetString(PyExc_ImportError, + "from-import-* object has no __dict__ and no __all__"); + return -1; + } + all = PyMapping_Keys(dict); + Py_DECREF(dict); + if (all == NULL) + return -1; + skip_leading_underscores = 1; + } + + for (pos = 0, err = 0; ; pos++) { + name = PySequence_GetItem(all, pos); + if (name == NULL) { + if (!PyErr_ExceptionMatches(PyExc_IndexError)) + err = -1; + else + PyErr_Clear(); + break; + } + if (skip_leading_underscores && + PyString_Check(name) && + PyString_AS_STRING(name)[0] == '_') + { + Py_DECREF(name); + continue; + } + value = PyObject_GetAttr(v, name); + if (value == NULL) + err = -1; + else if (PyDict_CheckExact(locals)) + err = PyDict_SetItem(locals, name, value); + else + err = PyObject_SetItem(locals, name, value); + Py_DECREF(name); + Py_XDECREF(value); + if (err != 0) + break; + } + Py_DECREF(all); + return err; +} + +static PyObject * +build_class(PyObject *methods, PyObject *bases, PyObject *name) +{ + PyObject *metaclass = NULL, *result, *base; + + if (PyDict_Check(methods)) + metaclass = PyDict_GetItemString(methods, "__metaclass__"); + if (metaclass != NULL) + Py_INCREF(metaclass); + else if (PyTuple_Check(bases) && PyTuple_GET_SIZE(bases) > 0) { + base = PyTuple_GET_ITEM(bases, 0); + metaclass = PyObject_GetAttrString(base, "__class__"); + if (metaclass == NULL) { + PyErr_Clear(); + metaclass = (PyObject *)base->ob_type; + Py_INCREF(metaclass); + } + } + else { + PyObject *g = PyEval_GetGlobals(); + if (g != NULL && PyDict_Check(g)) + metaclass = PyDict_GetItemString(g, "__metaclass__"); + if (metaclass == NULL) + metaclass = (PyObject *) &PyClass_Type; + Py_INCREF(metaclass); + } + result = PyObject_CallFunctionObjArgs(metaclass, name, bases, methods, + NULL); + Py_DECREF(metaclass); + if (result == NULL && PyErr_ExceptionMatches(PyExc_TypeError)) { + /* A type error here likely means that the user passed + in a base that was not a class (such the random module + instead of the random.random type). Help them out with + by augmenting the error message with more information.*/ + + PyObject *ptype, *pvalue, *ptraceback; + + PyErr_Fetch(&ptype, &pvalue, &ptraceback); + if (PyString_Check(pvalue)) { + PyObject *newmsg; + newmsg = PyString_FromFormat( + "Error when calling the metaclass bases\n" + " %s", + PyString_AS_STRING(pvalue)); + if (newmsg != NULL) { + Py_DECREF(pvalue); + pvalue = newmsg; + } + } + PyErr_Restore(ptype, pvalue, ptraceback); + } + return result; +} + +static int +exec_statement(PyFrameObject *f, PyObject *prog, PyObject *globals, + PyObject *locals) +{ + int n; + PyObject *v; + int plain = 0; + + if (PyTuple_Check(prog) && globals == Py_None && locals == Py_None && + ((n = PyTuple_Size(prog)) == 2 || n == 3)) { + /* Backward compatibility hack */ + globals = PyTuple_GetItem(prog, 1); + if (n == 3) + locals = PyTuple_GetItem(prog, 2); + prog = PyTuple_GetItem(prog, 0); + } + if (globals == Py_None) { + globals = PyEval_GetGlobals(); + if (locals == Py_None) { + locals = PyEval_GetLocals(); + plain = 1; + } + if (!globals || !locals) { + PyErr_SetString(PyExc_SystemError, + "globals and locals cannot be NULL"); + return -1; + } + } + else if (locals == Py_None) + locals = globals; + if (!PyString_Check(prog) && +#ifdef Py_USING_UNICODE + !PyUnicode_Check(prog) && +#endif + !PyCode_Check(prog) && + !PyFile_Check(prog)) { + PyErr_SetString(PyExc_TypeError, + "exec: arg 1 must be a string, file, or code object"); + return -1; + } + if (!PyDict_Check(globals)) { + PyErr_SetString(PyExc_TypeError, + "exec: arg 2 must be a dictionary or None"); + return -1; + } + if (!PyMapping_Check(locals)) { + PyErr_SetString(PyExc_TypeError, + "exec: arg 3 must be a mapping or None"); + return -1; + } + if (PyDict_GetItemString(globals, "__builtins__") == NULL) + PyDict_SetItemString(globals, "__builtins__", f->f_builtins); + if (PyCode_Check(prog)) { + if (PyCode_GetNumFree((PyCodeObject *)prog) > 0) { + PyErr_SetString(PyExc_TypeError, + "code object passed to exec may not contain free variables"); + return -1; + } + v = PyEval_EvalCode((PyCodeObject *) prog, globals, locals); + } + else if (PyFile_Check(prog)) { + FILE *fp = PyFile_AsFile(prog); + char *name = PyString_AsString(PyFile_Name(prog)); + PyCompilerFlags cf; + if (name == NULL) + return -1; + cf.cf_flags = 0; + if (PyEval_MergeCompilerFlags(&cf)) + v = PyRun_FileFlags(fp, name, Py_file_input, globals, + locals, &cf); + else + v = PyRun_File(fp, name, Py_file_input, globals, + locals); + } + else { + PyObject *tmp = NULL; + char *str; + PyCompilerFlags cf; + cf.cf_flags = 0; +#ifdef Py_USING_UNICODE + if (PyUnicode_Check(prog)) { + tmp = PyUnicode_AsUTF8String(prog); + if (tmp == NULL) + return -1; + prog = tmp; + cf.cf_flags |= PyCF_SOURCE_IS_UTF8; + } +#endif + if (PyString_AsStringAndSize(prog, &str, NULL)) + return -1; + if (PyEval_MergeCompilerFlags(&cf)) + v = PyRun_StringFlags(str, Py_file_input, globals, + locals, &cf); + else + v = PyRun_String(str, Py_file_input, globals, locals); + Py_XDECREF(tmp); + } + if (plain) + PyFrame_LocalsToFast(f, 0); + if (v == NULL) + return -1; + Py_DECREF(v); + return 0; +} + +static void +format_exc_check_arg(PyObject *exc, char *format_str, PyObject *obj) +{ + char *obj_str; + + if (!obj) + return; + + obj_str = PyString_AsString(obj); + if (!obj_str) + return; + + PyErr_Format(exc, format_str, obj_str); +} + +static PyObject * +string_concatenate(PyObject *v, PyObject *w, + PyFrameObject *f, unsigned char *next_instr) +{ + /* This function implements 'variable += expr' when both arguments + are strings. */ + Py_ssize_t v_len = PyString_GET_SIZE(v); + Py_ssize_t w_len = PyString_GET_SIZE(w); + Py_ssize_t new_len = v_len + w_len; + if (new_len < 0) { + PyErr_SetString(PyExc_OverflowError, + "strings are too large to concat"); + return NULL; + } + + if (v->ob_refcnt == 2) { + /* In the common case, there are 2 references to the value + * stored in 'variable' when the += is performed: one on the + * value stack (in 'v') and one still stored in the + * 'variable'. We try to delete the variable now to reduce + * the refcnt to 1. + */ + switch (*next_instr) { + case STORE_FAST: + { + int oparg = PEEKARG(); + PyObject **fastlocals = f->f_localsplus; + if (GETLOCAL(oparg) == v) + SETLOCAL(oparg, NULL); + break; + } + case STORE_DEREF: + { + PyObject **freevars = (f->f_localsplus + + f->f_code->co_nlocals); + PyObject *c = freevars[PEEKARG()]; + if (PyCell_GET(c) == v) + PyCell_Set(c, NULL); + break; + } + case STORE_NAME: + { + PyObject *names = f->f_code->co_names; + PyObject *name = GETITEM(names, PEEKARG()); + PyObject *locals = f->f_locals; + if (PyDict_CheckExact(locals) && + PyDict_GetItem(locals, name) == v) { + if (PyDict_DelItem(locals, name) != 0) { + PyErr_Clear(); + } + } + break; + } + } + } + + if (v->ob_refcnt == 1 && !PyString_CHECK_INTERNED(v)) { + /* Now we own the last reference to 'v', so we can resize it + * in-place. + */ + if (_PyString_Resize(&v, new_len) != 0) { + /* XXX if _PyString_Resize() fails, 'v' has been + * deallocated so it cannot be put back into + * 'variable'. The MemoryError is raised when there + * is no value in 'variable', which might (very + * remotely) be a cause of incompatibilities. + */ + return NULL; + } + /* copy 'w' into the newly allocated area of 'v' */ + memcpy(PyString_AS_STRING(v) + v_len, + PyString_AS_STRING(w), w_len); + return v; + } + else { + /* When in-place resizing is not an option. */ + PyString_Concat(&v, w); + return v; + } +} + +#ifdef DYNAMIC_EXECUTION_PROFILE + +static PyObject * +getarray(long a[256]) +{ + int i; + PyObject *l = PyList_New(256); + if (l == NULL) return NULL; + for (i = 0; i < 256; i++) { + PyObject *x = PyInt_FromLong(a[i]); + if (x == NULL) { + Py_DECREF(l); + return NULL; + } + PyList_SetItem(l, i, x); + } + for (i = 0; i < 256; i++) + a[i] = 0; + return l; +} + +PyObject * +_Py_GetDXProfile(PyObject *self, PyObject *args) +{ +#ifndef DXPAIRS + return getarray(dxp); +#else + int i; + PyObject *l = PyList_New(257); + if (l == NULL) return NULL; + for (i = 0; i < 257; i++) { + PyObject *x = getarray(dxpairs[i]); + if (x == NULL) { + Py_DECREF(l); + return NULL; + } + PyList_SetItem(l, i, x); + } + return l; +#endif +} + +#endif diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/codecs.c b/AppPkg/Applications/Python/Python-2.7.10/Python/codecs.c new file mode 100644 index 0000000000..8de5129f26 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/codecs.c @@ -0,0 +1,889 @@ +/* ------------------------------------------------------------------------ + + Python Codec Registry and support functions + +Written by Marc-Andre Lemburg (mal@lemburg.com). + +Copyright (c) Corporation for National Research Initiatives. + + ------------------------------------------------------------------------ */ + +#include "Python.h" +#include + +/* --- Codec Registry ----------------------------------------------------- */ + +/* Import the standard encodings package which will register the first + codec search function. + + This is done in a lazy way so that the Unicode implementation does + not downgrade startup time of scripts not needing it. + + ImportErrors are silently ignored by this function. Only one try is + made. + +*/ + +static int _PyCodecRegistry_Init(void); /* Forward */ + +int PyCodec_Register(PyObject *search_function) +{ + PyInterpreterState *interp = PyThreadState_GET()->interp; + if (interp->codec_search_path == NULL && _PyCodecRegistry_Init()) + goto onError; + if (search_function == NULL) { + PyErr_BadArgument(); + goto onError; + } + if (!PyCallable_Check(search_function)) { + PyErr_SetString(PyExc_TypeError, "argument must be callable"); + goto onError; + } + return PyList_Append(interp->codec_search_path, search_function); + + onError: + return -1; +} + +/* Convert a string to a normalized Python string: all characters are + converted to lower case, spaces are replaced with underscores. */ + +static +PyObject *normalizestring(const char *string) +{ + register size_t i; + size_t len = strlen(string); + char *p; + PyObject *v; + + if (len > PY_SSIZE_T_MAX) { + PyErr_SetString(PyExc_OverflowError, "string is too large"); + return NULL; + } + + v = PyString_FromStringAndSize(NULL, len); + if (v == NULL) + return NULL; + p = PyString_AS_STRING(v); + for (i = 0; i < len; i++) { + register char ch = string[i]; + if (ch == ' ') + ch = '-'; + else + ch = Py_TOLOWER(Py_CHARMASK(ch)); + p[i] = ch; + } + return v; +} + +/* Lookup the given encoding and return a tuple providing the codec + facilities. + + The encoding string is looked up converted to all lower-case + characters. This makes encodings looked up through this mechanism + effectively case-insensitive. + + If no codec is found, a LookupError is set and NULL returned. + + As side effect, this tries to load the encodings package, if not + yet done. This is part of the lazy load strategy for the encodings + package. + +*/ + +PyObject *_PyCodec_Lookup(const char *encoding) +{ + PyInterpreterState *interp; + PyObject *result, *args = NULL, *v; + Py_ssize_t i, len; + + if (encoding == NULL) { + PyErr_BadArgument(); + goto onError; + } + + interp = PyThreadState_GET()->interp; + if (interp->codec_search_path == NULL && _PyCodecRegistry_Init()) + goto onError; + + /* Convert the encoding to a normalized Python string: all + characters are converted to lower case, spaces and hyphens are + replaced with underscores. */ + v = normalizestring(encoding); + if (v == NULL) + goto onError; + PyString_InternInPlace(&v); + + /* First, try to lookup the name in the registry dictionary */ + result = PyDict_GetItem(interp->codec_search_cache, v); + if (result != NULL) { + Py_INCREF(result); + Py_DECREF(v); + return result; + } + + /* Next, scan the search functions in order of registration */ + args = PyTuple_New(1); + if (args == NULL) + goto onError; + PyTuple_SET_ITEM(args,0,v); + + len = PyList_Size(interp->codec_search_path); + if (len < 0) + goto onError; + if (len == 0) { + PyErr_SetString(PyExc_LookupError, + "no codec search functions registered: " + "can't find encoding"); + goto onError; + } + + for (i = 0; i < len; i++) { + PyObject *func; + + func = PyList_GetItem(interp->codec_search_path, i); + if (func == NULL) + goto onError; + result = PyEval_CallObject(func, args); + if (result == NULL) + goto onError; + if (result == Py_None) { + Py_DECREF(result); + continue; + } + if (!PyTuple_Check(result) || PyTuple_GET_SIZE(result) != 4) { + PyErr_SetString(PyExc_TypeError, + "codec search functions must return 4-tuples"); + Py_DECREF(result); + goto onError; + } + break; + } + if (i == len) { + /* XXX Perhaps we should cache misses too ? */ + PyErr_Format(PyExc_LookupError, + "unknown encoding: %s", encoding); + goto onError; + } + + /* Cache and return the result */ + PyDict_SetItem(interp->codec_search_cache, v, result); + Py_DECREF(args); + return result; + + onError: + Py_XDECREF(args); + return NULL; +} + +static +PyObject *args_tuple(PyObject *object, + const char *errors) +{ + PyObject *args; + + args = PyTuple_New(1 + (errors != NULL)); + if (args == NULL) + return NULL; + Py_INCREF(object); + PyTuple_SET_ITEM(args,0,object); + if (errors) { + PyObject *v; + + v = PyString_FromString(errors); + if (v == NULL) { + Py_DECREF(args); + return NULL; + } + PyTuple_SET_ITEM(args, 1, v); + } + return args; +} + +/* Helper function to get a codec item */ + +static +PyObject *codec_getitem(const char *encoding, int index) +{ + PyObject *codecs; + PyObject *v; + + codecs = _PyCodec_Lookup(encoding); + if (codecs == NULL) + return NULL; + v = PyTuple_GET_ITEM(codecs, index); + Py_DECREF(codecs); + Py_INCREF(v); + return v; +} + +/* Helper function to create an incremental codec. */ + +static +PyObject *codec_getincrementalcodec(const char *encoding, + const char *errors, + const char *attrname) +{ + PyObject *codecs, *ret, *inccodec; + + codecs = _PyCodec_Lookup(encoding); + if (codecs == NULL) + return NULL; + inccodec = PyObject_GetAttrString(codecs, attrname); + Py_DECREF(codecs); + if (inccodec == NULL) + return NULL; + if (errors) + ret = PyObject_CallFunction(inccodec, "s", errors); + else + ret = PyObject_CallFunction(inccodec, NULL); + Py_DECREF(inccodec); + return ret; +} + +/* Helper function to create a stream codec. */ + +static +PyObject *codec_getstreamcodec(const char *encoding, + PyObject *stream, + const char *errors, + const int index) +{ + PyObject *codecs, *streamcodec, *codeccls; + + codecs = _PyCodec_Lookup(encoding); + if (codecs == NULL) + return NULL; + + codeccls = PyTuple_GET_ITEM(codecs, index); + if (errors != NULL) + streamcodec = PyObject_CallFunction(codeccls, "Os", stream, errors); + else + streamcodec = PyObject_CallFunction(codeccls, "O", stream); + Py_DECREF(codecs); + return streamcodec; +} + +/* Convenience APIs to query the Codec registry. + + All APIs return a codec object with incremented refcount. + + */ + +PyObject *PyCodec_Encoder(const char *encoding) +{ + return codec_getitem(encoding, 0); +} + +PyObject *PyCodec_Decoder(const char *encoding) +{ + return codec_getitem(encoding, 1); +} + +PyObject *PyCodec_IncrementalEncoder(const char *encoding, + const char *errors) +{ + return codec_getincrementalcodec(encoding, errors, "incrementalencoder"); +} + +PyObject *PyCodec_IncrementalDecoder(const char *encoding, + const char *errors) +{ + return codec_getincrementalcodec(encoding, errors, "incrementaldecoder"); +} + +PyObject *PyCodec_StreamReader(const char *encoding, + PyObject *stream, + const char *errors) +{ + return codec_getstreamcodec(encoding, stream, errors, 2); +} + +PyObject *PyCodec_StreamWriter(const char *encoding, + PyObject *stream, + const char *errors) +{ + return codec_getstreamcodec(encoding, stream, errors, 3); +} + +/* Encode an object (e.g. an Unicode object) using the given encoding + and return the resulting encoded object (usually a Python string). + + errors is passed to the encoder factory as argument if non-NULL. */ + +PyObject *PyCodec_Encode(PyObject *object, + const char *encoding, + const char *errors) +{ + PyObject *encoder = NULL; + PyObject *args = NULL, *result = NULL; + PyObject *v; + + encoder = PyCodec_Encoder(encoding); + if (encoder == NULL) + goto onError; + + args = args_tuple(object, errors); + if (args == NULL) + goto onError; + + result = PyEval_CallObject(encoder,args); + if (result == NULL) + goto onError; + + if (!PyTuple_Check(result) || + PyTuple_GET_SIZE(result) != 2) { + PyErr_SetString(PyExc_TypeError, + "encoder must return a tuple (object,integer)"); + goto onError; + } + v = PyTuple_GET_ITEM(result,0); + Py_INCREF(v); + /* We don't check or use the second (integer) entry. */ + + Py_DECREF(args); + Py_DECREF(encoder); + Py_DECREF(result); + return v; + + onError: + Py_XDECREF(result); + Py_XDECREF(args); + Py_XDECREF(encoder); + return NULL; +} + +/* Decode an object (usually a Python string) using the given encoding + and return an equivalent object (e.g. an Unicode object). + + errors is passed to the decoder factory as argument if non-NULL. */ + +PyObject *PyCodec_Decode(PyObject *object, + const char *encoding, + const char *errors) +{ + PyObject *decoder = NULL; + PyObject *args = NULL, *result = NULL; + PyObject *v; + + decoder = PyCodec_Decoder(encoding); + if (decoder == NULL) + goto onError; + + args = args_tuple(object, errors); + if (args == NULL) + goto onError; + + result = PyEval_CallObject(decoder,args); + if (result == NULL) + goto onError; + if (!PyTuple_Check(result) || + PyTuple_GET_SIZE(result) != 2) { + PyErr_SetString(PyExc_TypeError, + "decoder must return a tuple (object,integer)"); + goto onError; + } + v = PyTuple_GET_ITEM(result,0); + Py_INCREF(v); + /* We don't check or use the second (integer) entry. */ + + Py_DECREF(args); + Py_DECREF(decoder); + Py_DECREF(result); + return v; + + onError: + Py_XDECREF(args); + Py_XDECREF(decoder); + Py_XDECREF(result); + return NULL; +} + +/* Register the error handling callback function error under the name + name. This function will be called by the codec when it encounters + an unencodable characters/undecodable bytes and doesn't know the + callback name, when name is specified as the error parameter + in the call to the encode/decode function. + Return 0 on success, -1 on error */ +int PyCodec_RegisterError(const char *name, PyObject *error) +{ + PyInterpreterState *interp = PyThreadState_GET()->interp; + if (interp->codec_search_path == NULL && _PyCodecRegistry_Init()) + return -1; + if (!PyCallable_Check(error)) { + PyErr_SetString(PyExc_TypeError, "handler must be callable"); + return -1; + } + return PyDict_SetItemString(interp->codec_error_registry, + (char *)name, error); +} + +/* Lookup the error handling callback function registered under the + name error. As a special case NULL can be passed, in which case + the error handling callback for strict encoding will be returned. */ +PyObject *PyCodec_LookupError(const char *name) +{ + PyObject *handler = NULL; + + PyInterpreterState *interp = PyThreadState_GET()->interp; + if (interp->codec_search_path == NULL && _PyCodecRegistry_Init()) + return NULL; + + if (name==NULL) + name = "strict"; + handler = PyDict_GetItemString(interp->codec_error_registry, (char *)name); + if (!handler) + PyErr_Format(PyExc_LookupError, "unknown error handler name '%.400s'", name); + else + Py_INCREF(handler); + return handler; +} + +static void wrong_exception_type(PyObject *exc) +{ + PyObject *type = PyObject_GetAttrString(exc, "__class__"); + if (type != NULL) { + PyObject *name = PyObject_GetAttrString(type, "__name__"); + Py_DECREF(type); + if (name != NULL) { + PyObject *string = PyObject_Str(name); + Py_DECREF(name); + if (string != NULL) { + PyErr_Format(PyExc_TypeError, + "don't know how to handle %.400s in error callback", + PyString_AS_STRING(string)); + Py_DECREF(string); + } + } + } +} + +PyObject *PyCodec_StrictErrors(PyObject *exc) +{ + if (PyExceptionInstance_Check(exc)) + PyErr_SetObject(PyExceptionInstance_Class(exc), exc); + else + PyErr_SetString(PyExc_TypeError, "codec must pass exception instance"); + return NULL; +} + + +#ifdef Py_USING_UNICODE +PyObject *PyCodec_IgnoreErrors(PyObject *exc) +{ + Py_ssize_t end; + if (PyObject_IsInstance(exc, PyExc_UnicodeEncodeError)) { + if (PyUnicodeEncodeError_GetEnd(exc, &end)) + return NULL; + } + else if (PyObject_IsInstance(exc, PyExc_UnicodeDecodeError)) { + if (PyUnicodeDecodeError_GetEnd(exc, &end)) + return NULL; + } + else if (PyObject_IsInstance(exc, PyExc_UnicodeTranslateError)) { + if (PyUnicodeTranslateError_GetEnd(exc, &end)) + return NULL; + } + else { + wrong_exception_type(exc); + return NULL; + } + /* ouch: passing NULL, 0, pos gives None instead of u'' */ + return Py_BuildValue("(u#n)", &end, 0, end); +} + + +PyObject *PyCodec_ReplaceErrors(PyObject *exc) +{ + PyObject *restuple; + Py_ssize_t start; + Py_ssize_t end; + Py_ssize_t i; + + if (PyObject_IsInstance(exc, PyExc_UnicodeEncodeError)) { + PyObject *res; + Py_UNICODE *p; + if (PyUnicodeEncodeError_GetStart(exc, &start)) + return NULL; + if (PyUnicodeEncodeError_GetEnd(exc, &end)) + return NULL; + res = PyUnicode_FromUnicode(NULL, end-start); + if (res == NULL) + return NULL; + for (p = PyUnicode_AS_UNICODE(res), i = start; + i PY_SSIZE_T_MAX / (2+7+1)) { + end = start + PY_SSIZE_T_MAX / (2+7+1); +#ifndef Py_UNICODE_WIDE + if (0xD800 <= startp[end - 1] && startp[end - 1] <= 0xDBFF) + end--; +#endif + } + e = startp + end; + for (p = startp+start, ressize = 0; p < e;) { + Py_UCS4 ch = *p++; +#ifndef Py_UNICODE_WIDE + if ((0xD800 <= ch && ch <= 0xDBFF) && + (p < e) && + (0xDC00 <= *p && *p <= 0xDFFF)) { + ch = ((((ch & 0x03FF) << 10) | + ((Py_UCS4)*p++ & 0x03FF)) + 0x10000); + } +#endif + if (ch < 10) + ressize += 2+1+1; + else if (ch < 100) + ressize += 2+2+1; + else if (ch < 1000) + ressize += 2+3+1; + else if (ch < 10000) + ressize += 2+4+1; + else if (ch < 100000) + ressize += 2+5+1; + else if (ch < 1000000) + ressize += 2+6+1; + else + ressize += 2+7+1; + } + /* allocate replacement */ + res = PyUnicode_FromUnicode(NULL, ressize); + if (res == NULL) { + Py_DECREF(object); + return NULL; + } + /* generate replacement */ + for (p = startp+start, outp = PyUnicode_AS_UNICODE(res); p < e;) { + int digits; + int base; + Py_UCS4 ch = *p++; +#ifndef Py_UNICODE_WIDE + if ((0xD800 <= ch && ch <= 0xDBFF) && + (p < startp+end) && + (0xDC00 <= *p && *p <= 0xDFFF)) { + ch = ((((ch & 0x03FF) << 10) | + ((Py_UCS4)*p++ & 0x03FF)) + 0x10000); + } +#endif + *outp++ = '&'; + *outp++ = '#'; + if (ch < 10) { + digits = 1; + base = 1; + } + else if (ch < 100) { + digits = 2; + base = 10; + } + else if (ch < 1000) { + digits = 3; + base = 100; + } + else if (ch < 10000) { + digits = 4; + base = 1000; + } + else if (ch < 100000) { + digits = 5; + base = 10000; + } + else if (ch < 1000000) { + digits = 6; + base = 100000; + } + else { + digits = 7; + base = 1000000; + } + while (digits-->0) { + *outp++ = '0' + ch/base; + ch %= base; + base /= 10; + } + *outp++ = ';'; + } + restuple = Py_BuildValue("(On)", res, end); + Py_DECREF(res); + Py_DECREF(object); + return restuple; + } + else { + wrong_exception_type(exc); + return NULL; + } +} + +static Py_UNICODE hexdigits[] = { + '0', '1', '2', '3', '4', '5', '6', '7', + '8', '9', 'a', 'b', 'c', 'd', 'e', 'f' +}; + +PyObject *PyCodec_BackslashReplaceErrors(PyObject *exc) +{ + if (PyObject_IsInstance(exc, PyExc_UnicodeEncodeError)) { + PyObject *restuple; + PyObject *object; + Py_ssize_t start; + Py_ssize_t end; + PyObject *res; + Py_UNICODE *p; + Py_UNICODE *startp; + Py_UNICODE *outp; + Py_ssize_t ressize; + if (PyUnicodeEncodeError_GetStart(exc, &start)) + return NULL; + if (PyUnicodeEncodeError_GetEnd(exc, &end)) + return NULL; + if (!(object = PyUnicodeEncodeError_GetObject(exc))) + return NULL; + if (end - start > PY_SSIZE_T_MAX / (1+1+8)) + end = start + PY_SSIZE_T_MAX / (1+1+8); + startp = PyUnicode_AS_UNICODE(object); + for (p = startp+start, ressize = 0; p < startp+end; ++p) { +#ifdef Py_UNICODE_WIDE + if (*p >= 0x00010000) + ressize += 1+1+8; + else +#endif + if (*p >= 0x100) { + ressize += 1+1+4; + } + else + ressize += 1+1+2; + } + res = PyUnicode_FromUnicode(NULL, ressize); + if (res == NULL) { + Py_DECREF(object); + return NULL; + } + for (p = startp+start, outp = PyUnicode_AS_UNICODE(res); + p < startp+end; ++p) { + Py_UNICODE c = *p; + *outp++ = '\\'; +#ifdef Py_UNICODE_WIDE + if (c >= 0x00010000) { + *outp++ = 'U'; + *outp++ = hexdigits[(c>>28)&0xf]; + *outp++ = hexdigits[(c>>24)&0xf]; + *outp++ = hexdigits[(c>>20)&0xf]; + *outp++ = hexdigits[(c>>16)&0xf]; + *outp++ = hexdigits[(c>>12)&0xf]; + *outp++ = hexdigits[(c>>8)&0xf]; + } + else +#endif + if (c >= 0x100) { + *outp++ = 'u'; + *outp++ = hexdigits[(c>>12)&0xf]; + *outp++ = hexdigits[(c>>8)&0xf]; + } + else + *outp++ = 'x'; + *outp++ = hexdigits[(c>>4)&0xf]; + *outp++ = hexdigits[c&0xf]; + } + + restuple = Py_BuildValue("(On)", res, end); + Py_DECREF(res); + Py_DECREF(object); + return restuple; + } + else { + wrong_exception_type(exc); + return NULL; + } +} +#endif + +static PyObject *strict_errors(PyObject *self, PyObject *exc) +{ + return PyCodec_StrictErrors(exc); +} + + +#ifdef Py_USING_UNICODE +static PyObject *ignore_errors(PyObject *self, PyObject *exc) +{ + return PyCodec_IgnoreErrors(exc); +} + + +static PyObject *replace_errors(PyObject *self, PyObject *exc) +{ + return PyCodec_ReplaceErrors(exc); +} + + +static PyObject *xmlcharrefreplace_errors(PyObject *self, PyObject *exc) +{ + return PyCodec_XMLCharRefReplaceErrors(exc); +} + + +static PyObject *backslashreplace_errors(PyObject *self, PyObject *exc) +{ + return PyCodec_BackslashReplaceErrors(exc); +} +#endif + +static int _PyCodecRegistry_Init(void) +{ + static struct { + char *name; + PyMethodDef def; + } methods[] = + { + { + "strict", + { + "strict_errors", + strict_errors, + METH_O, + PyDoc_STR("Implements the 'strict' error handling, which " + "raises a UnicodeError on coding errors.") + } + }, +#ifdef Py_USING_UNICODE + { + "ignore", + { + "ignore_errors", + ignore_errors, + METH_O, + PyDoc_STR("Implements the 'ignore' error handling, which " + "ignores malformed data and continues.") + } + }, + { + "replace", + { + "replace_errors", + replace_errors, + METH_O, + PyDoc_STR("Implements the 'replace' error handling, which " + "replaces malformed data with a replacement marker.") + } + }, + { + "xmlcharrefreplace", + { + "xmlcharrefreplace_errors", + xmlcharrefreplace_errors, + METH_O, + PyDoc_STR("Implements the 'xmlcharrefreplace' error handling, " + "which replaces an unencodable character with the " + "appropriate XML character reference.") + } + }, + { + "backslashreplace", + { + "backslashreplace_errors", + backslashreplace_errors, + METH_O, + PyDoc_STR("Implements the 'backslashreplace' error handling, " + "which replaces an unencodable character with a " + "backslashed escape sequence.") + } + } +#endif + }; + + PyInterpreterState *interp = PyThreadState_GET()->interp; + PyObject *mod; + unsigned i; + + if (interp->codec_search_path != NULL) + return 0; + + interp->codec_search_path = PyList_New(0); + interp->codec_search_cache = PyDict_New(); + interp->codec_error_registry = PyDict_New(); + + if (interp->codec_error_registry) { + for (i = 0; i < sizeof(methods)/sizeof(methods[0]); ++i) { + PyObject *func = PyCFunction_New(&methods[i].def, NULL); + int res; + if (!func) + Py_FatalError("can't initialize codec error registry"); + res = PyCodec_RegisterError(methods[i].name, func); + Py_DECREF(func); + if (res) + Py_FatalError("can't initialize codec error registry"); + } + } + + if (interp->codec_search_path == NULL || + interp->codec_search_cache == NULL || + interp->codec_error_registry == NULL) + Py_FatalError("can't initialize codec registry"); + + mod = PyImport_ImportModuleLevel("encodings", NULL, NULL, NULL, 0); + if (mod == NULL) { + if (PyErr_ExceptionMatches(PyExc_ImportError)) { + /* Ignore ImportErrors... this is done so that + distributions can disable the encodings package. Note + that other errors are not masked, e.g. SystemErrors + raised to inform the user of an error in the Python + configuration are still reported back to the user. */ + PyErr_Clear(); + return 0; + } + return -1; + } + Py_DECREF(mod); + return 0; +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/compile.c b/AppPkg/Applications/Python/Python-2.7.10/Python/compile.c new file mode 100644 index 0000000000..205f04477f --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/compile.c @@ -0,0 +1,4003 @@ +/* + * This file compiles an abstract syntax tree (AST) into Python bytecode. + * + * The primary entry point is PyAST_Compile(), which returns a + * PyCodeObject. The compiler makes several passes to build the code + * object: + * 1. Checks for future statements. See future.c + * 2. Builds a symbol table. See symtable.c. + * 3. Generate code for basic blocks. See compiler_mod() in this file. + * 4. Assemble the basic blocks into final code. See assemble() in + * this file. + * 5. Optimize the byte code (peephole optimizations). See peephole.c + * + * Note that compiler_mod() suggests module, but the module ast type + * (mod_ty) has cases for expressions and interactive statements. + * + * CAUTION: The VISIT_* macros abort the current function when they + * encounter a problem. So don't invoke them when there is memory + * which needs to be released. Code blocks are OK, as the compiler + * structure takes care of releasing those. Use the arena to manage + * objects. + */ + +#include "Python.h" + +#include "Python-ast.h" +#include "node.h" +#include "pyarena.h" +#include "ast.h" +#include "code.h" +#include "compile.h" +#include "symtable.h" +#include "opcode.h" + +int Py_OptimizeFlag = 0; + +#define DEFAULT_BLOCK_SIZE 16 +#define DEFAULT_BLOCKS 8 +#define DEFAULT_CODE_SIZE 128 +#define DEFAULT_LNOTAB_SIZE 16 + +#define COMP_GENEXP 0 +#define COMP_SETCOMP 1 +#define COMP_DICTCOMP 2 + +struct instr { + unsigned i_jabs : 1; + unsigned i_jrel : 1; + unsigned i_hasarg : 1; + unsigned char i_opcode; + int i_oparg; + struct basicblock_ *i_target; /* target block (if jump instruction) */ + int i_lineno; +}; + +typedef struct basicblock_ { + /* Each basicblock in a compilation unit is linked via b_list in the + reverse order that the block are allocated. b_list points to the next + block, not to be confused with b_next, which is next by control flow. */ + struct basicblock_ *b_list; + /* number of instructions used */ + int b_iused; + /* length of instruction array (b_instr) */ + int b_ialloc; + /* pointer to an array of instructions, initially NULL */ + struct instr *b_instr; + /* If b_next is non-NULL, it is a pointer to the next + block reached by normal control flow. */ + struct basicblock_ *b_next; + /* b_seen is used to perform a DFS of basicblocks. */ + unsigned b_seen : 1; + /* b_return is true if a RETURN_VALUE opcode is inserted. */ + unsigned b_return : 1; + /* depth of stack upon entry of block, computed by stackdepth() */ + int b_startdepth; + /* instruction offset for block, computed by assemble_jump_offsets() */ + int b_offset; +} basicblock; + +/* fblockinfo tracks the current frame block. + +A frame block is used to handle loops, try/except, and try/finally. +It's called a frame block to distinguish it from a basic block in the +compiler IR. +*/ + +enum fblocktype { LOOP, EXCEPT, FINALLY_TRY, FINALLY_END }; + +struct fblockinfo { + enum fblocktype fb_type; + basicblock *fb_block; +}; + +/* The following items change on entry and exit of code blocks. + They must be saved and restored when returning to a block. +*/ +struct compiler_unit { + PySTEntryObject *u_ste; + + PyObject *u_name; + /* The following fields are dicts that map objects to + the index of them in co_XXX. The index is used as + the argument for opcodes that refer to those collections. + */ + PyObject *u_consts; /* all constants */ + PyObject *u_names; /* all names */ + PyObject *u_varnames; /* local variables */ + PyObject *u_cellvars; /* cell variables */ + PyObject *u_freevars; /* free variables */ + + PyObject *u_private; /* for private name mangling */ + + int u_argcount; /* number of arguments for block */ + /* Pointer to the most recently allocated block. By following b_list + members, you can reach all early allocated blocks. */ + basicblock *u_blocks; + basicblock *u_curblock; /* pointer to current block */ + + int u_nfblocks; + struct fblockinfo u_fblock[CO_MAXBLOCKS]; + + int u_firstlineno; /* the first lineno of the block */ + int u_lineno; /* the lineno for the current stmt */ + bool u_lineno_set; /* boolean to indicate whether instr + has been generated with current lineno */ +}; + +/* This struct captures the global state of a compilation. + +The u pointer points to the current compilation unit, while units +for enclosing blocks are stored in c_stack. The u and c_stack are +managed by compiler_enter_scope() and compiler_exit_scope(). +*/ + +struct compiler { + const char *c_filename; + struct symtable *c_st; + PyFutureFeatures *c_future; /* pointer to module's __future__ */ + PyCompilerFlags *c_flags; + + int c_interactive; /* true if in interactive mode */ + int c_nestlevel; + + struct compiler_unit *u; /* compiler state for current block */ + PyObject *c_stack; /* Python list holding compiler_unit ptrs */ + PyArena *c_arena; /* pointer to memory allocation arena */ +}; + +static int compiler_enter_scope(struct compiler *, identifier, void *, int); +static void compiler_free(struct compiler *); +static basicblock *compiler_new_block(struct compiler *); +static int compiler_next_instr(struct compiler *, basicblock *); +static int compiler_addop(struct compiler *, int); +static int compiler_addop_o(struct compiler *, int, PyObject *, PyObject *); +static int compiler_addop_i(struct compiler *, int, int); +static int compiler_addop_j(struct compiler *, int, basicblock *, int); +static basicblock *compiler_use_new_block(struct compiler *); +static int compiler_error(struct compiler *, const char *); +static int compiler_nameop(struct compiler *, identifier, expr_context_ty); + +static PyCodeObject *compiler_mod(struct compiler *, mod_ty); +static int compiler_visit_stmt(struct compiler *, stmt_ty); +static int compiler_visit_keyword(struct compiler *, keyword_ty); +static int compiler_visit_expr(struct compiler *, expr_ty); +static int compiler_augassign(struct compiler *, stmt_ty); +static int compiler_visit_slice(struct compiler *, slice_ty, + expr_context_ty); + +static int compiler_push_fblock(struct compiler *, enum fblocktype, + basicblock *); +static void compiler_pop_fblock(struct compiler *, enum fblocktype, + basicblock *); +/* Returns true if there is a loop on the fblock stack. */ +static int compiler_in_loop(struct compiler *); + +static int inplace_binop(struct compiler *, operator_ty); +static int expr_constant(expr_ty e); + +static int compiler_with(struct compiler *, stmt_ty); + +static PyCodeObject *assemble(struct compiler *, int addNone); +static PyObject *__doc__; + +#define COMPILER_CAPSULE_NAME_COMPILER_UNIT "compile.c compiler unit" + +PyObject * +_Py_Mangle(PyObject *privateobj, PyObject *ident) +{ + /* Name mangling: __private becomes _classname__private. + This is independent from how the name is used. */ + const char *p, *name = PyString_AsString(ident); + char *buffer; + size_t nlen, plen; + if (privateobj == NULL || !PyString_Check(privateobj) || + name == NULL || name[0] != '_' || name[1] != '_') { + Py_INCREF(ident); + return ident; + } + p = PyString_AsString(privateobj); + nlen = strlen(name); + /* Don't mangle __id__ or names with dots. + + The only time a name with a dot can occur is when + we are compiling an import statement that has a + package name. + + TODO(jhylton): Decide whether we want to support + mangling of the module name, e.g. __M.X. + */ + if ((name[nlen-1] == '_' && name[nlen-2] == '_') + || strchr(name, '.')) { + Py_INCREF(ident); + return ident; /* Don't mangle __whatever__ */ + } + /* Strip leading underscores from class name */ + while (*p == '_') + p++; + if (*p == '\0') { + Py_INCREF(ident); + return ident; /* Don't mangle if class is just underscores */ + } + plen = strlen(p); + + if (plen + nlen >= PY_SSIZE_T_MAX - 1) { + PyErr_SetString(PyExc_OverflowError, + "private identifier too large to be mangled"); + return NULL; + } + + ident = PyString_FromStringAndSize(NULL, 1 + nlen + plen); + if (!ident) + return 0; + /* ident = "_" + p[:plen] + name # i.e. 1+plen+nlen bytes */ + buffer = PyString_AS_STRING(ident); + buffer[0] = '_'; + strncpy(buffer+1, p, plen); + strcpy(buffer+1+plen, name); + return ident; +} + +static int +compiler_init(struct compiler *c) +{ + memset(c, 0, sizeof(struct compiler)); + + c->c_stack = PyList_New(0); + if (!c->c_stack) + return 0; + + return 1; +} + +PyCodeObject * +PyAST_Compile(mod_ty mod, const char *filename, PyCompilerFlags *flags, + PyArena *arena) +{ + struct compiler c; + PyCodeObject *co = NULL; + PyCompilerFlags local_flags; + int merged; + + if (!__doc__) { + __doc__ = PyString_InternFromString("__doc__"); + if (!__doc__) + return NULL; + } + + if (!compiler_init(&c)) + return NULL; + c.c_filename = filename; + c.c_arena = arena; + c.c_future = PyFuture_FromAST(mod, filename); + if (c.c_future == NULL) + goto finally; + if (!flags) { + local_flags.cf_flags = 0; + flags = &local_flags; + } + merged = c.c_future->ff_features | flags->cf_flags; + c.c_future->ff_features = merged; + flags->cf_flags = merged; + c.c_flags = flags; + c.c_nestlevel = 0; + + c.c_st = PySymtable_Build(mod, filename, c.c_future); + if (c.c_st == NULL) { + if (!PyErr_Occurred()) + PyErr_SetString(PyExc_SystemError, "no symtable"); + goto finally; + } + + co = compiler_mod(&c, mod); + + finally: + compiler_free(&c); + assert(co || PyErr_Occurred()); + return co; +} + +PyCodeObject * +PyNode_Compile(struct _node *n, const char *filename) +{ + PyCodeObject *co = NULL; + mod_ty mod; + PyArena *arena = PyArena_New(); + if (!arena) + return NULL; + mod = PyAST_FromNode(n, NULL, filename, arena); + if (mod) + co = PyAST_Compile(mod, filename, NULL, arena); + PyArena_Free(arena); + return co; +} + +static void +compiler_free(struct compiler *c) +{ + if (c->c_st) + PySymtable_Free(c->c_st); + if (c->c_future) + PyObject_Free(c->c_future); + Py_DECREF(c->c_stack); +} + +static PyObject * +list2dict(PyObject *list) +{ + Py_ssize_t i, n; + PyObject *v, *k; + PyObject *dict = PyDict_New(); + if (!dict) return NULL; + + n = PyList_Size(list); + for (i = 0; i < n; i++) { + v = PyInt_FromLong(i); + if (!v) { + Py_DECREF(dict); + return NULL; + } + k = PyList_GET_ITEM(list, i); + k = PyTuple_Pack(2, k, k->ob_type); + if (k == NULL || PyDict_SetItem(dict, k, v) < 0) { + Py_XDECREF(k); + Py_DECREF(v); + Py_DECREF(dict); + return NULL; + } + Py_DECREF(k); + Py_DECREF(v); + } + return dict; +} + +/* Return new dict containing names from src that match scope(s). + +src is a symbol table dictionary. If the scope of a name matches +either scope_type or flag is set, insert it into the new dict. The +values are integers, starting at offset and increasing by one for +each key. +*/ + +static PyObject * +dictbytype(PyObject *src, int scope_type, int flag, int offset) +{ + Py_ssize_t i = offset, scope, num_keys, key_i; + PyObject *k, *v, *dest = PyDict_New(); + PyObject *sorted_keys; + + assert(offset >= 0); + if (dest == NULL) + return NULL; + + /* Sort the keys so that we have a deterministic order on the indexes + saved in the returned dictionary. These indexes are used as indexes + into the free and cell var storage. Therefore if they aren't + deterministic, then the generated bytecode is not deterministic. + */ + sorted_keys = PyDict_Keys(src); + if (sorted_keys == NULL) + return NULL; + if (PyList_Sort(sorted_keys) != 0) { + Py_DECREF(sorted_keys); + return NULL; + } + num_keys = PyList_GET_SIZE(sorted_keys); + + for (key_i = 0; key_i < num_keys; key_i++) { + k = PyList_GET_ITEM(sorted_keys, key_i); + v = PyDict_GetItem(src, k); + /* XXX this should probably be a macro in symtable.h */ + assert(PyInt_Check(v)); + scope = (PyInt_AS_LONG(v) >> SCOPE_OFF) & SCOPE_MASK; + + if (scope == scope_type || PyInt_AS_LONG(v) & flag) { + PyObject *tuple, *item = PyInt_FromLong(i); + if (item == NULL) { + Py_DECREF(sorted_keys); + Py_DECREF(dest); + return NULL; + } + i++; + tuple = PyTuple_Pack(2, k, k->ob_type); + if (!tuple || PyDict_SetItem(dest, tuple, item) < 0) { + Py_DECREF(sorted_keys); + Py_DECREF(item); + Py_DECREF(dest); + Py_XDECREF(tuple); + return NULL; + } + Py_DECREF(item); + Py_DECREF(tuple); + } + } + Py_DECREF(sorted_keys); + return dest; +} + +static void +compiler_unit_check(struct compiler_unit *u) +{ + basicblock *block; + for (block = u->u_blocks; block != NULL; block = block->b_list) { + assert((void *)block != (void *)0xcbcbcbcb); + assert((void *)block != (void *)0xfbfbfbfb); + assert((void *)block != (void *)0xdbdbdbdb); + if (block->b_instr != NULL) { + assert(block->b_ialloc > 0); + assert(block->b_iused > 0); + assert(block->b_ialloc >= block->b_iused); + } + else { + assert (block->b_iused == 0); + assert (block->b_ialloc == 0); + } + } +} + +static void +compiler_unit_free(struct compiler_unit *u) +{ + basicblock *b, *next; + + compiler_unit_check(u); + b = u->u_blocks; + while (b != NULL) { + if (b->b_instr) + PyObject_Free((void *)b->b_instr); + next = b->b_list; + PyObject_Free((void *)b); + b = next; + } + Py_CLEAR(u->u_ste); + Py_CLEAR(u->u_name); + Py_CLEAR(u->u_consts); + Py_CLEAR(u->u_names); + Py_CLEAR(u->u_varnames); + Py_CLEAR(u->u_freevars); + Py_CLEAR(u->u_cellvars); + Py_CLEAR(u->u_private); + PyObject_Free(u); +} + +static int +compiler_enter_scope(struct compiler *c, identifier name, void *key, + int lineno) +{ + struct compiler_unit *u; + + u = (struct compiler_unit *)PyObject_Malloc(sizeof( + struct compiler_unit)); + if (!u) { + PyErr_NoMemory(); + return 0; + } + memset(u, 0, sizeof(struct compiler_unit)); + u->u_argcount = 0; + u->u_ste = PySymtable_Lookup(c->c_st, key); + if (!u->u_ste) { + compiler_unit_free(u); + return 0; + } + Py_INCREF(name); + u->u_name = name; + u->u_varnames = list2dict(u->u_ste->ste_varnames); + u->u_cellvars = dictbytype(u->u_ste->ste_symbols, CELL, 0, 0); + if (!u->u_varnames || !u->u_cellvars) { + compiler_unit_free(u); + return 0; + } + + u->u_freevars = dictbytype(u->u_ste->ste_symbols, FREE, DEF_FREE_CLASS, + PyDict_Size(u->u_cellvars)); + if (!u->u_freevars) { + compiler_unit_free(u); + return 0; + } + + u->u_blocks = NULL; + u->u_nfblocks = 0; + u->u_firstlineno = lineno; + u->u_lineno = 0; + u->u_lineno_set = false; + u->u_consts = PyDict_New(); + if (!u->u_consts) { + compiler_unit_free(u); + return 0; + } + u->u_names = PyDict_New(); + if (!u->u_names) { + compiler_unit_free(u); + return 0; + } + + u->u_private = NULL; + + /* Push the old compiler_unit on the stack. */ + if (c->u) { + PyObject *capsule = PyCapsule_New(c->u, COMPILER_CAPSULE_NAME_COMPILER_UNIT, NULL); + if (!capsule || PyList_Append(c->c_stack, capsule) < 0) { + Py_XDECREF(capsule); + compiler_unit_free(u); + return 0; + } + Py_DECREF(capsule); + u->u_private = c->u->u_private; + Py_XINCREF(u->u_private); + } + c->u = u; + + c->c_nestlevel++; + if (compiler_use_new_block(c) == NULL) + return 0; + + return 1; +} + +static void +compiler_exit_scope(struct compiler *c) +{ + int n; + PyObject *capsule; + + c->c_nestlevel--; + compiler_unit_free(c->u); + /* Restore c->u to the parent unit. */ + n = PyList_GET_SIZE(c->c_stack) - 1; + if (n >= 0) { + capsule = PyList_GET_ITEM(c->c_stack, n); + c->u = (struct compiler_unit *)PyCapsule_GetPointer(capsule, COMPILER_CAPSULE_NAME_COMPILER_UNIT); + assert(c->u); + /* we are deleting from a list so this really shouldn't fail */ + if (PySequence_DelItem(c->c_stack, n) < 0) + Py_FatalError("compiler_exit_scope()"); + compiler_unit_check(c->u); + } + else + c->u = NULL; + +} + +/* Allocate a new block and return a pointer to it. + Returns NULL on error. +*/ + +static basicblock * +compiler_new_block(struct compiler *c) +{ + basicblock *b; + struct compiler_unit *u; + + u = c->u; + b = (basicblock *)PyObject_Malloc(sizeof(basicblock)); + if (b == NULL) { + PyErr_NoMemory(); + return NULL; + } + memset((void *)b, 0, sizeof(basicblock)); + /* Extend the singly linked list of blocks with new block. */ + b->b_list = u->u_blocks; + u->u_blocks = b; + return b; +} + +static basicblock * +compiler_use_new_block(struct compiler *c) +{ + basicblock *block = compiler_new_block(c); + if (block == NULL) + return NULL; + c->u->u_curblock = block; + return block; +} + +static basicblock * +compiler_next_block(struct compiler *c) +{ + basicblock *block = compiler_new_block(c); + if (block == NULL) + return NULL; + c->u->u_curblock->b_next = block; + c->u->u_curblock = block; + return block; +} + +static basicblock * +compiler_use_next_block(struct compiler *c, basicblock *block) +{ + assert(block != NULL); + c->u->u_curblock->b_next = block; + c->u->u_curblock = block; + return block; +} + +/* Returns the offset of the next instruction in the current block's + b_instr array. Resizes the b_instr as necessary. + Returns -1 on failure. +*/ + +static int +compiler_next_instr(struct compiler *c, basicblock *b) +{ + assert(b != NULL); + if (b->b_instr == NULL) { + b->b_instr = (struct instr *)PyObject_Malloc( + sizeof(struct instr) * DEFAULT_BLOCK_SIZE); + if (b->b_instr == NULL) { + PyErr_NoMemory(); + return -1; + } + b->b_ialloc = DEFAULT_BLOCK_SIZE; + memset((char *)b->b_instr, 0, + sizeof(struct instr) * DEFAULT_BLOCK_SIZE); + } + else if (b->b_iused == b->b_ialloc) { + struct instr *tmp; + size_t oldsize, newsize; + oldsize = b->b_ialloc * sizeof(struct instr); + newsize = oldsize << 1; + + if (oldsize > (PY_SIZE_MAX >> 1)) { + PyErr_NoMemory(); + return -1; + } + + if (newsize == 0) { + PyErr_NoMemory(); + return -1; + } + b->b_ialloc <<= 1; + tmp = (struct instr *)PyObject_Realloc( + (void *)b->b_instr, newsize); + if (tmp == NULL) { + PyErr_NoMemory(); + return -1; + } + b->b_instr = tmp; + memset((char *)b->b_instr + oldsize, 0, newsize - oldsize); + } + return b->b_iused++; +} + +/* Set the i_lineno member of the instruction at offset off if the + line number for the current expression/statement has not + already been set. If it has been set, the call has no effect. + + The line number is reset in the following cases: + - when entering a new scope + - on each statement + - on each expression that start a new line + - before the "except" clause + - before the "for" and "while" expressions +*/ + +static void +compiler_set_lineno(struct compiler *c, int off) +{ + basicblock *b; + if (c->u->u_lineno_set) + return; + c->u->u_lineno_set = true; + b = c->u->u_curblock; + b->b_instr[off].i_lineno = c->u->u_lineno; +} + +static int +opcode_stack_effect(int opcode, int oparg) +{ + switch (opcode) { + case POP_TOP: + return -1; + case ROT_TWO: + case ROT_THREE: + return 0; + case DUP_TOP: + return 1; + case ROT_FOUR: + return 0; + + case UNARY_POSITIVE: + case UNARY_NEGATIVE: + case UNARY_NOT: + case UNARY_CONVERT: + case UNARY_INVERT: + return 0; + + case SET_ADD: + case LIST_APPEND: + return -1; + + case MAP_ADD: + return -2; + + case BINARY_POWER: + case BINARY_MULTIPLY: + case BINARY_DIVIDE: + case BINARY_MODULO: + case BINARY_ADD: + case BINARY_SUBTRACT: + case BINARY_SUBSCR: + case BINARY_FLOOR_DIVIDE: + case BINARY_TRUE_DIVIDE: + return -1; + case INPLACE_FLOOR_DIVIDE: + case INPLACE_TRUE_DIVIDE: + return -1; + + case SLICE+0: + return 0; + case SLICE+1: + return -1; + case SLICE+2: + return -1; + case SLICE+3: + return -2; + + case STORE_SLICE+0: + return -2; + case STORE_SLICE+1: + return -3; + case STORE_SLICE+2: + return -3; + case STORE_SLICE+3: + return -4; + + case DELETE_SLICE+0: + return -1; + case DELETE_SLICE+1: + return -2; + case DELETE_SLICE+2: + return -2; + case DELETE_SLICE+3: + return -3; + + case INPLACE_ADD: + case INPLACE_SUBTRACT: + case INPLACE_MULTIPLY: + case INPLACE_DIVIDE: + case INPLACE_MODULO: + return -1; + case STORE_SUBSCR: + return -3; + case STORE_MAP: + return -2; + case DELETE_SUBSCR: + return -2; + + case BINARY_LSHIFT: + case BINARY_RSHIFT: + case BINARY_AND: + case BINARY_XOR: + case BINARY_OR: + return -1; + case INPLACE_POWER: + return -1; + case GET_ITER: + return 0; + + case PRINT_EXPR: + return -1; + case PRINT_ITEM: + return -1; + case PRINT_NEWLINE: + return 0; + case PRINT_ITEM_TO: + return -2; + case PRINT_NEWLINE_TO: + return -1; + case INPLACE_LSHIFT: + case INPLACE_RSHIFT: + case INPLACE_AND: + case INPLACE_XOR: + case INPLACE_OR: + return -1; + case BREAK_LOOP: + return 0; + case SETUP_WITH: + return 4; + case WITH_CLEANUP: + return -1; /* XXX Sometimes more */ + case LOAD_LOCALS: + return 1; + case RETURN_VALUE: + return -1; + case IMPORT_STAR: + return -1; + case EXEC_STMT: + return -3; + case YIELD_VALUE: + return 0; + + case POP_BLOCK: + return 0; + case END_FINALLY: + return -3; /* or -1 or -2 if no exception occurred or + return/break/continue */ + case BUILD_CLASS: + return -2; + + case STORE_NAME: + return -1; + case DELETE_NAME: + return 0; + case UNPACK_SEQUENCE: + return oparg-1; + case FOR_ITER: + return 1; /* or -1, at end of iterator */ + + case STORE_ATTR: + return -2; + case DELETE_ATTR: + return -1; + case STORE_GLOBAL: + return -1; + case DELETE_GLOBAL: + return 0; + case DUP_TOPX: + return oparg; + case LOAD_CONST: + return 1; + case LOAD_NAME: + return 1; + case BUILD_TUPLE: + case BUILD_LIST: + case BUILD_SET: + return 1-oparg; + case BUILD_MAP: + return 1; + case LOAD_ATTR: + return 0; + case COMPARE_OP: + return -1; + case IMPORT_NAME: + return -1; + case IMPORT_FROM: + return 1; + + case JUMP_FORWARD: + case JUMP_IF_TRUE_OR_POP: /* -1 if jump not taken */ + case JUMP_IF_FALSE_OR_POP: /* "" */ + case JUMP_ABSOLUTE: + return 0; + + case POP_JUMP_IF_FALSE: + case POP_JUMP_IF_TRUE: + return -1; + + case LOAD_GLOBAL: + return 1; + + case CONTINUE_LOOP: + return 0; + case SETUP_LOOP: + case SETUP_EXCEPT: + case SETUP_FINALLY: + return 0; + + case LOAD_FAST: + return 1; + case STORE_FAST: + return -1; + case DELETE_FAST: + return 0; + + case RAISE_VARARGS: + return -oparg; +#define NARGS(o) (((o) % 256) + 2*((o) / 256)) + case CALL_FUNCTION: + return -NARGS(oparg); + case CALL_FUNCTION_VAR: + case CALL_FUNCTION_KW: + return -NARGS(oparg)-1; + case CALL_FUNCTION_VAR_KW: + return -NARGS(oparg)-2; +#undef NARGS + case MAKE_FUNCTION: + return -oparg; + case BUILD_SLICE: + if (oparg == 3) + return -2; + else + return -1; + + case MAKE_CLOSURE: + return -oparg-1; + case LOAD_CLOSURE: + return 1; + case LOAD_DEREF: + return 1; + case STORE_DEREF: + return -1; + default: + fprintf(stderr, "opcode = %d\n", opcode); + Py_FatalError("opcode_stack_effect()"); + + } + return 0; /* not reachable */ +} + +/* Add an opcode with no argument. + Returns 0 on failure, 1 on success. +*/ + +static int +compiler_addop(struct compiler *c, int opcode) +{ + basicblock *b; + struct instr *i; + int off; + off = compiler_next_instr(c, c->u->u_curblock); + if (off < 0) + return 0; + b = c->u->u_curblock; + i = &b->b_instr[off]; + i->i_opcode = opcode; + i->i_hasarg = 0; + if (opcode == RETURN_VALUE) + b->b_return = 1; + compiler_set_lineno(c, off); + return 1; +} + +static int +compiler_add_o(struct compiler *c, PyObject *dict, PyObject *o) +{ + PyObject *t, *v; + Py_ssize_t arg; + double d; + + /* necessary to make sure types aren't coerced (e.g., int and long) */ + /* _and_ to distinguish 0.0 from -0.0 e.g. on IEEE platforms */ + if (PyFloat_Check(o)) { + d = PyFloat_AS_DOUBLE(o); + /* all we need is to make the tuple different in either the 0.0 + * or -0.0 case from all others, just to avoid the "coercion". + */ + if (d == 0.0 && copysign(1.0, d) < 0.0) + t = PyTuple_Pack(3, o, o->ob_type, Py_None); + else + t = PyTuple_Pack(2, o, o->ob_type); + } +#ifndef WITHOUT_COMPLEX + else if (PyComplex_Check(o)) { + Py_complex z; + int real_negzero, imag_negzero; + /* For the complex case we must make complex(x, 0.) + different from complex(x, -0.) and complex(0., y) + different from complex(-0., y), for any x and y. + All four complex zeros must be distinguished.*/ + z = PyComplex_AsCComplex(o); + real_negzero = z.real == 0.0 && copysign(1.0, z.real) < 0.0; + imag_negzero = z.imag == 0.0 && copysign(1.0, z.imag) < 0.0; + if (real_negzero && imag_negzero) { + t = PyTuple_Pack(5, o, o->ob_type, + Py_None, Py_None, Py_None); + } + else if (imag_negzero) { + t = PyTuple_Pack(4, o, o->ob_type, Py_None, Py_None); + } + else if (real_negzero) { + t = PyTuple_Pack(3, o, o->ob_type, Py_None); + } + else { + t = PyTuple_Pack(2, o, o->ob_type); + } + } +#endif /* WITHOUT_COMPLEX */ + else { + t = PyTuple_Pack(2, o, o->ob_type); + } + if (t == NULL) + return -1; + + v = PyDict_GetItem(dict, t); + if (!v) { + arg = PyDict_Size(dict); + v = PyInt_FromLong(arg); + if (!v) { + Py_DECREF(t); + return -1; + } + if (PyDict_SetItem(dict, t, v) < 0) { + Py_DECREF(t); + Py_DECREF(v); + return -1; + } + Py_DECREF(v); + } + else + arg = PyInt_AsLong(v); + Py_DECREF(t); + return arg; +} + +static int +compiler_addop_o(struct compiler *c, int opcode, PyObject *dict, + PyObject *o) +{ + int arg = compiler_add_o(c, dict, o); + if (arg < 0) + return 0; + return compiler_addop_i(c, opcode, arg); +} + +static int +compiler_addop_name(struct compiler *c, int opcode, PyObject *dict, + PyObject *o) +{ + int arg; + PyObject *mangled = _Py_Mangle(c->u->u_private, o); + if (!mangled) + return 0; + arg = compiler_add_o(c, dict, mangled); + Py_DECREF(mangled); + if (arg < 0) + return 0; + return compiler_addop_i(c, opcode, arg); +} + +/* Add an opcode with an integer argument. + Returns 0 on failure, 1 on success. +*/ + +static int +compiler_addop_i(struct compiler *c, int opcode, int oparg) +{ + struct instr *i; + int off; + off = compiler_next_instr(c, c->u->u_curblock); + if (off < 0) + return 0; + i = &c->u->u_curblock->b_instr[off]; + i->i_opcode = opcode; + i->i_oparg = oparg; + i->i_hasarg = 1; + compiler_set_lineno(c, off); + return 1; +} + +static int +compiler_addop_j(struct compiler *c, int opcode, basicblock *b, int absolute) +{ + struct instr *i; + int off; + + assert(b != NULL); + off = compiler_next_instr(c, c->u->u_curblock); + if (off < 0) + return 0; + i = &c->u->u_curblock->b_instr[off]; + i->i_opcode = opcode; + i->i_target = b; + i->i_hasarg = 1; + if (absolute) + i->i_jabs = 1; + else + i->i_jrel = 1; + compiler_set_lineno(c, off); + return 1; +} + +/* The distinction between NEW_BLOCK and NEXT_BLOCK is subtle. (I'd + like to find better names.) NEW_BLOCK() creates a new block and sets + it as the current block. NEXT_BLOCK() also creates an implicit jump + from the current block to the new block. +*/ + +/* The returns inside these macros make it impossible to decref objects + created in the local function. Local objects should use the arena. +*/ + + +#define NEW_BLOCK(C) { \ + if (compiler_use_new_block((C)) == NULL) \ + return 0; \ +} + +#define NEXT_BLOCK(C) { \ + if (compiler_next_block((C)) == NULL) \ + return 0; \ +} + +#define ADDOP(C, OP) { \ + if (!compiler_addop((C), (OP))) \ + return 0; \ +} + +#define ADDOP_IN_SCOPE(C, OP) { \ + if (!compiler_addop((C), (OP))) { \ + compiler_exit_scope(c); \ + return 0; \ + } \ +} + +#define ADDOP_O(C, OP, O, TYPE) { \ + if (!compiler_addop_o((C), (OP), (C)->u->u_ ## TYPE, (O))) \ + return 0; \ +} + +#define ADDOP_NAME(C, OP, O, TYPE) { \ + if (!compiler_addop_name((C), (OP), (C)->u->u_ ## TYPE, (O))) \ + return 0; \ +} + +#define ADDOP_I(C, OP, O) { \ + if (!compiler_addop_i((C), (OP), (O))) \ + return 0; \ +} + +#define ADDOP_JABS(C, OP, O) { \ + if (!compiler_addop_j((C), (OP), (O), 1)) \ + return 0; \ +} + +#define ADDOP_JREL(C, OP, O) { \ + if (!compiler_addop_j((C), (OP), (O), 0)) \ + return 0; \ +} + +/* VISIT and VISIT_SEQ takes an ASDL type as their second argument. They use + the ASDL name to synthesize the name of the C type and the visit function. +*/ + +#define VISIT(C, TYPE, V) {\ + if (!compiler_visit_ ## TYPE((C), (V))) \ + return 0; \ +} + +#define VISIT_IN_SCOPE(C, TYPE, V) {\ + if (!compiler_visit_ ## TYPE((C), (V))) { \ + compiler_exit_scope(c); \ + return 0; \ + } \ +} + +#define VISIT_SLICE(C, V, CTX) {\ + if (!compiler_visit_slice((C), (V), (CTX))) \ + return 0; \ +} + +#define VISIT_SEQ(C, TYPE, SEQ) { \ + int _i; \ + asdl_seq *seq = (SEQ); /* avoid variable capture */ \ + for (_i = 0; _i < asdl_seq_LEN(seq); _i++) { \ + TYPE ## _ty elt = (TYPE ## _ty)asdl_seq_GET(seq, _i); \ + if (!compiler_visit_ ## TYPE((C), elt)) \ + return 0; \ + } \ +} + +#define VISIT_SEQ_IN_SCOPE(C, TYPE, SEQ) { \ + int _i; \ + asdl_seq *seq = (SEQ); /* avoid variable capture */ \ + for (_i = 0; _i < asdl_seq_LEN(seq); _i++) { \ + TYPE ## _ty elt = (TYPE ## _ty)asdl_seq_GET(seq, _i); \ + if (!compiler_visit_ ## TYPE((C), elt)) { \ + compiler_exit_scope(c); \ + return 0; \ + } \ + } \ +} + +static int +compiler_isdocstring(stmt_ty s) +{ + if (s->kind != Expr_kind) + return 0; + return s->v.Expr.value->kind == Str_kind; +} + +/* Compile a sequence of statements, checking for a docstring. */ + +static int +compiler_body(struct compiler *c, asdl_seq *stmts) +{ + int i = 0; + stmt_ty st; + + if (!asdl_seq_LEN(stmts)) + return 1; + st = (stmt_ty)asdl_seq_GET(stmts, 0); + if (compiler_isdocstring(st) && Py_OptimizeFlag < 2) { + /* don't generate docstrings if -OO */ + i = 1; + VISIT(c, expr, st->v.Expr.value); + if (!compiler_nameop(c, __doc__, Store)) + return 0; + } + for (; i < asdl_seq_LEN(stmts); i++) + VISIT(c, stmt, (stmt_ty)asdl_seq_GET(stmts, i)); + return 1; +} + +static PyCodeObject * +compiler_mod(struct compiler *c, mod_ty mod) +{ + PyCodeObject *co; + int addNone = 1; + static PyObject *module; + if (!module) { + module = PyString_InternFromString(""); + if (!module) + return NULL; + } + /* Use 0 for firstlineno initially, will fixup in assemble(). */ + if (!compiler_enter_scope(c, module, mod, 0)) + return NULL; + switch (mod->kind) { + case Module_kind: + if (!compiler_body(c, mod->v.Module.body)) { + compiler_exit_scope(c); + return 0; + } + break; + case Interactive_kind: + c->c_interactive = 1; + VISIT_SEQ_IN_SCOPE(c, stmt, + mod->v.Interactive.body); + break; + case Expression_kind: + VISIT_IN_SCOPE(c, expr, mod->v.Expression.body); + addNone = 0; + break; + case Suite_kind: + PyErr_SetString(PyExc_SystemError, + "suite should not be possible"); + return 0; + default: + PyErr_Format(PyExc_SystemError, + "module kind %d should not be possible", + mod->kind); + return 0; + } + co = assemble(c, addNone); + compiler_exit_scope(c); + return co; +} + +/* The test for LOCAL must come before the test for FREE in order to + handle classes where name is both local and free. The local var is + a method and the free var is a free var referenced within a method. +*/ + +static int +get_ref_type(struct compiler *c, PyObject *name) +{ + int scope = PyST_GetScope(c->u->u_ste, name); + if (scope == 0) { + char buf[350]; + PyOS_snprintf(buf, sizeof(buf), + "unknown scope for %.100s in %.100s(%s) in %s\n" + "symbols: %s\nlocals: %s\nglobals: %s", + PyString_AS_STRING(name), + PyString_AS_STRING(c->u->u_name), + PyString_AS_STRING(PyObject_Repr(c->u->u_ste->ste_id)), + c->c_filename, + PyString_AS_STRING(PyObject_Repr(c->u->u_ste->ste_symbols)), + PyString_AS_STRING(PyObject_Repr(c->u->u_varnames)), + PyString_AS_STRING(PyObject_Repr(c->u->u_names)) + ); + Py_FatalError(buf); + } + + return scope; +} + +static int +compiler_lookup_arg(PyObject *dict, PyObject *name) +{ + PyObject *k, *v; + k = PyTuple_Pack(2, name, name->ob_type); + if (k == NULL) + return -1; + v = PyDict_GetItem(dict, k); + Py_DECREF(k); + if (v == NULL) + return -1; + return PyInt_AS_LONG(v); +} + +static int +compiler_make_closure(struct compiler *c, PyCodeObject *co, int args) +{ + int i, free = PyCode_GetNumFree(co); + if (free == 0) { + ADDOP_O(c, LOAD_CONST, (PyObject*)co, consts); + ADDOP_I(c, MAKE_FUNCTION, args); + return 1; + } + for (i = 0; i < free; ++i) { + /* Bypass com_addop_varname because it will generate + LOAD_DEREF but LOAD_CLOSURE is needed. + */ + PyObject *name = PyTuple_GET_ITEM(co->co_freevars, i); + int arg, reftype; + + /* Special case: If a class contains a method with a + free variable that has the same name as a method, + the name will be considered free *and* local in the + class. It should be handled by the closure, as + well as by the normal name loookup logic. + */ + reftype = get_ref_type(c, name); + if (reftype == CELL) + arg = compiler_lookup_arg(c->u->u_cellvars, name); + else /* (reftype == FREE) */ + arg = compiler_lookup_arg(c->u->u_freevars, name); + if (arg == -1) { + printf("lookup %s in %s %d %d\n" + "freevars of %s: %s\n", + PyString_AS_STRING(PyObject_Repr(name)), + PyString_AS_STRING(c->u->u_name), + reftype, arg, + PyString_AS_STRING(co->co_name), + PyString_AS_STRING(PyObject_Repr(co->co_freevars))); + Py_FatalError("compiler_make_closure()"); + } + ADDOP_I(c, LOAD_CLOSURE, arg); + } + ADDOP_I(c, BUILD_TUPLE, free); + ADDOP_O(c, LOAD_CONST, (PyObject*)co, consts); + ADDOP_I(c, MAKE_CLOSURE, args); + return 1; +} + +static int +compiler_decorators(struct compiler *c, asdl_seq* decos) +{ + int i; + + if (!decos) + return 1; + + for (i = 0; i < asdl_seq_LEN(decos); i++) { + VISIT(c, expr, (expr_ty)asdl_seq_GET(decos, i)); + } + return 1; +} + +static int +compiler_arguments(struct compiler *c, arguments_ty args) +{ + int i; + int n = asdl_seq_LEN(args->args); + /* Correctly handle nested argument lists */ + for (i = 0; i < n; i++) { + expr_ty arg = (expr_ty)asdl_seq_GET(args->args, i); + if (arg->kind == Tuple_kind) { + PyObject *id = PyString_FromFormat(".%d", i); + if (id == NULL) { + return 0; + } + if (!compiler_nameop(c, id, Load)) { + Py_DECREF(id); + return 0; + } + Py_DECREF(id); + VISIT(c, expr, arg); + } + } + return 1; +} + +static int +compiler_function(struct compiler *c, stmt_ty s) +{ + PyCodeObject *co; + PyObject *first_const = Py_None; + arguments_ty args = s->v.FunctionDef.args; + asdl_seq* decos = s->v.FunctionDef.decorator_list; + stmt_ty st; + int i, n, docstring; + + assert(s->kind == FunctionDef_kind); + + if (!compiler_decorators(c, decos)) + return 0; + if (args->defaults) + VISIT_SEQ(c, expr, args->defaults); + if (!compiler_enter_scope(c, s->v.FunctionDef.name, (void *)s, + s->lineno)) + return 0; + + st = (stmt_ty)asdl_seq_GET(s->v.FunctionDef.body, 0); + docstring = compiler_isdocstring(st); + if (docstring && Py_OptimizeFlag < 2) + first_const = st->v.Expr.value->v.Str.s; + if (compiler_add_o(c, c->u->u_consts, first_const) < 0) { + compiler_exit_scope(c); + return 0; + } + + /* unpack nested arguments */ + compiler_arguments(c, args); + + c->u->u_argcount = asdl_seq_LEN(args->args); + n = asdl_seq_LEN(s->v.FunctionDef.body); + /* if there was a docstring, we need to skip the first statement */ + for (i = docstring; i < n; i++) { + st = (stmt_ty)asdl_seq_GET(s->v.FunctionDef.body, i); + VISIT_IN_SCOPE(c, stmt, st); + } + co = assemble(c, 1); + compiler_exit_scope(c); + if (co == NULL) + return 0; + + compiler_make_closure(c, co, asdl_seq_LEN(args->defaults)); + Py_DECREF(co); + + for (i = 0; i < asdl_seq_LEN(decos); i++) { + ADDOP_I(c, CALL_FUNCTION, 1); + } + + return compiler_nameop(c, s->v.FunctionDef.name, Store); +} + +static int +compiler_class(struct compiler *c, stmt_ty s) +{ + int n, i; + PyCodeObject *co; + PyObject *str; + asdl_seq* decos = s->v.ClassDef.decorator_list; + + if (!compiler_decorators(c, decos)) + return 0; + + /* push class name on stack, needed by BUILD_CLASS */ + ADDOP_O(c, LOAD_CONST, s->v.ClassDef.name, consts); + /* push the tuple of base classes on the stack */ + n = asdl_seq_LEN(s->v.ClassDef.bases); + if (n > 0) + VISIT_SEQ(c, expr, s->v.ClassDef.bases); + ADDOP_I(c, BUILD_TUPLE, n); + if (!compiler_enter_scope(c, s->v.ClassDef.name, (void *)s, + s->lineno)) + return 0; + Py_XDECREF(c->u->u_private); + c->u->u_private = s->v.ClassDef.name; + Py_INCREF(c->u->u_private); + str = PyString_InternFromString("__name__"); + if (!str || !compiler_nameop(c, str, Load)) { + Py_XDECREF(str); + compiler_exit_scope(c); + return 0; + } + + Py_DECREF(str); + str = PyString_InternFromString("__module__"); + if (!str || !compiler_nameop(c, str, Store)) { + Py_XDECREF(str); + compiler_exit_scope(c); + return 0; + } + Py_DECREF(str); + + if (!compiler_body(c, s->v.ClassDef.body)) { + compiler_exit_scope(c); + return 0; + } + + ADDOP_IN_SCOPE(c, LOAD_LOCALS); + ADDOP_IN_SCOPE(c, RETURN_VALUE); + co = assemble(c, 1); + compiler_exit_scope(c); + if (co == NULL) + return 0; + + compiler_make_closure(c, co, 0); + Py_DECREF(co); + + ADDOP_I(c, CALL_FUNCTION, 0); + ADDOP(c, BUILD_CLASS); + /* apply decorators */ + for (i = 0; i < asdl_seq_LEN(decos); i++) { + ADDOP_I(c, CALL_FUNCTION, 1); + } + if (!compiler_nameop(c, s->v.ClassDef.name, Store)) + return 0; + return 1; +} + +static int +compiler_ifexp(struct compiler *c, expr_ty e) +{ + basicblock *end, *next; + + assert(e->kind == IfExp_kind); + end = compiler_new_block(c); + if (end == NULL) + return 0; + next = compiler_new_block(c); + if (next == NULL) + return 0; + VISIT(c, expr, e->v.IfExp.test); + ADDOP_JABS(c, POP_JUMP_IF_FALSE, next); + VISIT(c, expr, e->v.IfExp.body); + ADDOP_JREL(c, JUMP_FORWARD, end); + compiler_use_next_block(c, next); + VISIT(c, expr, e->v.IfExp.orelse); + compiler_use_next_block(c, end); + return 1; +} + +static int +compiler_lambda(struct compiler *c, expr_ty e) +{ + PyCodeObject *co; + static identifier name; + arguments_ty args = e->v.Lambda.args; + assert(e->kind == Lambda_kind); + + if (!name) { + name = PyString_InternFromString(""); + if (!name) + return 0; + } + + if (args->defaults) + VISIT_SEQ(c, expr, args->defaults); + if (!compiler_enter_scope(c, name, (void *)e, e->lineno)) + return 0; + + /* unpack nested arguments */ + compiler_arguments(c, args); + + /* Make None the first constant, so the lambda can't have a + docstring. */ + if (compiler_add_o(c, c->u->u_consts, Py_None) < 0) + return 0; + + c->u->u_argcount = asdl_seq_LEN(args->args); + VISIT_IN_SCOPE(c, expr, e->v.Lambda.body); + if (c->u->u_ste->ste_generator) { + ADDOP_IN_SCOPE(c, POP_TOP); + } + else { + ADDOP_IN_SCOPE(c, RETURN_VALUE); + } + co = assemble(c, 1); + compiler_exit_scope(c); + if (co == NULL) + return 0; + + compiler_make_closure(c, co, asdl_seq_LEN(args->defaults)); + Py_DECREF(co); + + return 1; +} + +static int +compiler_print(struct compiler *c, stmt_ty s) +{ + int i, n; + bool dest; + + assert(s->kind == Print_kind); + n = asdl_seq_LEN(s->v.Print.values); + dest = false; + if (s->v.Print.dest) { + VISIT(c, expr, s->v.Print.dest); + dest = true; + } + for (i = 0; i < n; i++) { + expr_ty e = (expr_ty)asdl_seq_GET(s->v.Print.values, i); + if (dest) { + ADDOP(c, DUP_TOP); + VISIT(c, expr, e); + ADDOP(c, ROT_TWO); + ADDOP(c, PRINT_ITEM_TO); + } + else { + VISIT(c, expr, e); + ADDOP(c, PRINT_ITEM); + } + } + if (s->v.Print.nl) { + if (dest) + ADDOP(c, PRINT_NEWLINE_TO) + else + ADDOP(c, PRINT_NEWLINE) + } + else if (dest) + ADDOP(c, POP_TOP); + return 1; +} + +static int +compiler_if(struct compiler *c, stmt_ty s) +{ + basicblock *end, *next; + int constant; + assert(s->kind == If_kind); + end = compiler_new_block(c); + if (end == NULL) + return 0; + + constant = expr_constant(s->v.If.test); + /* constant = 0: "if 0" + * constant = 1: "if 1", "if 2", ... + * constant = -1: rest */ + if (constant == 0) { + if (s->v.If.orelse) + VISIT_SEQ(c, stmt, s->v.If.orelse); + } else if (constant == 1) { + VISIT_SEQ(c, stmt, s->v.If.body); + } else { + if (s->v.If.orelse) { + next = compiler_new_block(c); + if (next == NULL) + return 0; + } + else + next = end; + VISIT(c, expr, s->v.If.test); + ADDOP_JABS(c, POP_JUMP_IF_FALSE, next); + VISIT_SEQ(c, stmt, s->v.If.body); + ADDOP_JREL(c, JUMP_FORWARD, end); + if (s->v.If.orelse) { + compiler_use_next_block(c, next); + VISIT_SEQ(c, stmt, s->v.If.orelse); + } + } + compiler_use_next_block(c, end); + return 1; +} + +static int +compiler_for(struct compiler *c, stmt_ty s) +{ + basicblock *start, *cleanup, *end; + + start = compiler_new_block(c); + cleanup = compiler_new_block(c); + end = compiler_new_block(c); + if (start == NULL || end == NULL || cleanup == NULL) + return 0; + ADDOP_JREL(c, SETUP_LOOP, end); + if (!compiler_push_fblock(c, LOOP, start)) + return 0; + VISIT(c, expr, s->v.For.iter); + ADDOP(c, GET_ITER); + compiler_use_next_block(c, start); + ADDOP_JREL(c, FOR_ITER, cleanup); + VISIT(c, expr, s->v.For.target); + VISIT_SEQ(c, stmt, s->v.For.body); + ADDOP_JABS(c, JUMP_ABSOLUTE, start); + compiler_use_next_block(c, cleanup); + ADDOP(c, POP_BLOCK); + compiler_pop_fblock(c, LOOP, start); + VISIT_SEQ(c, stmt, s->v.For.orelse); + compiler_use_next_block(c, end); + return 1; +} + +static int +compiler_while(struct compiler *c, stmt_ty s) +{ + basicblock *loop, *orelse, *end, *anchor = NULL; + int constant = expr_constant(s->v.While.test); + + if (constant == 0) { + if (s->v.While.orelse) + VISIT_SEQ(c, stmt, s->v.While.orelse); + return 1; + } + loop = compiler_new_block(c); + end = compiler_new_block(c); + if (constant == -1) { + anchor = compiler_new_block(c); + if (anchor == NULL) + return 0; + } + if (loop == NULL || end == NULL) + return 0; + if (s->v.While.orelse) { + orelse = compiler_new_block(c); + if (orelse == NULL) + return 0; + } + else + orelse = NULL; + + ADDOP_JREL(c, SETUP_LOOP, end); + compiler_use_next_block(c, loop); + if (!compiler_push_fblock(c, LOOP, loop)) + return 0; + if (constant == -1) { + VISIT(c, expr, s->v.While.test); + ADDOP_JABS(c, POP_JUMP_IF_FALSE, anchor); + } + VISIT_SEQ(c, stmt, s->v.While.body); + ADDOP_JABS(c, JUMP_ABSOLUTE, loop); + + /* XXX should the two POP instructions be in a separate block + if there is no else clause ? + */ + + if (constant == -1) + compiler_use_next_block(c, anchor); + ADDOP(c, POP_BLOCK); + compiler_pop_fblock(c, LOOP, loop); + if (orelse != NULL) /* what if orelse is just pass? */ + VISIT_SEQ(c, stmt, s->v.While.orelse); + compiler_use_next_block(c, end); + + return 1; +} + +static int +compiler_continue(struct compiler *c) +{ + static const char LOOP_ERROR_MSG[] = "'continue' not properly in loop"; + static const char IN_FINALLY_ERROR_MSG[] = + "'continue' not supported inside 'finally' clause"; + int i; + + if (!c->u->u_nfblocks) + return compiler_error(c, LOOP_ERROR_MSG); + i = c->u->u_nfblocks - 1; + switch (c->u->u_fblock[i].fb_type) { + case LOOP: + ADDOP_JABS(c, JUMP_ABSOLUTE, c->u->u_fblock[i].fb_block); + break; + case EXCEPT: + case FINALLY_TRY: + while (--i >= 0 && c->u->u_fblock[i].fb_type != LOOP) { + /* Prevent continue anywhere under a finally + even if hidden in a sub-try or except. */ + if (c->u->u_fblock[i].fb_type == FINALLY_END) + return compiler_error(c, IN_FINALLY_ERROR_MSG); + } + if (i == -1) + return compiler_error(c, LOOP_ERROR_MSG); + ADDOP_JABS(c, CONTINUE_LOOP, c->u->u_fblock[i].fb_block); + break; + case FINALLY_END: + return compiler_error(c, IN_FINALLY_ERROR_MSG); + } + + return 1; +} + +/* Code generated for "try: finally: " is as follows: + + SETUP_FINALLY L + + POP_BLOCK + LOAD_CONST + L: + END_FINALLY + + The special instructions use the block stack. Each block + stack entry contains the instruction that created it (here + SETUP_FINALLY), the level of the value stack at the time the + block stack entry was created, and a label (here L). + + SETUP_FINALLY: + Pushes the current value stack level and the label + onto the block stack. + POP_BLOCK: + Pops en entry from the block stack, and pops the value + stack until its level is the same as indicated on the + block stack. (The label is ignored.) + END_FINALLY: + Pops a variable number of entries from the *value* stack + and re-raises the exception they specify. The number of + entries popped depends on the (pseudo) exception type. + + The block stack is unwound when an exception is raised: + when a SETUP_FINALLY entry is found, the exception is pushed + onto the value stack (and the exception condition is cleared), + and the interpreter jumps to the label gotten from the block + stack. +*/ + +static int +compiler_try_finally(struct compiler *c, stmt_ty s) +{ + basicblock *body, *end; + body = compiler_new_block(c); + end = compiler_new_block(c); + if (body == NULL || end == NULL) + return 0; + + ADDOP_JREL(c, SETUP_FINALLY, end); + compiler_use_next_block(c, body); + if (!compiler_push_fblock(c, FINALLY_TRY, body)) + return 0; + VISIT_SEQ(c, stmt, s->v.TryFinally.body); + ADDOP(c, POP_BLOCK); + compiler_pop_fblock(c, FINALLY_TRY, body); + + ADDOP_O(c, LOAD_CONST, Py_None, consts); + compiler_use_next_block(c, end); + if (!compiler_push_fblock(c, FINALLY_END, end)) + return 0; + VISIT_SEQ(c, stmt, s->v.TryFinally.finalbody); + ADDOP(c, END_FINALLY); + compiler_pop_fblock(c, FINALLY_END, end); + + return 1; +} + +/* + Code generated for "try: S except E1, V1: S1 except E2, V2: S2 ...": + (The contents of the value stack is shown in [], with the top + at the right; 'tb' is trace-back info, 'val' the exception's + associated value, and 'exc' the exception.) + + Value stack Label Instruction Argument + [] SETUP_EXCEPT L1 + [] + [] POP_BLOCK + [] JUMP_FORWARD L0 + + [tb, val, exc] L1: DUP ) + [tb, val, exc, exc] ) + [tb, val, exc, exc, E1] COMPARE_OP EXC_MATCH ) only if E1 + [tb, val, exc, 1-or-0] POP_JUMP_IF_FALSE L2 ) + [tb, val, exc] POP + [tb, val] (or POP if no V1) + [tb] POP + [] + JUMP_FORWARD L0 + + [tb, val, exc] L2: DUP + .............................etc....................... + + [tb, val, exc] Ln+1: END_FINALLY # re-raise exception + + [] L0: + + Of course, parts are not generated if Vi or Ei is not present. +*/ +static int +compiler_try_except(struct compiler *c, stmt_ty s) +{ + basicblock *body, *orelse, *except, *end; + int i, n; + + body = compiler_new_block(c); + except = compiler_new_block(c); + orelse = compiler_new_block(c); + end = compiler_new_block(c); + if (body == NULL || except == NULL || orelse == NULL || end == NULL) + return 0; + ADDOP_JREL(c, SETUP_EXCEPT, except); + compiler_use_next_block(c, body); + if (!compiler_push_fblock(c, EXCEPT, body)) + return 0; + VISIT_SEQ(c, stmt, s->v.TryExcept.body); + ADDOP(c, POP_BLOCK); + compiler_pop_fblock(c, EXCEPT, body); + ADDOP_JREL(c, JUMP_FORWARD, orelse); + n = asdl_seq_LEN(s->v.TryExcept.handlers); + compiler_use_next_block(c, except); + for (i = 0; i < n; i++) { + excepthandler_ty handler = (excepthandler_ty)asdl_seq_GET( + s->v.TryExcept.handlers, i); + if (!handler->v.ExceptHandler.type && i < n-1) + return compiler_error(c, "default 'except:' must be last"); + c->u->u_lineno_set = false; + c->u->u_lineno = handler->lineno; + except = compiler_new_block(c); + if (except == NULL) + return 0; + if (handler->v.ExceptHandler.type) { + ADDOP(c, DUP_TOP); + VISIT(c, expr, handler->v.ExceptHandler.type); + ADDOP_I(c, COMPARE_OP, PyCmp_EXC_MATCH); + ADDOP_JABS(c, POP_JUMP_IF_FALSE, except); + } + ADDOP(c, POP_TOP); + if (handler->v.ExceptHandler.name) { + VISIT(c, expr, handler->v.ExceptHandler.name); + } + else { + ADDOP(c, POP_TOP); + } + ADDOP(c, POP_TOP); + VISIT_SEQ(c, stmt, handler->v.ExceptHandler.body); + ADDOP_JREL(c, JUMP_FORWARD, end); + compiler_use_next_block(c, except); + } + ADDOP(c, END_FINALLY); + compiler_use_next_block(c, orelse); + VISIT_SEQ(c, stmt, s->v.TryExcept.orelse); + compiler_use_next_block(c, end); + return 1; +} + +static int +compiler_import_as(struct compiler *c, identifier name, identifier asname) +{ + /* The IMPORT_NAME opcode was already generated. This function + merely needs to bind the result to a name. + + If there is a dot in name, we need to split it and emit a + LOAD_ATTR for each name. + */ + const char *src = PyString_AS_STRING(name); + const char *dot = strchr(src, '.'); + if (dot) { + /* Consume the base module name to get the first attribute */ + src = dot + 1; + while (dot) { + /* NB src is only defined when dot != NULL */ + PyObject *attr; + dot = strchr(src, '.'); + attr = PyString_FromStringAndSize(src, + dot ? dot - src : strlen(src)); + if (!attr) + return -1; + ADDOP_O(c, LOAD_ATTR, attr, names); + Py_DECREF(attr); + src = dot + 1; + } + } + return compiler_nameop(c, asname, Store); +} + +static int +compiler_import(struct compiler *c, stmt_ty s) +{ + /* The Import node stores a module name like a.b.c as a single + string. This is convenient for all cases except + import a.b.c as d + where we need to parse that string to extract the individual + module names. + XXX Perhaps change the representation to make this case simpler? + */ + int i, n = asdl_seq_LEN(s->v.Import.names); + + for (i = 0; i < n; i++) { + alias_ty alias = (alias_ty)asdl_seq_GET(s->v.Import.names, i); + int r; + PyObject *level; + + if (c->c_flags && (c->c_flags->cf_flags & CO_FUTURE_ABSOLUTE_IMPORT)) + level = PyInt_FromLong(0); + else + level = PyInt_FromLong(-1); + + if (level == NULL) + return 0; + + ADDOP_O(c, LOAD_CONST, level, consts); + Py_DECREF(level); + ADDOP_O(c, LOAD_CONST, Py_None, consts); + ADDOP_NAME(c, IMPORT_NAME, alias->name, names); + + if (alias->asname) { + r = compiler_import_as(c, alias->name, alias->asname); + if (!r) + return r; + } + else { + identifier tmp = alias->name; + const char *base = PyString_AS_STRING(alias->name); + char *dot = strchr(base, '.'); + if (dot) + tmp = PyString_FromStringAndSize(base, + dot - base); + r = compiler_nameop(c, tmp, Store); + if (dot) { + Py_DECREF(tmp); + } + if (!r) + return r; + } + } + return 1; +} + +static int +compiler_from_import(struct compiler *c, stmt_ty s) +{ + int i, n = asdl_seq_LEN(s->v.ImportFrom.names); + + PyObject *names = PyTuple_New(n); + PyObject *level; + static PyObject *empty_string; + + if (!empty_string) { + empty_string = PyString_FromString(""); + if (!empty_string) + return 0; + } + + if (!names) + return 0; + + if (s->v.ImportFrom.level == 0 && c->c_flags && + !(c->c_flags->cf_flags & CO_FUTURE_ABSOLUTE_IMPORT)) + level = PyInt_FromLong(-1); + else + level = PyInt_FromLong(s->v.ImportFrom.level); + + if (!level) { + Py_DECREF(names); + return 0; + } + + /* build up the names */ + for (i = 0; i < n; i++) { + alias_ty alias = (alias_ty)asdl_seq_GET(s->v.ImportFrom.names, i); + Py_INCREF(alias->name); + PyTuple_SET_ITEM(names, i, alias->name); + } + + if (s->lineno > c->c_future->ff_lineno && s->v.ImportFrom.module && + !strcmp(PyString_AS_STRING(s->v.ImportFrom.module), "__future__")) { + Py_DECREF(level); + Py_DECREF(names); + return compiler_error(c, "from __future__ imports must occur " + "at the beginning of the file"); + } + + ADDOP_O(c, LOAD_CONST, level, consts); + Py_DECREF(level); + ADDOP_O(c, LOAD_CONST, names, consts); + Py_DECREF(names); + if (s->v.ImportFrom.module) { + ADDOP_NAME(c, IMPORT_NAME, s->v.ImportFrom.module, names); + } + else { + ADDOP_NAME(c, IMPORT_NAME, empty_string, names); + } + for (i = 0; i < n; i++) { + alias_ty alias = (alias_ty)asdl_seq_GET(s->v.ImportFrom.names, i); + identifier store_name; + + if (i == 0 && *PyString_AS_STRING(alias->name) == '*') { + assert(n == 1); + ADDOP(c, IMPORT_STAR); + return 1; + } + + ADDOP_NAME(c, IMPORT_FROM, alias->name, names); + store_name = alias->name; + if (alias->asname) + store_name = alias->asname; + + if (!compiler_nameop(c, store_name, Store)) { + Py_DECREF(names); + return 0; + } + } + /* remove imported module */ + ADDOP(c, POP_TOP); + return 1; +} + +static int +compiler_assert(struct compiler *c, stmt_ty s) +{ + static PyObject *assertion_error = NULL; + basicblock *end; + + if (Py_OptimizeFlag) + return 1; + if (assertion_error == NULL) { + assertion_error = PyString_InternFromString("AssertionError"); + if (assertion_error == NULL) + return 0; + } + if (s->v.Assert.test->kind == Tuple_kind && + asdl_seq_LEN(s->v.Assert.test->v.Tuple.elts) > 0) { + const char* msg = + "assertion is always true, perhaps remove parentheses?"; + if (PyErr_WarnExplicit(PyExc_SyntaxWarning, msg, c->c_filename, + c->u->u_lineno, NULL, NULL) == -1) + return 0; + } + VISIT(c, expr, s->v.Assert.test); + end = compiler_new_block(c); + if (end == NULL) + return 0; + ADDOP_JABS(c, POP_JUMP_IF_TRUE, end); + ADDOP_O(c, LOAD_GLOBAL, assertion_error, names); + if (s->v.Assert.msg) { + VISIT(c, expr, s->v.Assert.msg); + ADDOP_I(c, CALL_FUNCTION, 1); + } + ADDOP_I(c, RAISE_VARARGS, 1); + compiler_use_next_block(c, end); + return 1; +} + +static int +compiler_visit_stmt(struct compiler *c, stmt_ty s) +{ + int i, n; + + /* Always assign a lineno to the next instruction for a stmt. */ + c->u->u_lineno = s->lineno; + c->u->u_lineno_set = false; + + switch (s->kind) { + case FunctionDef_kind: + return compiler_function(c, s); + case ClassDef_kind: + return compiler_class(c, s); + case Return_kind: + if (c->u->u_ste->ste_type != FunctionBlock) + return compiler_error(c, "'return' outside function"); + if (s->v.Return.value) { + VISIT(c, expr, s->v.Return.value); + } + else + ADDOP_O(c, LOAD_CONST, Py_None, consts); + ADDOP(c, RETURN_VALUE); + break; + case Delete_kind: + VISIT_SEQ(c, expr, s->v.Delete.targets) + break; + case Assign_kind: + n = asdl_seq_LEN(s->v.Assign.targets); + VISIT(c, expr, s->v.Assign.value); + for (i = 0; i < n; i++) { + if (i < n - 1) + ADDOP(c, DUP_TOP); + VISIT(c, expr, + (expr_ty)asdl_seq_GET(s->v.Assign.targets, i)); + } + break; + case AugAssign_kind: + return compiler_augassign(c, s); + case Print_kind: + return compiler_print(c, s); + case For_kind: + return compiler_for(c, s); + case While_kind: + return compiler_while(c, s); + case If_kind: + return compiler_if(c, s); + case Raise_kind: + n = 0; + if (s->v.Raise.type) { + VISIT(c, expr, s->v.Raise.type); + n++; + if (s->v.Raise.inst) { + VISIT(c, expr, s->v.Raise.inst); + n++; + if (s->v.Raise.tback) { + VISIT(c, expr, s->v.Raise.tback); + n++; + } + } + } + ADDOP_I(c, RAISE_VARARGS, n); + break; + case TryExcept_kind: + return compiler_try_except(c, s); + case TryFinally_kind: + return compiler_try_finally(c, s); + case Assert_kind: + return compiler_assert(c, s); + case Import_kind: + return compiler_import(c, s); + case ImportFrom_kind: + return compiler_from_import(c, s); + case Exec_kind: + VISIT(c, expr, s->v.Exec.body); + if (s->v.Exec.globals) { + VISIT(c, expr, s->v.Exec.globals); + if (s->v.Exec.locals) { + VISIT(c, expr, s->v.Exec.locals); + } else { + ADDOP(c, DUP_TOP); + } + } else { + ADDOP_O(c, LOAD_CONST, Py_None, consts); + ADDOP(c, DUP_TOP); + } + ADDOP(c, EXEC_STMT); + break; + case Global_kind: + break; + case Expr_kind: + if (c->c_interactive && c->c_nestlevel <= 1) { + VISIT(c, expr, s->v.Expr.value); + ADDOP(c, PRINT_EXPR); + } + else if (s->v.Expr.value->kind != Str_kind && + s->v.Expr.value->kind != Num_kind) { + VISIT(c, expr, s->v.Expr.value); + ADDOP(c, POP_TOP); + } + break; + case Pass_kind: + break; + case Break_kind: + if (!compiler_in_loop(c)) + return compiler_error(c, "'break' outside loop"); + ADDOP(c, BREAK_LOOP); + break; + case Continue_kind: + return compiler_continue(c); + case With_kind: + return compiler_with(c, s); + } + return 1; +} + +static int +unaryop(unaryop_ty op) +{ + switch (op) { + case Invert: + return UNARY_INVERT; + case Not: + return UNARY_NOT; + case UAdd: + return UNARY_POSITIVE; + case USub: + return UNARY_NEGATIVE; + default: + PyErr_Format(PyExc_SystemError, + "unary op %d should not be possible", op); + return 0; + } +} + +static int +binop(struct compiler *c, operator_ty op) +{ + switch (op) { + case Add: + return BINARY_ADD; + case Sub: + return BINARY_SUBTRACT; + case Mult: + return BINARY_MULTIPLY; + case Div: + if (c->c_flags && c->c_flags->cf_flags & CO_FUTURE_DIVISION) + return BINARY_TRUE_DIVIDE; + else + return BINARY_DIVIDE; + case Mod: + return BINARY_MODULO; + case Pow: + return BINARY_POWER; + case LShift: + return BINARY_LSHIFT; + case RShift: + return BINARY_RSHIFT; + case BitOr: + return BINARY_OR; + case BitXor: + return BINARY_XOR; + case BitAnd: + return BINARY_AND; + case FloorDiv: + return BINARY_FLOOR_DIVIDE; + default: + PyErr_Format(PyExc_SystemError, + "binary op %d should not be possible", op); + return 0; + } +} + +static int +cmpop(cmpop_ty op) +{ + switch (op) { + case Eq: + return PyCmp_EQ; + case NotEq: + return PyCmp_NE; + case Lt: + return PyCmp_LT; + case LtE: + return PyCmp_LE; + case Gt: + return PyCmp_GT; + case GtE: + return PyCmp_GE; + case Is: + return PyCmp_IS; + case IsNot: + return PyCmp_IS_NOT; + case In: + return PyCmp_IN; + case NotIn: + return PyCmp_NOT_IN; + default: + return PyCmp_BAD; + } +} + +static int +inplace_binop(struct compiler *c, operator_ty op) +{ + switch (op) { + case Add: + return INPLACE_ADD; + case Sub: + return INPLACE_SUBTRACT; + case Mult: + return INPLACE_MULTIPLY; + case Div: + if (c->c_flags && c->c_flags->cf_flags & CO_FUTURE_DIVISION) + return INPLACE_TRUE_DIVIDE; + else + return INPLACE_DIVIDE; + case Mod: + return INPLACE_MODULO; + case Pow: + return INPLACE_POWER; + case LShift: + return INPLACE_LSHIFT; + case RShift: + return INPLACE_RSHIFT; + case BitOr: + return INPLACE_OR; + case BitXor: + return INPLACE_XOR; + case BitAnd: + return INPLACE_AND; + case FloorDiv: + return INPLACE_FLOOR_DIVIDE; + default: + PyErr_Format(PyExc_SystemError, + "inplace binary op %d should not be possible", op); + return 0; + } +} + +static int +compiler_nameop(struct compiler *c, identifier name, expr_context_ty ctx) +{ + int op, scope, arg; + enum { OP_FAST, OP_GLOBAL, OP_DEREF, OP_NAME } optype; + + PyObject *dict = c->u->u_names; + PyObject *mangled; + /* XXX AugStore isn't used anywhere! */ + + mangled = _Py_Mangle(c->u->u_private, name); + if (!mangled) + return 0; + + op = 0; + optype = OP_NAME; + scope = PyST_GetScope(c->u->u_ste, mangled); + switch (scope) { + case FREE: + dict = c->u->u_freevars; + optype = OP_DEREF; + break; + case CELL: + dict = c->u->u_cellvars; + optype = OP_DEREF; + break; + case LOCAL: + if (c->u->u_ste->ste_type == FunctionBlock) + optype = OP_FAST; + break; + case GLOBAL_IMPLICIT: + if (c->u->u_ste->ste_type == FunctionBlock && + !c->u->u_ste->ste_unoptimized) + optype = OP_GLOBAL; + break; + case GLOBAL_EXPLICIT: + optype = OP_GLOBAL; + break; + default: + /* scope can be 0 */ + break; + } + + /* XXX Leave assert here, but handle __doc__ and the like better */ + assert(scope || PyString_AS_STRING(name)[0] == '_'); + + switch (optype) { + case OP_DEREF: + switch (ctx) { + case Load: op = LOAD_DEREF; break; + case Store: op = STORE_DEREF; break; + case AugLoad: + case AugStore: + break; + case Del: + PyErr_Format(PyExc_SyntaxError, + "can not delete variable '%s' referenced " + "in nested scope", + PyString_AS_STRING(name)); + Py_DECREF(mangled); + return 0; + case Param: + default: + PyErr_SetString(PyExc_SystemError, + "param invalid for deref variable"); + return 0; + } + break; + case OP_FAST: + switch (ctx) { + case Load: op = LOAD_FAST; break; + case Store: op = STORE_FAST; break; + case Del: op = DELETE_FAST; break; + case AugLoad: + case AugStore: + break; + case Param: + default: + PyErr_SetString(PyExc_SystemError, + "param invalid for local variable"); + return 0; + } + ADDOP_O(c, op, mangled, varnames); + Py_DECREF(mangled); + return 1; + case OP_GLOBAL: + switch (ctx) { + case Load: op = LOAD_GLOBAL; break; + case Store: op = STORE_GLOBAL; break; + case Del: op = DELETE_GLOBAL; break; + case AugLoad: + case AugStore: + break; + case Param: + default: + PyErr_SetString(PyExc_SystemError, + "param invalid for global variable"); + return 0; + } + break; + case OP_NAME: + switch (ctx) { + case Load: op = LOAD_NAME; break; + case Store: op = STORE_NAME; break; + case Del: op = DELETE_NAME; break; + case AugLoad: + case AugStore: + break; + case Param: + default: + PyErr_SetString(PyExc_SystemError, + "param invalid for name variable"); + return 0; + } + break; + } + + assert(op); + arg = compiler_add_o(c, dict, mangled); + Py_DECREF(mangled); + if (arg < 0) + return 0; + return compiler_addop_i(c, op, arg); +} + +static int +compiler_boolop(struct compiler *c, expr_ty e) +{ + basicblock *end; + int jumpi, i, n; + asdl_seq *s; + + assert(e->kind == BoolOp_kind); + if (e->v.BoolOp.op == And) + jumpi = JUMP_IF_FALSE_OR_POP; + else + jumpi = JUMP_IF_TRUE_OR_POP; + end = compiler_new_block(c); + if (end == NULL) + return 0; + s = e->v.BoolOp.values; + n = asdl_seq_LEN(s) - 1; + assert(n >= 0); + for (i = 0; i < n; ++i) { + VISIT(c, expr, (expr_ty)asdl_seq_GET(s, i)); + ADDOP_JABS(c, jumpi, end); + } + VISIT(c, expr, (expr_ty)asdl_seq_GET(s, n)); + compiler_use_next_block(c, end); + return 1; +} + +static int +compiler_list(struct compiler *c, expr_ty e) +{ + int n = asdl_seq_LEN(e->v.List.elts); + if (e->v.List.ctx == Store) { + ADDOP_I(c, UNPACK_SEQUENCE, n); + } + VISIT_SEQ(c, expr, e->v.List.elts); + if (e->v.List.ctx == Load) { + ADDOP_I(c, BUILD_LIST, n); + } + return 1; +} + +static int +compiler_tuple(struct compiler *c, expr_ty e) +{ + int n = asdl_seq_LEN(e->v.Tuple.elts); + if (e->v.Tuple.ctx == Store) { + ADDOP_I(c, UNPACK_SEQUENCE, n); + } + VISIT_SEQ(c, expr, e->v.Tuple.elts); + if (e->v.Tuple.ctx == Load) { + ADDOP_I(c, BUILD_TUPLE, n); + } + return 1; +} + +static int +compiler_compare(struct compiler *c, expr_ty e) +{ + int i, n; + basicblock *cleanup = NULL; + + /* XXX the logic can be cleaned up for 1 or multiple comparisons */ + VISIT(c, expr, e->v.Compare.left); + n = asdl_seq_LEN(e->v.Compare.ops); + assert(n > 0); + if (n > 1) { + cleanup = compiler_new_block(c); + if (cleanup == NULL) + return 0; + VISIT(c, expr, + (expr_ty)asdl_seq_GET(e->v.Compare.comparators, 0)); + } + for (i = 1; i < n; i++) { + ADDOP(c, DUP_TOP); + ADDOP(c, ROT_THREE); + ADDOP_I(c, COMPARE_OP, + cmpop((cmpop_ty)(asdl_seq_GET( + e->v.Compare.ops, i - 1)))); + ADDOP_JABS(c, JUMP_IF_FALSE_OR_POP, cleanup); + NEXT_BLOCK(c); + if (i < (n - 1)) + VISIT(c, expr, + (expr_ty)asdl_seq_GET(e->v.Compare.comparators, i)); + } + VISIT(c, expr, (expr_ty)asdl_seq_GET(e->v.Compare.comparators, n - 1)); + ADDOP_I(c, COMPARE_OP, + cmpop((cmpop_ty)(asdl_seq_GET(e->v.Compare.ops, n - 1)))); + if (n > 1) { + basicblock *end = compiler_new_block(c); + if (end == NULL) + return 0; + ADDOP_JREL(c, JUMP_FORWARD, end); + compiler_use_next_block(c, cleanup); + ADDOP(c, ROT_TWO); + ADDOP(c, POP_TOP); + compiler_use_next_block(c, end); + } + return 1; +} + +static int +compiler_call(struct compiler *c, expr_ty e) +{ + int n, code = 0; + + VISIT(c, expr, e->v.Call.func); + n = asdl_seq_LEN(e->v.Call.args); + VISIT_SEQ(c, expr, e->v.Call.args); + if (e->v.Call.keywords) { + VISIT_SEQ(c, keyword, e->v.Call.keywords); + n |= asdl_seq_LEN(e->v.Call.keywords) << 8; + } + if (e->v.Call.starargs) { + VISIT(c, expr, e->v.Call.starargs); + code |= 1; + } + if (e->v.Call.kwargs) { + VISIT(c, expr, e->v.Call.kwargs); + code |= 2; + } + switch (code) { + case 0: + ADDOP_I(c, CALL_FUNCTION, n); + break; + case 1: + ADDOP_I(c, CALL_FUNCTION_VAR, n); + break; + case 2: + ADDOP_I(c, CALL_FUNCTION_KW, n); + break; + case 3: + ADDOP_I(c, CALL_FUNCTION_VAR_KW, n); + break; + } + return 1; +} + +static int +compiler_listcomp_generator(struct compiler *c, asdl_seq *generators, + int gen_index, expr_ty elt) +{ + /* generate code for the iterator, then each of the ifs, + and then write to the element */ + + comprehension_ty l; + basicblock *start, *anchor, *skip, *if_cleanup; + int i, n; + + start = compiler_new_block(c); + skip = compiler_new_block(c); + if_cleanup = compiler_new_block(c); + anchor = compiler_new_block(c); + + if (start == NULL || skip == NULL || if_cleanup == NULL || + anchor == NULL) + return 0; + + l = (comprehension_ty)asdl_seq_GET(generators, gen_index); + VISIT(c, expr, l->iter); + ADDOP(c, GET_ITER); + compiler_use_next_block(c, start); + ADDOP_JREL(c, FOR_ITER, anchor); + NEXT_BLOCK(c); + VISIT(c, expr, l->target); + + /* XXX this needs to be cleaned up...a lot! */ + n = asdl_seq_LEN(l->ifs); + for (i = 0; i < n; i++) { + expr_ty e = (expr_ty)asdl_seq_GET(l->ifs, i); + VISIT(c, expr, e); + ADDOP_JABS(c, POP_JUMP_IF_FALSE, if_cleanup); + NEXT_BLOCK(c); + } + + if (++gen_index < asdl_seq_LEN(generators)) + if (!compiler_listcomp_generator(c, generators, gen_index, elt)) + return 0; + + /* only append after the last for generator */ + if (gen_index >= asdl_seq_LEN(generators)) { + VISIT(c, expr, elt); + ADDOP_I(c, LIST_APPEND, gen_index+1); + + compiler_use_next_block(c, skip); + } + compiler_use_next_block(c, if_cleanup); + ADDOP_JABS(c, JUMP_ABSOLUTE, start); + compiler_use_next_block(c, anchor); + + return 1; +} + +static int +compiler_listcomp(struct compiler *c, expr_ty e) +{ + assert(e->kind == ListComp_kind); + ADDOP_I(c, BUILD_LIST, 0); + return compiler_listcomp_generator(c, e->v.ListComp.generators, 0, + e->v.ListComp.elt); +} + +/* Dict and set comprehensions and generator expressions work by creating a + nested function to perform the actual iteration. This means that the + iteration variables don't leak into the current scope. + The defined function is called immediately following its definition, with the + result of that call being the result of the expression. + The LC/SC version returns the populated container, while the GE version is + flagged in symtable.c as a generator, so it returns the generator object + when the function is called. + This code *knows* that the loop cannot contain break, continue, or return, + so it cheats and skips the SETUP_LOOP/POP_BLOCK steps used in normal loops. + + Possible cleanups: + - iterate over the generator sequence instead of using recursion +*/ + +static int +compiler_comprehension_generator(struct compiler *c, + asdl_seq *generators, int gen_index, + expr_ty elt, expr_ty val, int type) +{ + /* generate code for the iterator, then each of the ifs, + and then write to the element */ + + comprehension_ty gen; + basicblock *start, *anchor, *skip, *if_cleanup; + int i, n; + + start = compiler_new_block(c); + skip = compiler_new_block(c); + if_cleanup = compiler_new_block(c); + anchor = compiler_new_block(c); + + if (start == NULL || skip == NULL || if_cleanup == NULL || + anchor == NULL) + return 0; + + gen = (comprehension_ty)asdl_seq_GET(generators, gen_index); + + if (gen_index == 0) { + /* Receive outermost iter as an implicit argument */ + c->u->u_argcount = 1; + ADDOP_I(c, LOAD_FAST, 0); + } + else { + /* Sub-iter - calculate on the fly */ + VISIT(c, expr, gen->iter); + ADDOP(c, GET_ITER); + } + compiler_use_next_block(c, start); + ADDOP_JREL(c, FOR_ITER, anchor); + NEXT_BLOCK(c); + VISIT(c, expr, gen->target); + + /* XXX this needs to be cleaned up...a lot! */ + n = asdl_seq_LEN(gen->ifs); + for (i = 0; i < n; i++) { + expr_ty e = (expr_ty)asdl_seq_GET(gen->ifs, i); + VISIT(c, expr, e); + ADDOP_JABS(c, POP_JUMP_IF_FALSE, if_cleanup); + NEXT_BLOCK(c); + } + + if (++gen_index < asdl_seq_LEN(generators)) + if (!compiler_comprehension_generator(c, + generators, gen_index, + elt, val, type)) + return 0; + + /* only append after the last for generator */ + if (gen_index >= asdl_seq_LEN(generators)) { + /* comprehension specific code */ + switch (type) { + case COMP_GENEXP: + VISIT(c, expr, elt); + ADDOP(c, YIELD_VALUE); + ADDOP(c, POP_TOP); + break; + case COMP_SETCOMP: + VISIT(c, expr, elt); + ADDOP_I(c, SET_ADD, gen_index + 1); + break; + case COMP_DICTCOMP: + /* With 'd[k] = v', v is evaluated before k, so we do + the same. */ + VISIT(c, expr, val); + VISIT(c, expr, elt); + ADDOP_I(c, MAP_ADD, gen_index + 1); + break; + default: + return 0; + } + + compiler_use_next_block(c, skip); + } + compiler_use_next_block(c, if_cleanup); + ADDOP_JABS(c, JUMP_ABSOLUTE, start); + compiler_use_next_block(c, anchor); + + return 1; +} + +static int +compiler_comprehension(struct compiler *c, expr_ty e, int type, identifier name, + asdl_seq *generators, expr_ty elt, expr_ty val) +{ + PyCodeObject *co = NULL; + expr_ty outermost_iter; + + outermost_iter = ((comprehension_ty) + asdl_seq_GET(generators, 0))->iter; + + if (!compiler_enter_scope(c, name, (void *)e, e->lineno)) + goto error; + + if (type != COMP_GENEXP) { + int op; + switch (type) { + case COMP_SETCOMP: + op = BUILD_SET; + break; + case COMP_DICTCOMP: + op = BUILD_MAP; + break; + default: + PyErr_Format(PyExc_SystemError, + "unknown comprehension type %d", type); + goto error_in_scope; + } + + ADDOP_I(c, op, 0); + } + + if (!compiler_comprehension_generator(c, generators, 0, elt, + val, type)) + goto error_in_scope; + + if (type != COMP_GENEXP) { + ADDOP(c, RETURN_VALUE); + } + + co = assemble(c, 1); + compiler_exit_scope(c); + if (co == NULL) + goto error; + + if (!compiler_make_closure(c, co, 0)) + goto error; + Py_DECREF(co); + + VISIT(c, expr, outermost_iter); + ADDOP(c, GET_ITER); + ADDOP_I(c, CALL_FUNCTION, 1); + return 1; +error_in_scope: + compiler_exit_scope(c); +error: + Py_XDECREF(co); + return 0; +} + +static int +compiler_genexp(struct compiler *c, expr_ty e) +{ + static identifier name; + if (!name) { + name = PyString_FromString(""); + if (!name) + return 0; + } + assert(e->kind == GeneratorExp_kind); + return compiler_comprehension(c, e, COMP_GENEXP, name, + e->v.GeneratorExp.generators, + e->v.GeneratorExp.elt, NULL); +} + +static int +compiler_setcomp(struct compiler *c, expr_ty e) +{ + static identifier name; + if (!name) { + name = PyString_FromString(""); + if (!name) + return 0; + } + assert(e->kind == SetComp_kind); + return compiler_comprehension(c, e, COMP_SETCOMP, name, + e->v.SetComp.generators, + e->v.SetComp.elt, NULL); +} + +static int +compiler_dictcomp(struct compiler *c, expr_ty e) +{ + static identifier name; + if (!name) { + name = PyString_FromString(""); + if (!name) + return 0; + } + assert(e->kind == DictComp_kind); + return compiler_comprehension(c, e, COMP_DICTCOMP, name, + e->v.DictComp.generators, + e->v.DictComp.key, e->v.DictComp.value); +} + +static int +compiler_visit_keyword(struct compiler *c, keyword_ty k) +{ + ADDOP_O(c, LOAD_CONST, k->arg, consts); + VISIT(c, expr, k->value); + return 1; +} + +/* Test whether expression is constant. For constants, report + whether they are true or false. + + Return values: 1 for true, 0 for false, -1 for non-constant. + */ + +static int +expr_constant(expr_ty e) +{ + switch (e->kind) { + case Num_kind: + return PyObject_IsTrue(e->v.Num.n); + case Str_kind: + return PyObject_IsTrue(e->v.Str.s); + case Name_kind: + /* __debug__ is not assignable, so we can optimize + * it away in if and while statements */ + if (strcmp(PyString_AS_STRING(e->v.Name.id), + "__debug__") == 0) + return ! Py_OptimizeFlag; + /* fall through */ + default: + return -1; + } +} + +/* + Implements the with statement from PEP 343. + + The semantics outlined in that PEP are as follows: + + with EXPR as VAR: + BLOCK + + It is implemented roughly as: + + context = EXPR + exit = context.__exit__ # not calling it + value = context.__enter__() + try: + VAR = value # if VAR present in the syntax + BLOCK + finally: + if an exception was raised: + exc = copy of (exception, instance, traceback) + else: + exc = (None, None, None) + exit(*exc) + */ +static int +compiler_with(struct compiler *c, stmt_ty s) +{ + basicblock *block, *finally; + + assert(s->kind == With_kind); + + block = compiler_new_block(c); + finally = compiler_new_block(c); + if (!block || !finally) + return 0; + + /* Evaluate EXPR */ + VISIT(c, expr, s->v.With.context_expr); + ADDOP_JREL(c, SETUP_WITH, finally); + + /* SETUP_WITH pushes a finally block. */ + compiler_use_next_block(c, block); + /* Note that the block is actually called SETUP_WITH in ceval.c, but + functions the same as SETUP_FINALLY except that exceptions are + normalized. */ + if (!compiler_push_fblock(c, FINALLY_TRY, block)) { + return 0; + } + + if (s->v.With.optional_vars) { + VISIT(c, expr, s->v.With.optional_vars); + } + else { + /* Discard result from context.__enter__() */ + ADDOP(c, POP_TOP); + } + + /* BLOCK code */ + VISIT_SEQ(c, stmt, s->v.With.body); + + /* End of try block; start the finally block */ + ADDOP(c, POP_BLOCK); + compiler_pop_fblock(c, FINALLY_TRY, block); + + ADDOP_O(c, LOAD_CONST, Py_None, consts); + compiler_use_next_block(c, finally); + if (!compiler_push_fblock(c, FINALLY_END, finally)) + return 0; + + /* Finally block starts; context.__exit__ is on the stack under + the exception or return information. Just issue our magic + opcode. */ + ADDOP(c, WITH_CLEANUP); + + /* Finally block ends. */ + ADDOP(c, END_FINALLY); + compiler_pop_fblock(c, FINALLY_END, finally); + return 1; +} + +static int +compiler_visit_expr(struct compiler *c, expr_ty e) +{ + int i, n; + + /* If expr e has a different line number than the last expr/stmt, + set a new line number for the next instruction. + */ + if (e->lineno > c->u->u_lineno) { + c->u->u_lineno = e->lineno; + c->u->u_lineno_set = false; + } + switch (e->kind) { + case BoolOp_kind: + return compiler_boolop(c, e); + case BinOp_kind: + VISIT(c, expr, e->v.BinOp.left); + VISIT(c, expr, e->v.BinOp.right); + ADDOP(c, binop(c, e->v.BinOp.op)); + break; + case UnaryOp_kind: + VISIT(c, expr, e->v.UnaryOp.operand); + ADDOP(c, unaryop(e->v.UnaryOp.op)); + break; + case Lambda_kind: + return compiler_lambda(c, e); + case IfExp_kind: + return compiler_ifexp(c, e); + case Dict_kind: + n = asdl_seq_LEN(e->v.Dict.values); + ADDOP_I(c, BUILD_MAP, (n>0xFFFF ? 0xFFFF : n)); + for (i = 0; i < n; i++) { + VISIT(c, expr, + (expr_ty)asdl_seq_GET(e->v.Dict.values, i)); + VISIT(c, expr, + (expr_ty)asdl_seq_GET(e->v.Dict.keys, i)); + ADDOP(c, STORE_MAP); + } + break; + case Set_kind: + n = asdl_seq_LEN(e->v.Set.elts); + VISIT_SEQ(c, expr, e->v.Set.elts); + ADDOP_I(c, BUILD_SET, n); + break; + case ListComp_kind: + return compiler_listcomp(c, e); + case SetComp_kind: + return compiler_setcomp(c, e); + case DictComp_kind: + return compiler_dictcomp(c, e); + case GeneratorExp_kind: + return compiler_genexp(c, e); + case Yield_kind: + if (c->u->u_ste->ste_type != FunctionBlock) + return compiler_error(c, "'yield' outside function"); + if (e->v.Yield.value) { + VISIT(c, expr, e->v.Yield.value); + } + else { + ADDOP_O(c, LOAD_CONST, Py_None, consts); + } + ADDOP(c, YIELD_VALUE); + break; + case Compare_kind: + return compiler_compare(c, e); + case Call_kind: + return compiler_call(c, e); + case Repr_kind: + VISIT(c, expr, e->v.Repr.value); + ADDOP(c, UNARY_CONVERT); + break; + case Num_kind: + ADDOP_O(c, LOAD_CONST, e->v.Num.n, consts); + break; + case Str_kind: + ADDOP_O(c, LOAD_CONST, e->v.Str.s, consts); + break; + /* The following exprs can be assignment targets. */ + case Attribute_kind: + if (e->v.Attribute.ctx != AugStore) + VISIT(c, expr, e->v.Attribute.value); + switch (e->v.Attribute.ctx) { + case AugLoad: + ADDOP(c, DUP_TOP); + /* Fall through to load */ + case Load: + ADDOP_NAME(c, LOAD_ATTR, e->v.Attribute.attr, names); + break; + case AugStore: + ADDOP(c, ROT_TWO); + /* Fall through to save */ + case Store: + ADDOP_NAME(c, STORE_ATTR, e->v.Attribute.attr, names); + break; + case Del: + ADDOP_NAME(c, DELETE_ATTR, e->v.Attribute.attr, names); + break; + case Param: + default: + PyErr_SetString(PyExc_SystemError, + "param invalid in attribute expression"); + return 0; + } + break; + case Subscript_kind: + switch (e->v.Subscript.ctx) { + case AugLoad: + VISIT(c, expr, e->v.Subscript.value); + VISIT_SLICE(c, e->v.Subscript.slice, AugLoad); + break; + case Load: + VISIT(c, expr, e->v.Subscript.value); + VISIT_SLICE(c, e->v.Subscript.slice, Load); + break; + case AugStore: + VISIT_SLICE(c, e->v.Subscript.slice, AugStore); + break; + case Store: + VISIT(c, expr, e->v.Subscript.value); + VISIT_SLICE(c, e->v.Subscript.slice, Store); + break; + case Del: + VISIT(c, expr, e->v.Subscript.value); + VISIT_SLICE(c, e->v.Subscript.slice, Del); + break; + case Param: + default: + PyErr_SetString(PyExc_SystemError, + "param invalid in subscript expression"); + return 0; + } + break; + case Name_kind: + return compiler_nameop(c, e->v.Name.id, e->v.Name.ctx); + /* child nodes of List and Tuple will have expr_context set */ + case List_kind: + return compiler_list(c, e); + case Tuple_kind: + return compiler_tuple(c, e); + } + return 1; +} + +static int +compiler_augassign(struct compiler *c, stmt_ty s) +{ + expr_ty e = s->v.AugAssign.target; + expr_ty auge; + + assert(s->kind == AugAssign_kind); + + switch (e->kind) { + case Attribute_kind: + auge = Attribute(e->v.Attribute.value, e->v.Attribute.attr, + AugLoad, e->lineno, e->col_offset, c->c_arena); + if (auge == NULL) + return 0; + VISIT(c, expr, auge); + VISIT(c, expr, s->v.AugAssign.value); + ADDOP(c, inplace_binop(c, s->v.AugAssign.op)); + auge->v.Attribute.ctx = AugStore; + VISIT(c, expr, auge); + break; + case Subscript_kind: + auge = Subscript(e->v.Subscript.value, e->v.Subscript.slice, + AugLoad, e->lineno, e->col_offset, c->c_arena); + if (auge == NULL) + return 0; + VISIT(c, expr, auge); + VISIT(c, expr, s->v.AugAssign.value); + ADDOP(c, inplace_binop(c, s->v.AugAssign.op)); + auge->v.Subscript.ctx = AugStore; + VISIT(c, expr, auge); + break; + case Name_kind: + if (!compiler_nameop(c, e->v.Name.id, Load)) + return 0; + VISIT(c, expr, s->v.AugAssign.value); + ADDOP(c, inplace_binop(c, s->v.AugAssign.op)); + return compiler_nameop(c, e->v.Name.id, Store); + default: + PyErr_Format(PyExc_SystemError, + "invalid node type (%d) for augmented assignment", + e->kind); + return 0; + } + return 1; +} + +static int +compiler_push_fblock(struct compiler *c, enum fblocktype t, basicblock *b) +{ + struct fblockinfo *f; + if (c->u->u_nfblocks >= CO_MAXBLOCKS) { + PyErr_SetString(PyExc_SystemError, + "too many statically nested blocks"); + return 0; + } + f = &c->u->u_fblock[c->u->u_nfblocks++]; + f->fb_type = t; + f->fb_block = b; + return 1; +} + +static void +compiler_pop_fblock(struct compiler *c, enum fblocktype t, basicblock *b) +{ + struct compiler_unit *u = c->u; + assert(u->u_nfblocks > 0); + u->u_nfblocks--; + assert(u->u_fblock[u->u_nfblocks].fb_type == t); + assert(u->u_fblock[u->u_nfblocks].fb_block == b); +} + +static int +compiler_in_loop(struct compiler *c) { + int i; + struct compiler_unit *u = c->u; + for (i = 0; i < u->u_nfblocks; ++i) { + if (u->u_fblock[i].fb_type == LOOP) + return 1; + } + return 0; +} +/* Raises a SyntaxError and returns 0. + If something goes wrong, a different exception may be raised. +*/ + +static int +compiler_error(struct compiler *c, const char *errstr) +{ + PyObject *loc; + PyObject *u = NULL, *v = NULL; + + loc = PyErr_ProgramText(c->c_filename, c->u->u_lineno); + if (!loc) { + Py_INCREF(Py_None); + loc = Py_None; + } + u = Py_BuildValue("(ziOO)", c->c_filename, c->u->u_lineno, + Py_None, loc); + if (!u) + goto exit; + v = Py_BuildValue("(zO)", errstr, u); + if (!v) + goto exit; + PyErr_SetObject(PyExc_SyntaxError, v); + exit: + Py_DECREF(loc); + Py_XDECREF(u); + Py_XDECREF(v); + return 0; +} + +static int +compiler_handle_subscr(struct compiler *c, const char *kind, + expr_context_ty ctx) +{ + int op = 0; + + /* XXX this code is duplicated */ + switch (ctx) { + case AugLoad: /* fall through to Load */ + case Load: op = BINARY_SUBSCR; break; + case AugStore:/* fall through to Store */ + case Store: op = STORE_SUBSCR; break; + case Del: op = DELETE_SUBSCR; break; + case Param: + PyErr_Format(PyExc_SystemError, + "invalid %s kind %d in subscript\n", + kind, ctx); + return 0; + } + if (ctx == AugLoad) { + ADDOP_I(c, DUP_TOPX, 2); + } + else if (ctx == AugStore) { + ADDOP(c, ROT_THREE); + } + ADDOP(c, op); + return 1; +} + +static int +compiler_slice(struct compiler *c, slice_ty s, expr_context_ty ctx) +{ + int n = 2; + assert(s->kind == Slice_kind); + + /* only handles the cases where BUILD_SLICE is emitted */ + if (s->v.Slice.lower) { + VISIT(c, expr, s->v.Slice.lower); + } + else { + ADDOP_O(c, LOAD_CONST, Py_None, consts); + } + + if (s->v.Slice.upper) { + VISIT(c, expr, s->v.Slice.upper); + } + else { + ADDOP_O(c, LOAD_CONST, Py_None, consts); + } + + if (s->v.Slice.step) { + n++; + VISIT(c, expr, s->v.Slice.step); + } + ADDOP_I(c, BUILD_SLICE, n); + return 1; +} + +static int +compiler_simple_slice(struct compiler *c, slice_ty s, expr_context_ty ctx) +{ + int op = 0, slice_offset = 0, stack_count = 0; + + assert(s->v.Slice.step == NULL); + if (s->v.Slice.lower) { + slice_offset++; + stack_count++; + if (ctx != AugStore) + VISIT(c, expr, s->v.Slice.lower); + } + if (s->v.Slice.upper) { + slice_offset += 2; + stack_count++; + if (ctx != AugStore) + VISIT(c, expr, s->v.Slice.upper); + } + + if (ctx == AugLoad) { + switch (stack_count) { + case 0: ADDOP(c, DUP_TOP); break; + case 1: ADDOP_I(c, DUP_TOPX, 2); break; + case 2: ADDOP_I(c, DUP_TOPX, 3); break; + } + } + else if (ctx == AugStore) { + switch (stack_count) { + case 0: ADDOP(c, ROT_TWO); break; + case 1: ADDOP(c, ROT_THREE); break; + case 2: ADDOP(c, ROT_FOUR); break; + } + } + + switch (ctx) { + case AugLoad: /* fall through to Load */ + case Load: op = SLICE; break; + case AugStore:/* fall through to Store */ + case Store: op = STORE_SLICE; break; + case Del: op = DELETE_SLICE; break; + case Param: + default: + PyErr_SetString(PyExc_SystemError, + "param invalid in simple slice"); + return 0; + } + + ADDOP(c, op + slice_offset); + return 1; +} + +static int +compiler_visit_nested_slice(struct compiler *c, slice_ty s, + expr_context_ty ctx) +{ + switch (s->kind) { + case Ellipsis_kind: + ADDOP_O(c, LOAD_CONST, Py_Ellipsis, consts); + break; + case Slice_kind: + return compiler_slice(c, s, ctx); + case Index_kind: + VISIT(c, expr, s->v.Index.value); + break; + case ExtSlice_kind: + default: + PyErr_SetString(PyExc_SystemError, + "extended slice invalid in nested slice"); + return 0; + } + return 1; +} + +static int +compiler_visit_slice(struct compiler *c, slice_ty s, expr_context_ty ctx) +{ + char * kindname = NULL; + switch (s->kind) { + case Index_kind: + kindname = "index"; + if (ctx != AugStore) { + VISIT(c, expr, s->v.Index.value); + } + break; + case Ellipsis_kind: + kindname = "ellipsis"; + if (ctx != AugStore) { + ADDOP_O(c, LOAD_CONST, Py_Ellipsis, consts); + } + break; + case Slice_kind: + kindname = "slice"; + if (!s->v.Slice.step) + return compiler_simple_slice(c, s, ctx); + if (ctx != AugStore) { + if (!compiler_slice(c, s, ctx)) + return 0; + } + break; + case ExtSlice_kind: + kindname = "extended slice"; + if (ctx != AugStore) { + int i, n = asdl_seq_LEN(s->v.ExtSlice.dims); + for (i = 0; i < n; i++) { + slice_ty sub = (slice_ty)asdl_seq_GET( + s->v.ExtSlice.dims, i); + if (!compiler_visit_nested_slice(c, sub, ctx)) + return 0; + } + ADDOP_I(c, BUILD_TUPLE, n); + } + break; + default: + PyErr_Format(PyExc_SystemError, + "invalid subscript kind %d", s->kind); + return 0; + } + return compiler_handle_subscr(c, kindname, ctx); +} + + +/* End of the compiler section, beginning of the assembler section */ + +/* do depth-first search of basic block graph, starting with block. + post records the block indices in post-order. + + XXX must handle implicit jumps from one block to next +*/ + +struct assembler { + PyObject *a_bytecode; /* string containing bytecode */ + int a_offset; /* offset into bytecode */ + int a_nblocks; /* number of reachable blocks */ + basicblock **a_postorder; /* list of blocks in dfs postorder */ + PyObject *a_lnotab; /* string containing lnotab */ + int a_lnotab_off; /* offset into lnotab */ + int a_lineno; /* last lineno of emitted instruction */ + int a_lineno_off; /* bytecode offset of last lineno */ +}; + +static void +dfs(struct compiler *c, basicblock *b, struct assembler *a) +{ + int i; + struct instr *instr = NULL; + + if (b->b_seen) + return; + b->b_seen = 1; + if (b->b_next != NULL) + dfs(c, b->b_next, a); + for (i = 0; i < b->b_iused; i++) { + instr = &b->b_instr[i]; + if (instr->i_jrel || instr->i_jabs) + dfs(c, instr->i_target, a); + } + a->a_postorder[a->a_nblocks++] = b; +} + +static int +stackdepth_walk(struct compiler *c, basicblock *b, int depth, int maxdepth) +{ + int i, target_depth; + struct instr *instr; + if (b->b_seen || b->b_startdepth >= depth) + return maxdepth; + b->b_seen = 1; + b->b_startdepth = depth; + for (i = 0; i < b->b_iused; i++) { + instr = &b->b_instr[i]; + depth += opcode_stack_effect(instr->i_opcode, instr->i_oparg); + if (depth > maxdepth) + maxdepth = depth; + assert(depth >= 0); /* invalid code or bug in stackdepth() */ + if (instr->i_jrel || instr->i_jabs) { + target_depth = depth; + if (instr->i_opcode == FOR_ITER) { + target_depth = depth-2; + } + else if (instr->i_opcode == SETUP_FINALLY || + instr->i_opcode == SETUP_EXCEPT) { + target_depth = depth+3; + if (target_depth > maxdepth) + maxdepth = target_depth; + } + else if (instr->i_opcode == JUMP_IF_TRUE_OR_POP || + instr->i_opcode == JUMP_IF_FALSE_OR_POP) + depth = depth - 1; + maxdepth = stackdepth_walk(c, instr->i_target, + target_depth, maxdepth); + if (instr->i_opcode == JUMP_ABSOLUTE || + instr->i_opcode == JUMP_FORWARD) { + goto out; /* remaining code is dead */ + } + } + } + if (b->b_next) + maxdepth = stackdepth_walk(c, b->b_next, depth, maxdepth); +out: + b->b_seen = 0; + return maxdepth; +} + +/* Find the flow path that needs the largest stack. We assume that + * cycles in the flow graph have no net effect on the stack depth. + */ +static int +stackdepth(struct compiler *c) +{ + basicblock *b, *entryblock; + entryblock = NULL; + for (b = c->u->u_blocks; b != NULL; b = b->b_list) { + b->b_seen = 0; + b->b_startdepth = INT_MIN; + entryblock = b; + } + if (!entryblock) + return 0; + return stackdepth_walk(c, entryblock, 0, 0); +} + +static int +assemble_init(struct assembler *a, int nblocks, int firstlineno) +{ + memset(a, 0, sizeof(struct assembler)); + a->a_lineno = firstlineno; + a->a_bytecode = PyString_FromStringAndSize(NULL, DEFAULT_CODE_SIZE); + if (!a->a_bytecode) + return 0; + a->a_lnotab = PyString_FromStringAndSize(NULL, DEFAULT_LNOTAB_SIZE); + if (!a->a_lnotab) + return 0; + if (nblocks > PY_SIZE_MAX / sizeof(basicblock *)) { + PyErr_NoMemory(); + return 0; + } + a->a_postorder = (basicblock **)PyObject_Malloc( + sizeof(basicblock *) * nblocks); + if (!a->a_postorder) { + PyErr_NoMemory(); + return 0; + } + return 1; +} + +static void +assemble_free(struct assembler *a) +{ + Py_XDECREF(a->a_bytecode); + Py_XDECREF(a->a_lnotab); + if (a->a_postorder) + PyObject_Free(a->a_postorder); +} + +/* Return the size of a basic block in bytes. */ + +static int +instrsize(struct instr *instr) +{ + if (!instr->i_hasarg) + return 1; /* 1 byte for the opcode*/ + if (instr->i_oparg > 0xffff) + return 6; /* 1 (opcode) + 1 (EXTENDED_ARG opcode) + 2 (oparg) + 2(oparg extended) */ + return 3; /* 1 (opcode) + 2 (oparg) */ +} + +static int +blocksize(basicblock *b) +{ + int i; + int size = 0; + + for (i = 0; i < b->b_iused; i++) + size += instrsize(&b->b_instr[i]); + return size; +} + +/* Appends a pair to the end of the line number table, a_lnotab, representing + the instruction's bytecode offset and line number. See + Objects/lnotab_notes.txt for the description of the line number table. */ + +static int +assemble_lnotab(struct assembler *a, struct instr *i) +{ + int d_bytecode, d_lineno; + int len; + unsigned char *lnotab; + + d_bytecode = a->a_offset - a->a_lineno_off; + d_lineno = i->i_lineno - a->a_lineno; + + assert(d_bytecode >= 0); + assert(d_lineno >= 0); + + if(d_bytecode == 0 && d_lineno == 0) + return 1; + + if (d_bytecode > 255) { + int j, nbytes, ncodes = d_bytecode / 255; + nbytes = a->a_lnotab_off + 2 * ncodes; + len = PyString_GET_SIZE(a->a_lnotab); + if (nbytes >= len) { + if ((len <= INT_MAX / 2) && (len * 2 < nbytes)) + len = nbytes; + else if (len <= INT_MAX / 2) + len *= 2; + else { + PyErr_NoMemory(); + return 0; + } + if (_PyString_Resize(&a->a_lnotab, len) < 0) + return 0; + } + lnotab = (unsigned char *) + PyString_AS_STRING(a->a_lnotab) + a->a_lnotab_off; + for (j = 0; j < ncodes; j++) { + *lnotab++ = 255; + *lnotab++ = 0; + } + d_bytecode -= ncodes * 255; + a->a_lnotab_off += ncodes * 2; + } + assert(d_bytecode <= 255); + if (d_lineno > 255) { + int j, nbytes, ncodes = d_lineno / 255; + nbytes = a->a_lnotab_off + 2 * ncodes; + len = PyString_GET_SIZE(a->a_lnotab); + if (nbytes >= len) { + if ((len <= INT_MAX / 2) && len * 2 < nbytes) + len = nbytes; + else if (len <= INT_MAX / 2) + len *= 2; + else { + PyErr_NoMemory(); + return 0; + } + if (_PyString_Resize(&a->a_lnotab, len) < 0) + return 0; + } + lnotab = (unsigned char *) + PyString_AS_STRING(a->a_lnotab) + a->a_lnotab_off; + *lnotab++ = d_bytecode; + *lnotab++ = 255; + d_bytecode = 0; + for (j = 1; j < ncodes; j++) { + *lnotab++ = 0; + *lnotab++ = 255; + } + d_lineno -= ncodes * 255; + a->a_lnotab_off += ncodes * 2; + } + + len = PyString_GET_SIZE(a->a_lnotab); + if (a->a_lnotab_off + 2 >= len) { + if (_PyString_Resize(&a->a_lnotab, len * 2) < 0) + return 0; + } + lnotab = (unsigned char *) + PyString_AS_STRING(a->a_lnotab) + a->a_lnotab_off; + + a->a_lnotab_off += 2; + if (d_bytecode) { + *lnotab++ = d_bytecode; + *lnotab++ = d_lineno; + } + else { /* First line of a block; def stmt, etc. */ + *lnotab++ = 0; + *lnotab++ = d_lineno; + } + a->a_lineno = i->i_lineno; + a->a_lineno_off = a->a_offset; + return 1; +} + +/* assemble_emit() + Extend the bytecode with a new instruction. + Update lnotab if necessary. +*/ + +static int +assemble_emit(struct assembler *a, struct instr *i) +{ + int size, arg = 0, ext = 0; + Py_ssize_t len = PyString_GET_SIZE(a->a_bytecode); + char *code; + + size = instrsize(i); + if (i->i_hasarg) { + arg = i->i_oparg; + ext = arg >> 16; + } + if (i->i_lineno && !assemble_lnotab(a, i)) + return 0; + if (a->a_offset + size >= len) { + if (len > PY_SSIZE_T_MAX / 2) + return 0; + if (_PyString_Resize(&a->a_bytecode, len * 2) < 0) + return 0; + } + code = PyString_AS_STRING(a->a_bytecode) + a->a_offset; + a->a_offset += size; + if (size == 6) { + assert(i->i_hasarg); + *code++ = (char)EXTENDED_ARG; + *code++ = ext & 0xff; + *code++ = ext >> 8; + arg &= 0xffff; + } + *code++ = i->i_opcode; + if (i->i_hasarg) { + assert(size == 3 || size == 6); + *code++ = arg & 0xff; + *code++ = arg >> 8; + } + return 1; +} + +static void +assemble_jump_offsets(struct assembler *a, struct compiler *c) +{ + basicblock *b; + int bsize, totsize, extended_arg_count = 0, last_extended_arg_count; + int i; + + /* Compute the size of each block and fixup jump args. + Replace block pointer with position in bytecode. */ + do { + totsize = 0; + for (i = a->a_nblocks - 1; i >= 0; i--) { + b = a->a_postorder[i]; + bsize = blocksize(b); + b->b_offset = totsize; + totsize += bsize; + } + last_extended_arg_count = extended_arg_count; + extended_arg_count = 0; + for (b = c->u->u_blocks; b != NULL; b = b->b_list) { + bsize = b->b_offset; + for (i = 0; i < b->b_iused; i++) { + struct instr *instr = &b->b_instr[i]; + /* Relative jumps are computed relative to + the instruction pointer after fetching + the jump instruction. + */ + bsize += instrsize(instr); + if (instr->i_jabs) + instr->i_oparg = instr->i_target->b_offset; + else if (instr->i_jrel) { + int delta = instr->i_target->b_offset - bsize; + instr->i_oparg = delta; + } + else + continue; + if (instr->i_oparg > 0xffff) + extended_arg_count++; + } + } + + /* XXX: This is an awful hack that could hurt performance, but + on the bright side it should work until we come up + with a better solution. + + The issue is that in the first loop blocksize() is called + which calls instrsize() which requires i_oparg be set + appropriately. There is a bootstrap problem because + i_oparg is calculated in the second loop above. + + So we loop until we stop seeing new EXTENDED_ARGs. + The only EXTENDED_ARGs that could be popping up are + ones in jump instructions. So this should converge + fairly quickly. + */ + } while (last_extended_arg_count != extended_arg_count); +} + +static PyObject * +dict_keys_inorder(PyObject *dict, int offset) +{ + PyObject *tuple, *k, *v; + Py_ssize_t i, pos = 0, size = PyDict_Size(dict); + + tuple = PyTuple_New(size); + if (tuple == NULL) + return NULL; + while (PyDict_Next(dict, &pos, &k, &v)) { + i = PyInt_AS_LONG(v); + /* The keys of the dictionary are tuples. (see compiler_add_o) + The object we want is always first, though. */ + k = PyTuple_GET_ITEM(k, 0); + Py_INCREF(k); + assert((i - offset) < size); + assert((i - offset) >= 0); + PyTuple_SET_ITEM(tuple, i - offset, k); + } + return tuple; +} + +static int +compute_code_flags(struct compiler *c) +{ + PySTEntryObject *ste = c->u->u_ste; + int flags = 0, n; + if (ste->ste_type != ModuleBlock) + flags |= CO_NEWLOCALS; + if (ste->ste_type == FunctionBlock) { + if (!ste->ste_unoptimized) + flags |= CO_OPTIMIZED; + if (ste->ste_nested) + flags |= CO_NESTED; + if (ste->ste_generator) + flags |= CO_GENERATOR; + if (ste->ste_varargs) + flags |= CO_VARARGS; + if (ste->ste_varkeywords) + flags |= CO_VARKEYWORDS; + } + + /* (Only) inherit compilerflags in PyCF_MASK */ + flags |= (c->c_flags->cf_flags & PyCF_MASK); + + n = PyDict_Size(c->u->u_freevars); + if (n < 0) + return -1; + if (n == 0) { + n = PyDict_Size(c->u->u_cellvars); + if (n < 0) + return -1; + if (n == 0) { + flags |= CO_NOFREE; + } + } + + return flags; +} + +static PyCodeObject * +makecode(struct compiler *c, struct assembler *a) +{ + PyObject *tmp; + PyCodeObject *co = NULL; + PyObject *consts = NULL; + PyObject *names = NULL; + PyObject *varnames = NULL; + PyObject *filename = NULL; + PyObject *name = NULL; + PyObject *freevars = NULL; + PyObject *cellvars = NULL; + PyObject *bytecode = NULL; + int nlocals, flags; + + tmp = dict_keys_inorder(c->u->u_consts, 0); + if (!tmp) + goto error; + consts = PySequence_List(tmp); /* optimize_code requires a list */ + Py_DECREF(tmp); + + names = dict_keys_inorder(c->u->u_names, 0); + varnames = dict_keys_inorder(c->u->u_varnames, 0); + if (!consts || !names || !varnames) + goto error; + + cellvars = dict_keys_inorder(c->u->u_cellvars, 0); + if (!cellvars) + goto error; + freevars = dict_keys_inorder(c->u->u_freevars, PyTuple_Size(cellvars)); + if (!freevars) + goto error; + filename = PyString_FromString(c->c_filename); + if (!filename) + goto error; + + nlocals = PyDict_Size(c->u->u_varnames); + flags = compute_code_flags(c); + if (flags < 0) + goto error; + + bytecode = PyCode_Optimize(a->a_bytecode, consts, names, a->a_lnotab); + if (!bytecode) + goto error; + + tmp = PyList_AsTuple(consts); /* PyCode_New requires a tuple */ + if (!tmp) + goto error; + Py_DECREF(consts); + consts = tmp; + + co = PyCode_New(c->u->u_argcount, nlocals, stackdepth(c), flags, + bytecode, consts, names, varnames, + freevars, cellvars, + filename, c->u->u_name, + c->u->u_firstlineno, + a->a_lnotab); + error: + Py_XDECREF(consts); + Py_XDECREF(names); + Py_XDECREF(varnames); + Py_XDECREF(filename); + Py_XDECREF(name); + Py_XDECREF(freevars); + Py_XDECREF(cellvars); + Py_XDECREF(bytecode); + return co; +} + + +/* For debugging purposes only */ +#if 0 +static void +dump_instr(const struct instr *i) +{ + const char *jrel = i->i_jrel ? "jrel " : ""; + const char *jabs = i->i_jabs ? "jabs " : ""; + char arg[128]; + + *arg = '\0'; + if (i->i_hasarg) + sprintf(arg, "arg: %d ", i->i_oparg); + + fprintf(stderr, "line: %d, opcode: %d %s%s%s\n", + i->i_lineno, i->i_opcode, arg, jabs, jrel); +} + +static void +dump_basicblock(const basicblock *b) +{ + const char *seen = b->b_seen ? "seen " : ""; + const char *b_return = b->b_return ? "return " : ""; + fprintf(stderr, "used: %d, depth: %d, offset: %d %s%s\n", + b->b_iused, b->b_startdepth, b->b_offset, seen, b_return); + if (b->b_instr) { + int i; + for (i = 0; i < b->b_iused; i++) { + fprintf(stderr, " [%02d] ", i); + dump_instr(b->b_instr + i); + } + } +} +#endif + +static PyCodeObject * +assemble(struct compiler *c, int addNone) +{ + basicblock *b, *entryblock; + struct assembler a; + int i, j, nblocks; + PyCodeObject *co = NULL; + + /* Make sure every block that falls off the end returns None. + XXX NEXT_BLOCK() isn't quite right, because if the last + block ends with a jump or return b_next shouldn't set. + */ + if (!c->u->u_curblock->b_return) { + NEXT_BLOCK(c); + if (addNone) + ADDOP_O(c, LOAD_CONST, Py_None, consts); + ADDOP(c, RETURN_VALUE); + } + + nblocks = 0; + entryblock = NULL; + for (b = c->u->u_blocks; b != NULL; b = b->b_list) { + nblocks++; + entryblock = b; + } + + /* Set firstlineno if it wasn't explicitly set. */ + if (!c->u->u_firstlineno) { + if (entryblock && entryblock->b_instr) + c->u->u_firstlineno = entryblock->b_instr->i_lineno; + else + c->u->u_firstlineno = 1; + } + if (!assemble_init(&a, nblocks, c->u->u_firstlineno)) + goto error; + dfs(c, entryblock, &a); + + /* Can't modify the bytecode after computing jump offsets. */ + assemble_jump_offsets(&a, c); + + /* Emit code in reverse postorder from dfs. */ + for (i = a.a_nblocks - 1; i >= 0; i--) { + b = a.a_postorder[i]; + for (j = 0; j < b->b_iused; j++) + if (!assemble_emit(&a, &b->b_instr[j])) + goto error; + } + + if (_PyString_Resize(&a.a_lnotab, a.a_lnotab_off) < 0) + goto error; + if (_PyString_Resize(&a.a_bytecode, a.a_offset) < 0) + goto error; + + co = makecode(c, &a); + error: + assemble_free(&a); + return co; +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/dtoa.c b/AppPkg/Applications/Python/Python-2.7.10/Python/dtoa.c new file mode 100644 index 0000000000..655e366027 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/dtoa.c @@ -0,0 +1,2949 @@ +/**************************************************************** + * + * The author of this software is David M. Gay. + * + * Copyright (c) 1991, 2000, 2001 by Lucent Technologies. + * + * Permission to use, copy, modify, and distribute this software for any + * purpose without fee is hereby granted, provided that this entire notice + * is included in all copies of any software which is or includes a copy + * or modification of this software and in all copies of the supporting + * documentation for such software. + * + * THIS SOFTWARE IS BEING PROVIDED "AS IS", WITHOUT ANY EXPRESS OR IMPLIED + * WARRANTY. IN PARTICULAR, NEITHER THE AUTHOR NOR LUCENT MAKES ANY + * REPRESENTATION OR WARRANTY OF ANY KIND CONCERNING THE MERCHANTABILITY + * OF THIS SOFTWARE OR ITS FITNESS FOR ANY PARTICULAR PURPOSE. + * + ***************************************************************/ + +/**************************************************************** + * This is dtoa.c by David M. Gay, downloaded from + * http://www.netlib.org/fp/dtoa.c on April 15, 2009 and modified for + * inclusion into the Python core by Mark E. T. Dickinson and Eric V. Smith. + * + * Please remember to check http://www.netlib.org/fp regularly (and especially + * before any Python release) for bugfixes and updates. + * + * The major modifications from Gay's original code are as follows: + * + * 0. The original code has been specialized to Python's needs by removing + * many of the #ifdef'd sections. In particular, code to support VAX and + * IBM floating-point formats, hex NaNs, hex floats, locale-aware + * treatment of the decimal point, and setting of the inexact flag have + * been removed. + * + * 1. We use PyMem_Malloc and PyMem_Free in place of malloc and free. + * + * 2. The public functions strtod, dtoa and freedtoa all now have + * a _Py_dg_ prefix. + * + * 3. Instead of assuming that PyMem_Malloc always succeeds, we thread + * PyMem_Malloc failures through the code. The functions + * + * Balloc, multadd, s2b, i2b, mult, pow5mult, lshift, diff, d2b + * + * of return type *Bigint all return NULL to indicate a malloc failure. + * Similarly, rv_alloc and nrv_alloc (return type char *) return NULL on + * failure. bigcomp now has return type int (it used to be void) and + * returns -1 on failure and 0 otherwise. _Py_dg_dtoa returns NULL + * on failure. _Py_dg_strtod indicates failure due to malloc failure + * by returning -1.0, setting errno=ENOMEM and *se to s00. + * + * 4. The static variable dtoa_result has been removed. Callers of + * _Py_dg_dtoa are expected to call _Py_dg_freedtoa to free + * the memory allocated by _Py_dg_dtoa. + * + * 5. The code has been reformatted to better fit with Python's + * C style guide (PEP 7). + * + * 6. A bug in the memory allocation has been fixed: to avoid FREEing memory + * that hasn't been MALLOC'ed, private_mem should only be used when k <= + * Kmax. + * + * 7. _Py_dg_strtod has been modified so that it doesn't accept strings with + * leading whitespace. + * + ***************************************************************/ + +/* Please send bug reports for the original dtoa.c code to David M. Gay (dmg + * at acm dot org, with " at " changed at "@" and " dot " changed to "."). + * Please report bugs for this modified version using the Python issue tracker + * (http://bugs.python.org). */ + +/* On a machine with IEEE extended-precision registers, it is + * necessary to specify double-precision (53-bit) rounding precision + * before invoking strtod or dtoa. If the machine uses (the equivalent + * of) Intel 80x87 arithmetic, the call + * _control87(PC_53, MCW_PC); + * does this with many compilers. Whether this or another call is + * appropriate depends on the compiler; for this to work, it may be + * necessary to #include "float.h" or another system-dependent header + * file. + */ + +/* strtod for IEEE-, VAX-, and IBM-arithmetic machines. + * + * This strtod returns a nearest machine number to the input decimal + * string (or sets errno to ERANGE). With IEEE arithmetic, ties are + * broken by the IEEE round-even rule. Otherwise ties are broken by + * biased rounding (add half and chop). + * + * Inspired loosely by William D. Clinger's paper "How to Read Floating + * Point Numbers Accurately" [Proc. ACM SIGPLAN '90, pp. 92-101]. + * + * Modifications: + * + * 1. We only require IEEE, IBM, or VAX double-precision + * arithmetic (not IEEE double-extended). + * 2. We get by with floating-point arithmetic in a case that + * Clinger missed -- when we're computing d * 10^n + * for a small integer d and the integer n is not too + * much larger than 22 (the maximum integer k for which + * we can represent 10^k exactly), we may be able to + * compute (d*10^k) * 10^(e-k) with just one roundoff. + * 3. Rather than a bit-at-a-time adjustment of the binary + * result in the hard case, we use floating-point + * arithmetic to determine the adjustment to within + * one bit; only in really hard cases do we need to + * compute a second residual. + * 4. Because of 3., we don't need a large table of powers of 10 + * for ten-to-e (just some small tables, e.g. of 10^k + * for 0 <= k <= 22). + */ + +/* Linking of Python's #defines to Gay's #defines starts here. */ + +#include "Python.h" + +/* if PY_NO_SHORT_FLOAT_REPR is defined, then don't even try to compile + the following code */ +#ifndef PY_NO_SHORT_FLOAT_REPR + +#include "float.h" + +#define MALLOC PyMem_Malloc +#define FREE PyMem_Free + +/* This code should also work for ARM mixed-endian format on little-endian + machines, where doubles have byte order 45670123 (in increasing address + order, 0 being the least significant byte). */ +#ifdef DOUBLE_IS_LITTLE_ENDIAN_IEEE754 +# define IEEE_8087 +#endif +#if defined(DOUBLE_IS_BIG_ENDIAN_IEEE754) || \ + defined(DOUBLE_IS_ARM_MIXED_ENDIAN_IEEE754) +# define IEEE_MC68k +#endif +#if defined(IEEE_8087) + defined(IEEE_MC68k) != 1 +#error "Exactly one of IEEE_8087 or IEEE_MC68k should be defined." +#endif + +/* The code below assumes that the endianness of integers matches the + endianness of the two 32-bit words of a double. Check this. */ +#if defined(WORDS_BIGENDIAN) && (defined(DOUBLE_IS_LITTLE_ENDIAN_IEEE754) || \ + defined(DOUBLE_IS_ARM_MIXED_ENDIAN_IEEE754)) +#error "doubles and ints have incompatible endianness" +#endif + +#if !defined(WORDS_BIGENDIAN) && defined(DOUBLE_IS_BIG_ENDIAN_IEEE754) +#error "doubles and ints have incompatible endianness" +#endif + + +#if defined(HAVE_UINT32_T) && defined(HAVE_INT32_T) +typedef PY_UINT32_T ULong; +typedef PY_INT32_T Long; +#else +#error "Failed to find an exact-width 32-bit integer type" +#endif + +#if defined(HAVE_UINT64_T) +#define ULLong PY_UINT64_T +#else +#undef ULLong +#endif + +#undef DEBUG +#ifdef Py_DEBUG +#define DEBUG +#endif + +/* End Python #define linking */ + +#ifdef DEBUG +#define Bug(x) {fprintf(stderr, "%s\n", x); exit(1);} +#endif + +#ifndef PRIVATE_MEM +#define PRIVATE_MEM 2304 +#endif +#define PRIVATE_mem ((PRIVATE_MEM+sizeof(double)-1)/sizeof(double)) +static double private_mem[PRIVATE_mem], *pmem_next = private_mem; + +#ifdef __cplusplus +extern "C" { +#endif + +typedef union { double d; ULong L[2]; } U; + +#ifdef IEEE_8087 +#define word0(x) (x)->L[1] +#define word1(x) (x)->L[0] +#else +#define word0(x) (x)->L[0] +#define word1(x) (x)->L[1] +#endif +#define dval(x) (x)->d + +#ifndef STRTOD_DIGLIM +#define STRTOD_DIGLIM 40 +#endif + +/* maximum permitted exponent value for strtod; exponents larger than + MAX_ABS_EXP in absolute value get truncated to +-MAX_ABS_EXP. MAX_ABS_EXP + should fit into an int. */ +#ifndef MAX_ABS_EXP +#define MAX_ABS_EXP 1100000000U +#endif +/* Bound on length of pieces of input strings in _Py_dg_strtod; specifically, + this is used to bound the total number of digits ignoring leading zeros and + the number of digits that follow the decimal point. Ideally, MAX_DIGITS + should satisfy MAX_DIGITS + 400 < MAX_ABS_EXP; that ensures that the + exponent clipping in _Py_dg_strtod can't affect the value of the output. */ +#ifndef MAX_DIGITS +#define MAX_DIGITS 1000000000U +#endif + +/* Guard against trying to use the above values on unusual platforms with ints + * of width less than 32 bits. */ +#if MAX_ABS_EXP > INT_MAX +#error "MAX_ABS_EXP should fit in an int" +#endif +#if MAX_DIGITS > INT_MAX +#error "MAX_DIGITS should fit in an int" +#endif + +/* The following definition of Storeinc is appropriate for MIPS processors. + * An alternative that might be better on some machines is + * #define Storeinc(a,b,c) (*a++ = b << 16 | c & 0xffff) + */ +#if defined(IEEE_8087) +#define Storeinc(a,b,c) (((unsigned short *)a)[1] = (unsigned short)b, \ + ((unsigned short *)a)[0] = (unsigned short)c, a++) +#else +#define Storeinc(a,b,c) (((unsigned short *)a)[0] = (unsigned short)b, \ + ((unsigned short *)a)[1] = (unsigned short)c, a++) +#endif + +/* #define P DBL_MANT_DIG */ +/* Ten_pmax = floor(P*log(2)/log(5)) */ +/* Bletch = (highest power of 2 < DBL_MAX_10_EXP) / 16 */ +/* Quick_max = floor((P-1)*log(FLT_RADIX)/log(10) - 1) */ +/* Int_max = floor(P*log(FLT_RADIX)/log(10) - 1) */ + +#define Exp_shift 20 +#define Exp_shift1 20 +#define Exp_msk1 0x100000 +#define Exp_msk11 0x100000 +#define Exp_mask 0x7ff00000 +#define P 53 +#define Nbits 53 +#define Bias 1023 +#define Emax 1023 +#define Emin (-1022) +#define Etiny (-1074) /* smallest denormal is 2**Etiny */ +#define Exp_1 0x3ff00000 +#define Exp_11 0x3ff00000 +#define Ebits 11 +#define Frac_mask 0xfffff +#define Frac_mask1 0xfffff +#define Ten_pmax 22 +#define Bletch 0x10 +#define Bndry_mask 0xfffff +#define Bndry_mask1 0xfffff +#define Sign_bit 0x80000000 +#define Log2P 1 +#define Tiny0 0 +#define Tiny1 1 +#define Quick_max 14 +#define Int_max 14 + +#ifndef Flt_Rounds +#ifdef FLT_ROUNDS +#define Flt_Rounds FLT_ROUNDS +#else +#define Flt_Rounds 1 +#endif +#endif /*Flt_Rounds*/ + +#define Rounding Flt_Rounds + +#define Big0 (Frac_mask1 | Exp_msk1*(DBL_MAX_EXP+Bias-1)) +#define Big1 0xffffffff + +/* struct BCinfo is used to pass information from _Py_dg_strtod to bigcomp */ + +typedef struct BCinfo BCinfo; +struct +BCinfo { + int e0, nd, nd0, scale; +}; + +#define FFFFFFFF 0xffffffffUL + +#define Kmax 7 + +/* struct Bigint is used to represent arbitrary-precision integers. These + integers are stored in sign-magnitude format, with the magnitude stored as + an array of base 2**32 digits. Bigints are always normalized: if x is a + Bigint then x->wds >= 1, and either x->wds == 1 or x[wds-1] is nonzero. + + The Bigint fields are as follows: + + - next is a header used by Balloc and Bfree to keep track of lists + of freed Bigints; it's also used for the linked list of + powers of 5 of the form 5**2**i used by pow5mult. + - k indicates which pool this Bigint was allocated from + - maxwds is the maximum number of words space was allocated for + (usually maxwds == 2**k) + - sign is 1 for negative Bigints, 0 for positive. The sign is unused + (ignored on inputs, set to 0 on outputs) in almost all operations + involving Bigints: a notable exception is the diff function, which + ignores signs on inputs but sets the sign of the output correctly. + - wds is the actual number of significant words + - x contains the vector of words (digits) for this Bigint, from least + significant (x[0]) to most significant (x[wds-1]). +*/ + +struct +Bigint { + struct Bigint *next; + int k, maxwds, sign, wds; + ULong x[1]; +}; + +typedef struct Bigint Bigint; + +#ifndef Py_USING_MEMORY_DEBUGGER + +/* Memory management: memory is allocated from, and returned to, Kmax+1 pools + of memory, where pool k (0 <= k <= Kmax) is for Bigints b with b->maxwds == + 1 << k. These pools are maintained as linked lists, with freelist[k] + pointing to the head of the list for pool k. + + On allocation, if there's no free slot in the appropriate pool, MALLOC is + called to get more memory. This memory is not returned to the system until + Python quits. There's also a private memory pool that's allocated from + in preference to using MALLOC. + + For Bigints with more than (1 << Kmax) digits (which implies at least 1233 + decimal digits), memory is directly allocated using MALLOC, and freed using + FREE. + + XXX: it would be easy to bypass this memory-management system and + translate each call to Balloc into a call to PyMem_Malloc, and each + Bfree to PyMem_Free. Investigate whether this has any significant + performance on impact. */ + +static Bigint *freelist[Kmax+1]; + +/* Allocate space for a Bigint with up to 1<next; + else { + x = 1 << k; + len = (sizeof(Bigint) + (x-1)*sizeof(ULong) + sizeof(double) - 1) + /sizeof(double); + if (k <= Kmax && pmem_next - private_mem + len <= PRIVATE_mem) { + rv = (Bigint*)pmem_next; + pmem_next += len; + } + else { + rv = (Bigint*)MALLOC(len*sizeof(double)); + if (rv == NULL) + return NULL; + } + rv->k = k; + rv->maxwds = x; + } + rv->sign = rv->wds = 0; + return rv; +} + +/* Free a Bigint allocated with Balloc */ + +static void +Bfree(Bigint *v) +{ + if (v) { + if (v->k > Kmax) + FREE((void*)v); + else { + v->next = freelist[v->k]; + freelist[v->k] = v; + } + } +} + +#else + +/* Alternative versions of Balloc and Bfree that use PyMem_Malloc and + PyMem_Free directly in place of the custom memory allocation scheme above. + These are provided for the benefit of memory debugging tools like + Valgrind. */ + +/* Allocate space for a Bigint with up to 1<k = k; + rv->maxwds = x; + rv->sign = rv->wds = 0; + return rv; +} + +/* Free a Bigint allocated with Balloc */ + +static void +Bfree(Bigint *v) +{ + if (v) { + FREE((void*)v); + } +} + +#endif /* Py_USING_MEMORY_DEBUGGER */ + +#define Bcopy(x,y) memcpy((char *)&x->sign, (char *)&y->sign, \ + y->wds*sizeof(Long) + 2*sizeof(int)) + +/* Multiply a Bigint b by m and add a. Either modifies b in place and returns + a pointer to the modified b, or Bfrees b and returns a pointer to a copy. + On failure, return NULL. In this case, b will have been already freed. */ + +static Bigint * +multadd(Bigint *b, int m, int a) /* multiply by m and add a */ +{ + int i, wds; +#ifdef ULLong + ULong *x; + ULLong carry, y; +#else + ULong carry, *x, y; + ULong xi, z; +#endif + Bigint *b1; + + wds = b->wds; + x = b->x; + i = 0; + carry = a; + do { +#ifdef ULLong + y = *x * (ULLong)m + carry; + carry = y >> 32; + *x++ = (ULong)(y & FFFFFFFF); +#else + xi = *x; + y = (xi & 0xffff) * m + carry; + z = (xi >> 16) * m + (y >> 16); + carry = z >> 16; + *x++ = (z << 16) + (y & 0xffff); +#endif + } + while(++i < wds); + if (carry) { + if (wds >= b->maxwds) { + b1 = Balloc(b->k+1); + if (b1 == NULL){ + Bfree(b); + return NULL; + } + Bcopy(b1, b); + Bfree(b); + b = b1; + } + b->x[wds++] = (ULong)carry; + b->wds = wds; + } + return b; +} + +/* convert a string s containing nd decimal digits (possibly containing a + decimal separator at position nd0, which is ignored) to a Bigint. This + function carries on where the parsing code in _Py_dg_strtod leaves off: on + entry, y9 contains the result of converting the first 9 digits. Returns + NULL on failure. */ + +static Bigint * +s2b(const char *s, int nd0, int nd, ULong y9) +{ + Bigint *b; + int i, k; + Long x, y; + + x = (nd + 8) / 9; + for(k = 0, y = 1; x > y; y <<= 1, k++) ; + b = Balloc(k); + if (b == NULL) + return NULL; + b->x[0] = y9; + b->wds = 1; + + if (nd <= 9) + return b; + + s += 9; + for (i = 9; i < nd0; i++) { + b = multadd(b, 10, *s++ - '0'); + if (b == NULL) + return NULL; + } + s++; + for(; i < nd; i++) { + b = multadd(b, 10, *s++ - '0'); + if (b == NULL) + return NULL; + } + return b; +} + +/* count leading 0 bits in the 32-bit integer x. */ + +static int +hi0bits(ULong x) +{ + int k = 0; + + if (!(x & 0xffff0000)) { + k = 16; + x <<= 16; + } + if (!(x & 0xff000000)) { + k += 8; + x <<= 8; + } + if (!(x & 0xf0000000)) { + k += 4; + x <<= 4; + } + if (!(x & 0xc0000000)) { + k += 2; + x <<= 2; + } + if (!(x & 0x80000000)) { + k++; + if (!(x & 0x40000000)) + return 32; + } + return k; +} + +/* count trailing 0 bits in the 32-bit integer y, and shift y right by that + number of bits. */ + +static int +lo0bits(ULong *y) +{ + int k; + ULong x = *y; + + if (x & 7) { + if (x & 1) + return 0; + if (x & 2) { + *y = x >> 1; + return 1; + } + *y = x >> 2; + return 2; + } + k = 0; + if (!(x & 0xffff)) { + k = 16; + x >>= 16; + } + if (!(x & 0xff)) { + k += 8; + x >>= 8; + } + if (!(x & 0xf)) { + k += 4; + x >>= 4; + } + if (!(x & 0x3)) { + k += 2; + x >>= 2; + } + if (!(x & 1)) { + k++; + x >>= 1; + if (!x) + return 32; + } + *y = x; + return k; +} + +/* convert a small nonnegative integer to a Bigint */ + +static Bigint * +i2b(int i) +{ + Bigint *b; + + b = Balloc(1); + if (b == NULL) + return NULL; + b->x[0] = i; + b->wds = 1; + return b; +} + +/* multiply two Bigints. Returns a new Bigint, or NULL on failure. Ignores + the signs of a and b. */ + +static Bigint * +mult(Bigint *a, Bigint *b) +{ + Bigint *c; + int k, wa, wb, wc; + ULong *x, *xa, *xae, *xb, *xbe, *xc, *xc0; + ULong y; +#ifdef ULLong + ULLong carry, z; +#else + ULong carry, z; + ULong z2; +#endif + + if ((!a->x[0] && a->wds == 1) || (!b->x[0] && b->wds == 1)) { + c = Balloc(0); + if (c == NULL) + return NULL; + c->wds = 1; + c->x[0] = 0; + return c; + } + + if (a->wds < b->wds) { + c = a; + a = b; + b = c; + } + k = a->k; + wa = a->wds; + wb = b->wds; + wc = wa + wb; + if (wc > a->maxwds) + k++; + c = Balloc(k); + if (c == NULL) + return NULL; + for(x = c->x, xa = x + wc; x < xa; x++) + *x = 0; + xa = a->x; + xae = xa + wa; + xb = b->x; + xbe = xb + wb; + xc0 = c->x; +#ifdef ULLong + for(; xb < xbe; xc0++) { + if ((y = *xb++)) { + x = xa; + xc = xc0; + carry = 0; + do { + z = *x++ * (ULLong)y + *xc + carry; + carry = z >> 32; + *xc++ = (ULong)(z & FFFFFFFF); + } + while(x < xae); + *xc = (ULong)carry; + } + } +#else + for(; xb < xbe; xb++, xc0++) { + if (y = *xb & 0xffff) { + x = xa; + xc = xc0; + carry = 0; + do { + z = (*x & 0xffff) * y + (*xc & 0xffff) + carry; + carry = z >> 16; + z2 = (*x++ >> 16) * y + (*xc >> 16) + carry; + carry = z2 >> 16; + Storeinc(xc, z2, z); + } + while(x < xae); + *xc = carry; + } + if (y = *xb >> 16) { + x = xa; + xc = xc0; + carry = 0; + z2 = *xc; + do { + z = (*x & 0xffff) * y + (*xc >> 16) + carry; + carry = z >> 16; + Storeinc(xc, z, z2); + z2 = (*x++ >> 16) * y + (*xc & 0xffff) + carry; + carry = z2 >> 16; + } + while(x < xae); + *xc = z2; + } + } +#endif + for(xc0 = c->x, xc = xc0 + wc; wc > 0 && !*--xc; --wc) ; + c->wds = wc; + return c; +} + +#ifndef Py_USING_MEMORY_DEBUGGER + +/* p5s is a linked list of powers of 5 of the form 5**(2**i), i >= 2 */ + +static Bigint *p5s; + +/* multiply the Bigint b by 5**k. Returns a pointer to the result, or NULL on + failure; if the returned pointer is distinct from b then the original + Bigint b will have been Bfree'd. Ignores the sign of b. */ + +static Bigint * +pow5mult(Bigint *b, int k) +{ + Bigint *b1, *p5, *p51; + int i; + static int p05[3] = { 5, 25, 125 }; + + if ((i = k & 3)) { + b = multadd(b, p05[i-1], 0); + if (b == NULL) + return NULL; + } + + if (!(k >>= 2)) + return b; + p5 = p5s; + if (!p5) { + /* first time */ + p5 = i2b(625); + if (p5 == NULL) { + Bfree(b); + return NULL; + } + p5s = p5; + p5->next = 0; + } + for(;;) { + if (k & 1) { + b1 = mult(b, p5); + Bfree(b); + b = b1; + if (b == NULL) + return NULL; + } + if (!(k >>= 1)) + break; + p51 = p5->next; + if (!p51) { + p51 = mult(p5,p5); + if (p51 == NULL) { + Bfree(b); + return NULL; + } + p51->next = 0; + p5->next = p51; + } + p5 = p51; + } + return b; +} + +#else + +/* Version of pow5mult that doesn't cache powers of 5. Provided for + the benefit of memory debugging tools like Valgrind. */ + +static Bigint * +pow5mult(Bigint *b, int k) +{ + Bigint *b1, *p5, *p51; + int i; + static int p05[3] = { 5, 25, 125 }; + + if ((i = k & 3)) { + b = multadd(b, p05[i-1], 0); + if (b == NULL) + return NULL; + } + + if (!(k >>= 2)) + return b; + p5 = i2b(625); + if (p5 == NULL) { + Bfree(b); + return NULL; + } + + for(;;) { + if (k & 1) { + b1 = mult(b, p5); + Bfree(b); + b = b1; + if (b == NULL) { + Bfree(p5); + return NULL; + } + } + if (!(k >>= 1)) + break; + p51 = mult(p5, p5); + Bfree(p5); + p5 = p51; + if (p5 == NULL) { + Bfree(b); + return NULL; + } + } + Bfree(p5); + return b; +} + +#endif /* Py_USING_MEMORY_DEBUGGER */ + +/* shift a Bigint b left by k bits. Return a pointer to the shifted result, + or NULL on failure. If the returned pointer is distinct from b then the + original b will have been Bfree'd. Ignores the sign of b. */ + +static Bigint * +lshift(Bigint *b, int k) +{ + int i, k1, n, n1; + Bigint *b1; + ULong *x, *x1, *xe, z; + + if (!k || (!b->x[0] && b->wds == 1)) + return b; + + n = k >> 5; + k1 = b->k; + n1 = n + b->wds + 1; + for(i = b->maxwds; n1 > i; i <<= 1) + k1++; + b1 = Balloc(k1); + if (b1 == NULL) { + Bfree(b); + return NULL; + } + x1 = b1->x; + for(i = 0; i < n; i++) + *x1++ = 0; + x = b->x; + xe = x + b->wds; + if (k &= 0x1f) { + k1 = 32 - k; + z = 0; + do { + *x1++ = *x << k | z; + z = *x++ >> k1; + } + while(x < xe); + if ((*x1 = z)) + ++n1; + } + else do + *x1++ = *x++; + while(x < xe); + b1->wds = n1 - 1; + Bfree(b); + return b1; +} + +/* Do a three-way compare of a and b, returning -1 if a < b, 0 if a == b and + 1 if a > b. Ignores signs of a and b. */ + +static int +cmp(Bigint *a, Bigint *b) +{ + ULong *xa, *xa0, *xb, *xb0; + int i, j; + + i = a->wds; + j = b->wds; +#ifdef DEBUG + if (i > 1 && !a->x[i-1]) + Bug("cmp called with a->x[a->wds-1] == 0"); + if (j > 1 && !b->x[j-1]) + Bug("cmp called with b->x[b->wds-1] == 0"); +#endif + if (i -= j) + return i; + xa0 = a->x; + xa = xa0 + j; + xb0 = b->x; + xb = xb0 + j; + for(;;) { + if (*--xa != *--xb) + return *xa < *xb ? -1 : 1; + if (xa <= xa0) + break; + } + return 0; +} + +/* Take the difference of Bigints a and b, returning a new Bigint. Returns + NULL on failure. The signs of a and b are ignored, but the sign of the + result is set appropriately. */ + +static Bigint * +diff(Bigint *a, Bigint *b) +{ + Bigint *c; + int i, wa, wb; + ULong *xa, *xae, *xb, *xbe, *xc; +#ifdef ULLong + ULLong borrow, y; +#else + ULong borrow, y; + ULong z; +#endif + + i = cmp(a,b); + if (!i) { + c = Balloc(0); + if (c == NULL) + return NULL; + c->wds = 1; + c->x[0] = 0; + return c; + } + if (i < 0) { + c = a; + a = b; + b = c; + i = 1; + } + else + i = 0; + c = Balloc(a->k); + if (c == NULL) + return NULL; + c->sign = i; + wa = a->wds; + xa = a->x; + xae = xa + wa; + wb = b->wds; + xb = b->x; + xbe = xb + wb; + xc = c->x; + borrow = 0; +#ifdef ULLong + do { + y = (ULLong)*xa++ - *xb++ - borrow; + borrow = y >> 32 & (ULong)1; + *xc++ = (ULong)(y & FFFFFFFF); + } + while(xb < xbe); + while(xa < xae) { + y = *xa++ - borrow; + borrow = y >> 32 & (ULong)1; + *xc++ = (ULong)(y & FFFFFFFF); + } +#else + do { + y = (*xa & 0xffff) - (*xb & 0xffff) - borrow; + borrow = (y & 0x10000) >> 16; + z = (*xa++ >> 16) - (*xb++ >> 16) - borrow; + borrow = (z & 0x10000) >> 16; + Storeinc(xc, z, y); + } + while(xb < xbe); + while(xa < xae) { + y = (*xa & 0xffff) - borrow; + borrow = (y & 0x10000) >> 16; + z = (*xa++ >> 16) - borrow; + borrow = (z & 0x10000) >> 16; + Storeinc(xc, z, y); + } +#endif + while(!*--xc) + wa--; + c->wds = wa; + return c; +} + +/* Given a positive normal double x, return the difference between x and the + next double up. Doesn't give correct results for subnormals. */ + +static double +ulp(U *x) +{ + Long L; + U u; + + L = (word0(x) & Exp_mask) - (P-1)*Exp_msk1; + word0(&u) = L; + word1(&u) = 0; + return dval(&u); +} + +/* Convert a Bigint to a double plus an exponent */ + +static double +b2d(Bigint *a, int *e) +{ + ULong *xa, *xa0, w, y, z; + int k; + U d; + + xa0 = a->x; + xa = xa0 + a->wds; + y = *--xa; +#ifdef DEBUG + if (!y) Bug("zero y in b2d"); +#endif + k = hi0bits(y); + *e = 32 - k; + if (k < Ebits) { + word0(&d) = Exp_1 | y >> (Ebits - k); + w = xa > xa0 ? *--xa : 0; + word1(&d) = y << ((32-Ebits) + k) | w >> (Ebits - k); + goto ret_d; + } + z = xa > xa0 ? *--xa : 0; + if (k -= Ebits) { + word0(&d) = Exp_1 | y << k | z >> (32 - k); + y = xa > xa0 ? *--xa : 0; + word1(&d) = z << k | y >> (32 - k); + } + else { + word0(&d) = Exp_1 | y; + word1(&d) = z; + } + ret_d: + return dval(&d); +} + +/* Convert a scaled double to a Bigint plus an exponent. Similar to d2b, + except that it accepts the scale parameter used in _Py_dg_strtod (which + should be either 0 or 2*P), and the normalization for the return value is + different (see below). On input, d should be finite and nonnegative, and d + / 2**scale should be exactly representable as an IEEE 754 double. + + Returns a Bigint b and an integer e such that + + dval(d) / 2**scale = b * 2**e. + + Unlike d2b, b is not necessarily odd: b and e are normalized so + that either 2**(P-1) <= b < 2**P and e >= Etiny, or b < 2**P + and e == Etiny. This applies equally to an input of 0.0: in that + case the return values are b = 0 and e = Etiny. + + The above normalization ensures that for all possible inputs d, + 2**e gives ulp(d/2**scale). + + Returns NULL on failure. +*/ + +static Bigint * +sd2b(U *d, int scale, int *e) +{ + Bigint *b; + + b = Balloc(1); + if (b == NULL) + return NULL; + + /* First construct b and e assuming that scale == 0. */ + b->wds = 2; + b->x[0] = word1(d); + b->x[1] = word0(d) & Frac_mask; + *e = Etiny - 1 + (int)((word0(d) & Exp_mask) >> Exp_shift); + if (*e < Etiny) + *e = Etiny; + else + b->x[1] |= Exp_msk1; + + /* Now adjust for scale, provided that b != 0. */ + if (scale && (b->x[0] || b->x[1])) { + *e -= scale; + if (*e < Etiny) { + scale = Etiny - *e; + *e = Etiny; + /* We can't shift more than P-1 bits without shifting out a 1. */ + assert(0 < scale && scale <= P - 1); + if (scale >= 32) { + /* The bits shifted out should all be zero. */ + assert(b->x[0] == 0); + b->x[0] = b->x[1]; + b->x[1] = 0; + scale -= 32; + } + if (scale) { + /* The bits shifted out should all be zero. */ + assert(b->x[0] << (32 - scale) == 0); + b->x[0] = (b->x[0] >> scale) | (b->x[1] << (32 - scale)); + b->x[1] >>= scale; + } + } + } + /* Ensure b is normalized. */ + if (!b->x[1]) + b->wds = 1; + + return b; +} + +/* Convert a double to a Bigint plus an exponent. Return NULL on failure. + + Given a finite nonzero double d, return an odd Bigint b and exponent *e + such that fabs(d) = b * 2**e. On return, *bbits gives the number of + significant bits of b; that is, 2**(*bbits-1) <= b < 2**(*bbits). + + If d is zero, then b == 0, *e == -1010, *bbits = 0. + */ + +static Bigint * +d2b(U *d, int *e, int *bits) +{ + Bigint *b; + int de, k; + ULong *x, y, z; + int i; + + b = Balloc(1); + if (b == NULL) + return NULL; + x = b->x; + + z = word0(d) & Frac_mask; + word0(d) &= 0x7fffffff; /* clear sign bit, which we ignore */ + if ((de = (int)(word0(d) >> Exp_shift))) + z |= Exp_msk1; + if ((y = word1(d))) { + if ((k = lo0bits(&y))) { + x[0] = y | z << (32 - k); + z >>= k; + } + else + x[0] = y; + i = + b->wds = (x[1] = z) ? 2 : 1; + } + else { + k = lo0bits(&z); + x[0] = z; + i = + b->wds = 1; + k += 32; + } + if (de) { + *e = de - Bias - (P-1) + k; + *bits = P - k; + } + else { + *e = de - Bias - (P-1) + 1 + k; + *bits = 32*i - hi0bits(x[i-1]); + } + return b; +} + +/* Compute the ratio of two Bigints, as a double. The result may have an + error of up to 2.5 ulps. */ + +static double +ratio(Bigint *a, Bigint *b) +{ + U da, db; + int k, ka, kb; + + dval(&da) = b2d(a, &ka); + dval(&db) = b2d(b, &kb); + k = ka - kb + 32*(a->wds - b->wds); + if (k > 0) + word0(&da) += k*Exp_msk1; + else { + k = -k; + word0(&db) += k*Exp_msk1; + } + return dval(&da) / dval(&db); +} + +static const double +tens[] = { + 1e0, 1e1, 1e2, 1e3, 1e4, 1e5, 1e6, 1e7, 1e8, 1e9, + 1e10, 1e11, 1e12, 1e13, 1e14, 1e15, 1e16, 1e17, 1e18, 1e19, + 1e20, 1e21, 1e22 +}; + +static const double +bigtens[] = { 1e16, 1e32, 1e64, 1e128, 1e256 }; +static const double tinytens[] = { 1e-16, 1e-32, 1e-64, 1e-128, + 9007199254740992.*9007199254740992.e-256 + /* = 2^106 * 1e-256 */ +}; +/* The factor of 2^53 in tinytens[4] helps us avoid setting the underflow */ +/* flag unnecessarily. It leads to a song and dance at the end of strtod. */ +#define Scale_Bit 0x10 +#define n_bigtens 5 + +#define ULbits 32 +#define kshift 5 +#define kmask 31 + + +static int +dshift(Bigint *b, int p2) +{ + int rv = hi0bits(b->x[b->wds-1]) - 4; + if (p2 > 0) + rv -= p2; + return rv & kmask; +} + +/* special case of Bigint division. The quotient is always in the range 0 <= + quotient < 10, and on entry the divisor S is normalized so that its top 4 + bits (28--31) are zero and bit 27 is set. */ + +static int +quorem(Bigint *b, Bigint *S) +{ + int n; + ULong *bx, *bxe, q, *sx, *sxe; +#ifdef ULLong + ULLong borrow, carry, y, ys; +#else + ULong borrow, carry, y, ys; + ULong si, z, zs; +#endif + + n = S->wds; +#ifdef DEBUG + /*debug*/ if (b->wds > n) + /*debug*/ Bug("oversize b in quorem"); +#endif + if (b->wds < n) + return 0; + sx = S->x; + sxe = sx + --n; + bx = b->x; + bxe = bx + n; + q = *bxe / (*sxe + 1); /* ensure q <= true quotient */ +#ifdef DEBUG + /*debug*/ if (q > 9) + /*debug*/ Bug("oversized quotient in quorem"); +#endif + if (q) { + borrow = 0; + carry = 0; + do { +#ifdef ULLong + ys = *sx++ * (ULLong)q + carry; + carry = ys >> 32; + y = *bx - (ys & FFFFFFFF) - borrow; + borrow = y >> 32 & (ULong)1; + *bx++ = (ULong)(y & FFFFFFFF); +#else + si = *sx++; + ys = (si & 0xffff) * q + carry; + zs = (si >> 16) * q + (ys >> 16); + carry = zs >> 16; + y = (*bx & 0xffff) - (ys & 0xffff) - borrow; + borrow = (y & 0x10000) >> 16; + z = (*bx >> 16) - (zs & 0xffff) - borrow; + borrow = (z & 0x10000) >> 16; + Storeinc(bx, z, y); +#endif + } + while(sx <= sxe); + if (!*bxe) { + bx = b->x; + while(--bxe > bx && !*bxe) + --n; + b->wds = n; + } + } + if (cmp(b, S) >= 0) { + q++; + borrow = 0; + carry = 0; + bx = b->x; + sx = S->x; + do { +#ifdef ULLong + ys = *sx++ + carry; + carry = ys >> 32; + y = *bx - (ys & FFFFFFFF) - borrow; + borrow = y >> 32 & (ULong)1; + *bx++ = (ULong)(y & FFFFFFFF); +#else + si = *sx++; + ys = (si & 0xffff) + carry; + zs = (si >> 16) + (ys >> 16); + carry = zs >> 16; + y = (*bx & 0xffff) - (ys & 0xffff) - borrow; + borrow = (y & 0x10000) >> 16; + z = (*bx >> 16) - (zs & 0xffff) - borrow; + borrow = (z & 0x10000) >> 16; + Storeinc(bx, z, y); +#endif + } + while(sx <= sxe); + bx = b->x; + bxe = bx + n; + if (!*bxe) { + while(--bxe > bx && !*bxe) + --n; + b->wds = n; + } + } + return q; +} + +/* sulp(x) is a version of ulp(x) that takes bc.scale into account. + + Assuming that x is finite and nonnegative (positive zero is fine + here) and x / 2^bc.scale is exactly representable as a double, + sulp(x) is equivalent to 2^bc.scale * ulp(x / 2^bc.scale). */ + +static double +sulp(U *x, BCinfo *bc) +{ + U u; + + if (bc->scale && 2*P + 1 > (int)((word0(x) & Exp_mask) >> Exp_shift)) { + /* rv/2^bc->scale is subnormal */ + word0(&u) = (P+2)*Exp_msk1; + word1(&u) = 0; + return u.d; + } + else { + assert(word0(x) || word1(x)); /* x != 0.0 */ + return ulp(x); + } +} + +/* The bigcomp function handles some hard cases for strtod, for inputs + with more than STRTOD_DIGLIM digits. It's called once an initial + estimate for the double corresponding to the input string has + already been obtained by the code in _Py_dg_strtod. + + The bigcomp function is only called after _Py_dg_strtod has found a + double value rv such that either rv or rv + 1ulp represents the + correctly rounded value corresponding to the original string. It + determines which of these two values is the correct one by + computing the decimal digits of rv + 0.5ulp and comparing them with + the corresponding digits of s0. + + In the following, write dv for the absolute value of the number represented + by the input string. + + Inputs: + + s0 points to the first significant digit of the input string. + + rv is a (possibly scaled) estimate for the closest double value to the + value represented by the original input to _Py_dg_strtod. If + bc->scale is nonzero, then rv/2^(bc->scale) is the approximation to + the input value. + + bc is a struct containing information gathered during the parsing and + estimation steps of _Py_dg_strtod. Description of fields follows: + + bc->e0 gives the exponent of the input value, such that dv = (integer + given by the bd->nd digits of s0) * 10**e0 + + bc->nd gives the total number of significant digits of s0. It will + be at least 1. + + bc->nd0 gives the number of significant digits of s0 before the + decimal separator. If there's no decimal separator, bc->nd0 == + bc->nd. + + bc->scale is the value used to scale rv to avoid doing arithmetic with + subnormal values. It's either 0 or 2*P (=106). + + Outputs: + + On successful exit, rv/2^(bc->scale) is the closest double to dv. + + Returns 0 on success, -1 on failure (e.g., due to a failed malloc call). */ + +static int +bigcomp(U *rv, const char *s0, BCinfo *bc) +{ + Bigint *b, *d; + int b2, d2, dd, i, nd, nd0, odd, p2, p5; + + nd = bc->nd; + nd0 = bc->nd0; + p5 = nd + bc->e0; + b = sd2b(rv, bc->scale, &p2); + if (b == NULL) + return -1; + + /* record whether the lsb of rv/2^(bc->scale) is odd: in the exact halfway + case, this is used for round to even. */ + odd = b->x[0] & 1; + + /* left shift b by 1 bit and or a 1 into the least significant bit; + this gives us b * 2**p2 = rv/2^(bc->scale) + 0.5 ulp. */ + b = lshift(b, 1); + if (b == NULL) + return -1; + b->x[0] |= 1; + p2--; + + p2 -= p5; + d = i2b(1); + if (d == NULL) { + Bfree(b); + return -1; + } + /* Arrange for convenient computation of quotients: + * shift left if necessary so divisor has 4 leading 0 bits. + */ + if (p5 > 0) { + d = pow5mult(d, p5); + if (d == NULL) { + Bfree(b); + return -1; + } + } + else if (p5 < 0) { + b = pow5mult(b, -p5); + if (b == NULL) { + Bfree(d); + return -1; + } + } + if (p2 > 0) { + b2 = p2; + d2 = 0; + } + else { + b2 = 0; + d2 = -p2; + } + i = dshift(d, d2); + if ((b2 += i) > 0) { + b = lshift(b, b2); + if (b == NULL) { + Bfree(d); + return -1; + } + } + if ((d2 += i) > 0) { + d = lshift(d, d2); + if (d == NULL) { + Bfree(b); + return -1; + } + } + + /* Compare s0 with b/d: set dd to -1, 0, or 1 according as s0 < b/d, s0 == + * b/d, or s0 > b/d. Here the digits of s0 are thought of as representing + * a number in the range [0.1, 1). */ + if (cmp(b, d) >= 0) + /* b/d >= 1 */ + dd = -1; + else { + i = 0; + for(;;) { + b = multadd(b, 10, 0); + if (b == NULL) { + Bfree(d); + return -1; + } + dd = s0[i < nd0 ? i : i+1] - '0' - quorem(b, d); + i++; + + if (dd) + break; + if (!b->x[0] && b->wds == 1) { + /* b/d == 0 */ + dd = i < nd; + break; + } + if (!(i < nd)) { + /* b/d != 0, but digits of s0 exhausted */ + dd = -1; + break; + } + } + } + Bfree(b); + Bfree(d); + if (dd > 0 || (dd == 0 && odd)) + dval(rv) += sulp(rv, bc); + return 0; +} + +double +_Py_dg_strtod(const char *s00, char **se) +{ + int bb2, bb5, bbe, bd2, bd5, bs2, c, dsign, e, e1, error; + int esign, i, j, k, lz, nd, nd0, odd, sign; + const char *s, *s0, *s1; + double aadj, aadj1; + U aadj2, adj, rv, rv0; + ULong y, z, abs_exp; + Long L; + BCinfo bc; + Bigint *bb, *bb1, *bd, *bd0, *bs, *delta; + size_t ndigits, fraclen; + + dval(&rv) = 0.; + + /* Start parsing. */ + c = *(s = s00); + + /* Parse optional sign, if present. */ + sign = 0; + switch (c) { + case '-': + sign = 1; + /* no break */ + case '+': + c = *++s; + } + + /* Skip leading zeros: lz is true iff there were leading zeros. */ + s1 = s; + while (c == '0') + c = *++s; + lz = s != s1; + + /* Point s0 at the first nonzero digit (if any). fraclen will be the + number of digits between the decimal point and the end of the + digit string. ndigits will be the total number of digits ignoring + leading zeros. */ + s0 = s1 = s; + while ('0' <= c && c <= '9') + c = *++s; + ndigits = s - s1; + fraclen = 0; + + /* Parse decimal point and following digits. */ + if (c == '.') { + c = *++s; + if (!ndigits) { + s1 = s; + while (c == '0') + c = *++s; + lz = lz || s != s1; + fraclen += (s - s1); + s0 = s; + } + s1 = s; + while ('0' <= c && c <= '9') + c = *++s; + ndigits += s - s1; + fraclen += s - s1; + } + + /* Now lz is true if and only if there were leading zero digits, and + ndigits gives the total number of digits ignoring leading zeros. A + valid input must have at least one digit. */ + if (!ndigits && !lz) { + if (se) + *se = (char *)s00; + goto parse_error; + } + + /* Range check ndigits and fraclen to make sure that they, and values + computed with them, can safely fit in an int. */ + if (ndigits > MAX_DIGITS || fraclen > MAX_DIGITS) { + if (se) + *se = (char *)s00; + goto parse_error; + } + nd = (int)ndigits; + nd0 = (int)ndigits - (int)fraclen; + + /* Parse exponent. */ + e = 0; + if (c == 'e' || c == 'E') { + s00 = s; + c = *++s; + + /* Exponent sign. */ + esign = 0; + switch (c) { + case '-': + esign = 1; + /* no break */ + case '+': + c = *++s; + } + + /* Skip zeros. lz is true iff there are leading zeros. */ + s1 = s; + while (c == '0') + c = *++s; + lz = s != s1; + + /* Get absolute value of the exponent. */ + s1 = s; + abs_exp = 0; + while ('0' <= c && c <= '9') { + abs_exp = 10*abs_exp + (c - '0'); + c = *++s; + } + + /* abs_exp will be correct modulo 2**32. But 10**9 < 2**32, so if + there are at most 9 significant exponent digits then overflow is + impossible. */ + if (s - s1 > 9 || abs_exp > MAX_ABS_EXP) + e = (int)MAX_ABS_EXP; + else + e = (int)abs_exp; + if (esign) + e = -e; + + /* A valid exponent must have at least one digit. */ + if (s == s1 && !lz) + s = s00; + } + + /* Adjust exponent to take into account position of the point. */ + e -= nd - nd0; + if (nd0 <= 0) + nd0 = nd; + + /* Finished parsing. Set se to indicate how far we parsed */ + if (se) + *se = (char *)s; + + /* If all digits were zero, exit with return value +-0.0. Otherwise, + strip trailing zeros: scan back until we hit a nonzero digit. */ + if (!nd) + goto ret; + for (i = nd; i > 0; ) { + --i; + if (s0[i < nd0 ? i : i+1] != '0') { + ++i; + break; + } + } + e += nd - i; + nd = i; + if (nd0 > nd) + nd0 = nd; + + /* Summary of parsing results. After parsing, and dealing with zero + * inputs, we have values s0, nd0, nd, e, sign, where: + * + * - s0 points to the first significant digit of the input string + * + * - nd is the total number of significant digits (here, and + * below, 'significant digits' means the set of digits of the + * significand of the input that remain after ignoring leading + * and trailing zeros). + * + * - nd0 indicates the position of the decimal point, if present; it + * satisfies 1 <= nd0 <= nd. The nd significant digits are in + * s0[0:nd0] and s0[nd0+1:nd+1] using the usual Python half-open slice + * notation. (If nd0 < nd, then s0[nd0] contains a '.' character; if + * nd0 == nd, then s0[nd0] could be any non-digit character.) + * + * - e is the adjusted exponent: the absolute value of the number + * represented by the original input string is n * 10**e, where + * n is the integer represented by the concatenation of + * s0[0:nd0] and s0[nd0+1:nd+1] + * + * - sign gives the sign of the input: 1 for negative, 0 for positive + * + * - the first and last significant digits are nonzero + */ + + /* put first DBL_DIG+1 digits into integer y and z. + * + * - y contains the value represented by the first min(9, nd) + * significant digits + * + * - if nd > 9, z contains the value represented by significant digits + * with indices in [9, min(16, nd)). So y * 10**(min(16, nd) - 9) + z + * gives the value represented by the first min(16, nd) sig. digits. + */ + + bc.e0 = e1 = e; + y = z = 0; + for (i = 0; i < nd; i++) { + if (i < 9) + y = 10*y + s0[i < nd0 ? i : i+1] - '0'; + else if (i < DBL_DIG+1) + z = 10*z + s0[i < nd0 ? i : i+1] - '0'; + else + break; + } + + k = nd < DBL_DIG + 1 ? nd : DBL_DIG + 1; + dval(&rv) = y; + if (k > 9) { + dval(&rv) = tens[k - 9] * dval(&rv) + z; + } + bd0 = 0; + if (nd <= DBL_DIG + && Flt_Rounds == 1 + ) { + if (!e) + goto ret; + if (e > 0) { + if (e <= Ten_pmax) { + dval(&rv) *= tens[e]; + goto ret; + } + i = DBL_DIG - nd; + if (e <= Ten_pmax + i) { + /* A fancier test would sometimes let us do + * this for larger i values. + */ + e -= i; + dval(&rv) *= tens[i]; + dval(&rv) *= tens[e]; + goto ret; + } + } + else if (e >= -Ten_pmax) { + dval(&rv) /= tens[-e]; + goto ret; + } + } + e1 += nd - k; + + bc.scale = 0; + + /* Get starting approximation = rv * 10**e1 */ + + if (e1 > 0) { + if ((i = e1 & 15)) + dval(&rv) *= tens[i]; + if (e1 &= ~15) { + if (e1 > DBL_MAX_10_EXP) + goto ovfl; + e1 >>= 4; + for(j = 0; e1 > 1; j++, e1 >>= 1) + if (e1 & 1) + dval(&rv) *= bigtens[j]; + /* The last multiplication could overflow. */ + word0(&rv) -= P*Exp_msk1; + dval(&rv) *= bigtens[j]; + if ((z = word0(&rv) & Exp_mask) + > Exp_msk1*(DBL_MAX_EXP+Bias-P)) + goto ovfl; + if (z > Exp_msk1*(DBL_MAX_EXP+Bias-1-P)) { + /* set to largest number */ + /* (Can't trust DBL_MAX) */ + word0(&rv) = Big0; + word1(&rv) = Big1; + } + else + word0(&rv) += P*Exp_msk1; + } + } + else if (e1 < 0) { + /* The input decimal value lies in [10**e1, 10**(e1+16)). + + If e1 <= -512, underflow immediately. + If e1 <= -256, set bc.scale to 2*P. + + So for input value < 1e-256, bc.scale is always set; + for input value >= 1e-240, bc.scale is never set. + For input values in [1e-256, 1e-240), bc.scale may or may + not be set. */ + + e1 = -e1; + if ((i = e1 & 15)) + dval(&rv) /= tens[i]; + if (e1 >>= 4) { + if (e1 >= 1 << n_bigtens) + goto undfl; + if (e1 & Scale_Bit) + bc.scale = 2*P; + for(j = 0; e1 > 0; j++, e1 >>= 1) + if (e1 & 1) + dval(&rv) *= tinytens[j]; + if (bc.scale && (j = 2*P + 1 - ((word0(&rv) & Exp_mask) + >> Exp_shift)) > 0) { + /* scaled rv is denormal; clear j low bits */ + if (j >= 32) { + word1(&rv) = 0; + if (j >= 53) + word0(&rv) = (P+2)*Exp_msk1; + else + word0(&rv) &= 0xffffffff << (j-32); + } + else + word1(&rv) &= 0xffffffff << j; + } + if (!dval(&rv)) + goto undfl; + } + } + + /* Now the hard part -- adjusting rv to the correct value.*/ + + /* Put digits into bd: true value = bd * 10^e */ + + bc.nd = nd; + bc.nd0 = nd0; /* Only needed if nd > STRTOD_DIGLIM, but done here */ + /* to silence an erroneous warning about bc.nd0 */ + /* possibly not being initialized. */ + if (nd > STRTOD_DIGLIM) { + /* ASSERT(STRTOD_DIGLIM >= 18); 18 == one more than the */ + /* minimum number of decimal digits to distinguish double values */ + /* in IEEE arithmetic. */ + + /* Truncate input to 18 significant digits, then discard any trailing + zeros on the result by updating nd, nd0, e and y suitably. (There's + no need to update z; it's not reused beyond this point.) */ + for (i = 18; i > 0; ) { + /* scan back until we hit a nonzero digit. significant digit 'i' + is s0[i] if i < nd0, s0[i+1] if i >= nd0. */ + --i; + if (s0[i < nd0 ? i : i+1] != '0') { + ++i; + break; + } + } + e += nd - i; + nd = i; + if (nd0 > nd) + nd0 = nd; + if (nd < 9) { /* must recompute y */ + y = 0; + for(i = 0; i < nd0; ++i) + y = 10*y + s0[i] - '0'; + for(; i < nd; ++i) + y = 10*y + s0[i+1] - '0'; + } + } + bd0 = s2b(s0, nd0, nd, y); + if (bd0 == NULL) + goto failed_malloc; + + /* Notation for the comments below. Write: + + - dv for the absolute value of the number represented by the original + decimal input string. + + - if we've truncated dv, write tdv for the truncated value. + Otherwise, set tdv == dv. + + - srv for the quantity rv/2^bc.scale; so srv is the current binary + approximation to tdv (and dv). It should be exactly representable + in an IEEE 754 double. + */ + + for(;;) { + + /* This is the main correction loop for _Py_dg_strtod. + + We've got a decimal value tdv, and a floating-point approximation + srv=rv/2^bc.scale to tdv. The aim is to determine whether srv is + close enough (i.e., within 0.5 ulps) to tdv, and to compute a new + approximation if not. + + To determine whether srv is close enough to tdv, compute integers + bd, bb and bs proportional to tdv, srv and 0.5 ulp(srv) + respectively, and then use integer arithmetic to determine whether + |tdv - srv| is less than, equal to, or greater than 0.5 ulp(srv). + */ + + bd = Balloc(bd0->k); + if (bd == NULL) { + Bfree(bd0); + goto failed_malloc; + } + Bcopy(bd, bd0); + bb = sd2b(&rv, bc.scale, &bbe); /* srv = bb * 2^bbe */ + if (bb == NULL) { + Bfree(bd); + Bfree(bd0); + goto failed_malloc; + } + /* Record whether lsb of bb is odd, in case we need this + for the round-to-even step later. */ + odd = bb->x[0] & 1; + + /* tdv = bd * 10**e; srv = bb * 2**bbe */ + bs = i2b(1); + if (bs == NULL) { + Bfree(bb); + Bfree(bd); + Bfree(bd0); + goto failed_malloc; + } + + if (e >= 0) { + bb2 = bb5 = 0; + bd2 = bd5 = e; + } + else { + bb2 = bb5 = -e; + bd2 = bd5 = 0; + } + if (bbe >= 0) + bb2 += bbe; + else + bd2 -= bbe; + bs2 = bb2; + bb2++; + bd2++; + + /* At this stage bd5 - bb5 == e == bd2 - bb2 + bbe, bb2 - bs2 == 1, + and bs == 1, so: + + tdv == bd * 10**e = bd * 2**(bbe - bb2 + bd2) * 5**(bd5 - bb5) + srv == bb * 2**bbe = bb * 2**(bbe - bb2 + bb2) + 0.5 ulp(srv) == 2**(bbe-1) = bs * 2**(bbe - bb2 + bs2) + + It follows that: + + M * tdv = bd * 2**bd2 * 5**bd5 + M * srv = bb * 2**bb2 * 5**bb5 + M * 0.5 ulp(srv) = bs * 2**bs2 * 5**bb5 + + for some constant M. (Actually, M == 2**(bb2 - bbe) * 5**bb5, but + this fact is not needed below.) + */ + + /* Remove factor of 2**i, where i = min(bb2, bd2, bs2). */ + i = bb2 < bd2 ? bb2 : bd2; + if (i > bs2) + i = bs2; + if (i > 0) { + bb2 -= i; + bd2 -= i; + bs2 -= i; + } + + /* Scale bb, bd, bs by the appropriate powers of 2 and 5. */ + if (bb5 > 0) { + bs = pow5mult(bs, bb5); + if (bs == NULL) { + Bfree(bb); + Bfree(bd); + Bfree(bd0); + goto failed_malloc; + } + bb1 = mult(bs, bb); + Bfree(bb); + bb = bb1; + if (bb == NULL) { + Bfree(bs); + Bfree(bd); + Bfree(bd0); + goto failed_malloc; + } + } + if (bb2 > 0) { + bb = lshift(bb, bb2); + if (bb == NULL) { + Bfree(bs); + Bfree(bd); + Bfree(bd0); + goto failed_malloc; + } + } + if (bd5 > 0) { + bd = pow5mult(bd, bd5); + if (bd == NULL) { + Bfree(bb); + Bfree(bs); + Bfree(bd0); + goto failed_malloc; + } + } + if (bd2 > 0) { + bd = lshift(bd, bd2); + if (bd == NULL) { + Bfree(bb); + Bfree(bs); + Bfree(bd0); + goto failed_malloc; + } + } + if (bs2 > 0) { + bs = lshift(bs, bs2); + if (bs == NULL) { + Bfree(bb); + Bfree(bd); + Bfree(bd0); + goto failed_malloc; + } + } + + /* Now bd, bb and bs are scaled versions of tdv, srv and 0.5 ulp(srv), + respectively. Compute the difference |tdv - srv|, and compare + with 0.5 ulp(srv). */ + + delta = diff(bb, bd); + if (delta == NULL) { + Bfree(bb); + Bfree(bs); + Bfree(bd); + Bfree(bd0); + goto failed_malloc; + } + dsign = delta->sign; + delta->sign = 0; + i = cmp(delta, bs); + if (bc.nd > nd && i <= 0) { + if (dsign) + break; /* Must use bigcomp(). */ + + /* Here rv overestimates the truncated decimal value by at most + 0.5 ulp(rv). Hence rv either overestimates the true decimal + value by <= 0.5 ulp(rv), or underestimates it by some small + amount (< 0.1 ulp(rv)); either way, rv is within 0.5 ulps of + the true decimal value, so it's possible to exit. + + Exception: if scaled rv is a normal exact power of 2, but not + DBL_MIN, then rv - 0.5 ulp(rv) takes us all the way down to the + next double, so the correctly rounded result is either rv - 0.5 + ulp(rv) or rv; in this case, use bigcomp to distinguish. */ + + if (!word1(&rv) && !(word0(&rv) & Bndry_mask)) { + /* rv can't be 0, since it's an overestimate for some + nonzero value. So rv is a normal power of 2. */ + j = (int)(word0(&rv) & Exp_mask) >> Exp_shift; + /* rv / 2^bc.scale = 2^(j - 1023 - bc.scale); use bigcomp if + rv / 2^bc.scale >= 2^-1021. */ + if (j - bc.scale >= 2) { + dval(&rv) -= 0.5 * sulp(&rv, &bc); + break; /* Use bigcomp. */ + } + } + + { + bc.nd = nd; + i = -1; /* Discarded digits make delta smaller. */ + } + } + + if (i < 0) { + /* Error is less than half an ulp -- check for + * special case of mantissa a power of two. + */ + if (dsign || word1(&rv) || word0(&rv) & Bndry_mask + || (word0(&rv) & Exp_mask) <= (2*P+1)*Exp_msk1 + ) { + break; + } + if (!delta->x[0] && delta->wds <= 1) { + /* exact result */ + break; + } + delta = lshift(delta,Log2P); + if (delta == NULL) { + Bfree(bb); + Bfree(bs); + Bfree(bd); + Bfree(bd0); + goto failed_malloc; + } + if (cmp(delta, bs) > 0) + goto drop_down; + break; + } + if (i == 0) { + /* exactly half-way between */ + if (dsign) { + if ((word0(&rv) & Bndry_mask1) == Bndry_mask1 + && word1(&rv) == ( + (bc.scale && + (y = word0(&rv) & Exp_mask) <= 2*P*Exp_msk1) ? + (0xffffffff & (0xffffffff << (2*P+1-(y>>Exp_shift)))) : + 0xffffffff)) { + /*boundary case -- increment exponent*/ + word0(&rv) = (word0(&rv) & Exp_mask) + + Exp_msk1 + ; + word1(&rv) = 0; + dsign = 0; + break; + } + } + else if (!(word0(&rv) & Bndry_mask) && !word1(&rv)) { + drop_down: + /* boundary case -- decrement exponent */ + if (bc.scale) { + L = word0(&rv) & Exp_mask; + if (L <= (2*P+1)*Exp_msk1) { + if (L > (P+2)*Exp_msk1) + /* round even ==> */ + /* accept rv */ + break; + /* rv = smallest denormal */ + if (bc.nd > nd) + break; + goto undfl; + } + } + L = (word0(&rv) & Exp_mask) - Exp_msk1; + word0(&rv) = L | Bndry_mask1; + word1(&rv) = 0xffffffff; + break; + } + if (!odd) + break; + if (dsign) + dval(&rv) += sulp(&rv, &bc); + else { + dval(&rv) -= sulp(&rv, &bc); + if (!dval(&rv)) { + if (bc.nd >nd) + break; + goto undfl; + } + } + dsign = 1 - dsign; + break; + } + if ((aadj = ratio(delta, bs)) <= 2.) { + if (dsign) + aadj = aadj1 = 1.; + else if (word1(&rv) || word0(&rv) & Bndry_mask) { + if (word1(&rv) == Tiny1 && !word0(&rv)) { + if (bc.nd >nd) + break; + goto undfl; + } + aadj = 1.; + aadj1 = -1.; + } + else { + /* special case -- power of FLT_RADIX to be */ + /* rounded down... */ + + if (aadj < 2./FLT_RADIX) + aadj = 1./FLT_RADIX; + else + aadj *= 0.5; + aadj1 = -aadj; + } + } + else { + aadj *= 0.5; + aadj1 = dsign ? aadj : -aadj; + if (Flt_Rounds == 0) + aadj1 += 0.5; + } + y = word0(&rv) & Exp_mask; + + /* Check for overflow */ + + if (y == Exp_msk1*(DBL_MAX_EXP+Bias-1)) { + dval(&rv0) = dval(&rv); + word0(&rv) -= P*Exp_msk1; + adj.d = aadj1 * ulp(&rv); + dval(&rv) += adj.d; + if ((word0(&rv) & Exp_mask) >= + Exp_msk1*(DBL_MAX_EXP+Bias-P)) { + if (word0(&rv0) == Big0 && word1(&rv0) == Big1) { + Bfree(bb); + Bfree(bd); + Bfree(bs); + Bfree(bd0); + Bfree(delta); + goto ovfl; + } + word0(&rv) = Big0; + word1(&rv) = Big1; + goto cont; + } + else + word0(&rv) += P*Exp_msk1; + } + else { + if (bc.scale && y <= 2*P*Exp_msk1) { + if (aadj <= 0x7fffffff) { + if ((z = (ULong)aadj) <= 0) + z = 1; + aadj = z; + aadj1 = dsign ? aadj : -aadj; + } + dval(&aadj2) = aadj1; + word0(&aadj2) += (2*P+1)*Exp_msk1 - y; + aadj1 = dval(&aadj2); + } + adj.d = aadj1 * ulp(&rv); + dval(&rv) += adj.d; + } + z = word0(&rv) & Exp_mask; + if (bc.nd == nd) { + if (!bc.scale) + if (y == z) { + /* Can we stop now? */ + L = (Long)aadj; + aadj -= L; + /* The tolerances below are conservative. */ + if (dsign || word1(&rv) || word0(&rv) & Bndry_mask) { + if (aadj < .4999999 || aadj > .5000001) + break; + } + else if (aadj < .4999999/FLT_RADIX) + break; + } + } + cont: + Bfree(bb); + Bfree(bd); + Bfree(bs); + Bfree(delta); + } + Bfree(bb); + Bfree(bd); + Bfree(bs); + Bfree(bd0); + Bfree(delta); + if (bc.nd > nd) { + error = bigcomp(&rv, s0, &bc); + if (error) + goto failed_malloc; + } + + if (bc.scale) { + word0(&rv0) = Exp_1 - 2*P*Exp_msk1; + word1(&rv0) = 0; + dval(&rv) *= dval(&rv0); + } + + ret: + return sign ? -dval(&rv) : dval(&rv); + + parse_error: + return 0.0; + + failed_malloc: + errno = ENOMEM; + return -1.0; + + undfl: + return sign ? -0.0 : 0.0; + + ovfl: + errno = ERANGE; + /* Can't trust HUGE_VAL */ + word0(&rv) = Exp_mask; + word1(&rv) = 0; + return sign ? -dval(&rv) : dval(&rv); + +} + +static char * +rv_alloc(int i) +{ + int j, k, *r; + + j = sizeof(ULong); + for(k = 0; + sizeof(Bigint) - sizeof(ULong) - sizeof(int) + j <= (unsigned)i; + j <<= 1) + k++; + r = (int*)Balloc(k); + if (r == NULL) + return NULL; + *r = k; + return (char *)(r+1); +} + +static char * +nrv_alloc(char *s, char **rve, int n) +{ + char *rv, *t; + + rv = rv_alloc(n); + if (rv == NULL) + return NULL; + t = rv; + while((*t = *s++)) t++; + if (rve) + *rve = t; + return rv; +} + +/* freedtoa(s) must be used to free values s returned by dtoa + * when MULTIPLE_THREADS is #defined. It should be used in all cases, + * but for consistency with earlier versions of dtoa, it is optional + * when MULTIPLE_THREADS is not defined. + */ + +void +_Py_dg_freedtoa(char *s) +{ + Bigint *b = (Bigint *)((int *)s - 1); + b->maxwds = 1 << (b->k = *(int*)b); + Bfree(b); +} + +/* dtoa for IEEE arithmetic (dmg): convert double to ASCII string. + * + * Inspired by "How to Print Floating-Point Numbers Accurately" by + * Guy L. Steele, Jr. and Jon L. White [Proc. ACM SIGPLAN '90, pp. 112-126]. + * + * Modifications: + * 1. Rather than iterating, we use a simple numeric overestimate + * to determine k = floor(log10(d)). We scale relevant + * quantities using O(log2(k)) rather than O(k) multiplications. + * 2. For some modes > 2 (corresponding to ecvt and fcvt), we don't + * try to generate digits strictly left to right. Instead, we + * compute with fewer bits and propagate the carry if necessary + * when rounding the final digit up. This is often faster. + * 3. Under the assumption that input will be rounded nearest, + * mode 0 renders 1e23 as 1e23 rather than 9.999999999999999e22. + * That is, we allow equality in stopping tests when the + * round-nearest rule will give the same floating-point value + * as would satisfaction of the stopping test with strict + * inequality. + * 4. We remove common factors of powers of 2 from relevant + * quantities. + * 5. When converting floating-point integers less than 1e16, + * we use floating-point arithmetic rather than resorting + * to multiple-precision integers. + * 6. When asked to produce fewer than 15 digits, we first try + * to get by with floating-point arithmetic; we resort to + * multiple-precision integer arithmetic only if we cannot + * guarantee that the floating-point calculation has given + * the correctly rounded result. For k requested digits and + * "uniformly" distributed input, the probability is + * something like 10^(k-15) that we must resort to the Long + * calculation. + */ + +/* Additional notes (METD): (1) returns NULL on failure. (2) to avoid memory + leakage, a successful call to _Py_dg_dtoa should always be matched by a + call to _Py_dg_freedtoa. */ + +char * +_Py_dg_dtoa(double dd, int mode, int ndigits, + int *decpt, int *sign, char **rve) +{ + /* Arguments ndigits, decpt, sign are similar to those + of ecvt and fcvt; trailing zeros are suppressed from + the returned string. If not null, *rve is set to point + to the end of the return value. If d is +-Infinity or NaN, + then *decpt is set to 9999. + + mode: + 0 ==> shortest string that yields d when read in + and rounded to nearest. + 1 ==> like 0, but with Steele & White stopping rule; + e.g. with IEEE P754 arithmetic , mode 0 gives + 1e23 whereas mode 1 gives 9.999999999999999e22. + 2 ==> max(1,ndigits) significant digits. This gives a + return value similar to that of ecvt, except + that trailing zeros are suppressed. + 3 ==> through ndigits past the decimal point. This + gives a return value similar to that from fcvt, + except that trailing zeros are suppressed, and + ndigits can be negative. + 4,5 ==> similar to 2 and 3, respectively, but (in + round-nearest mode) with the tests of mode 0 to + possibly return a shorter string that rounds to d. + With IEEE arithmetic and compilation with + -DHonor_FLT_ROUNDS, modes 4 and 5 behave the same + as modes 2 and 3 when FLT_ROUNDS != 1. + 6-9 ==> Debugging modes similar to mode - 4: don't try + fast floating-point estimate (if applicable). + + Values of mode other than 0-9 are treated as mode 0. + + Sufficient space is allocated to the return value + to hold the suppressed trailing zeros. + */ + + int bbits, b2, b5, be, dig, i, ieps, ilim, ilim0, ilim1, + j, j1, k, k0, k_check, leftright, m2, m5, s2, s5, + spec_case, try_quick; + Long L; + int denorm; + ULong x; + Bigint *b, *b1, *delta, *mlo, *mhi, *S; + U d2, eps, u; + double ds; + char *s, *s0; + + /* set pointers to NULL, to silence gcc compiler warnings and make + cleanup easier on error */ + mlo = mhi = S = 0; + s0 = 0; + + u.d = dd; + if (word0(&u) & Sign_bit) { + /* set sign for everything, including 0's and NaNs */ + *sign = 1; + word0(&u) &= ~Sign_bit; /* clear sign bit */ + } + else + *sign = 0; + + /* quick return for Infinities, NaNs and zeros */ + if ((word0(&u) & Exp_mask) == Exp_mask) + { + /* Infinity or NaN */ + *decpt = 9999; + if (!word1(&u) && !(word0(&u) & 0xfffff)) + return nrv_alloc("Infinity", rve, 8); + return nrv_alloc("NaN", rve, 3); + } + if (!dval(&u)) { + *decpt = 1; + return nrv_alloc("0", rve, 1); + } + + /* compute k = floor(log10(d)). The computation may leave k + one too large, but should never leave k too small. */ + b = d2b(&u, &be, &bbits); + if (b == NULL) + goto failed_malloc; + if ((i = (int)(word0(&u) >> Exp_shift1 & (Exp_mask>>Exp_shift1)))) { + dval(&d2) = dval(&u); + word0(&d2) &= Frac_mask1; + word0(&d2) |= Exp_11; + + /* log(x) ~=~ log(1.5) + (x-1.5)/1.5 + * log10(x) = log(x) / log(10) + * ~=~ log(1.5)/log(10) + (x-1.5)/(1.5*log(10)) + * log10(d) = (i-Bias)*log(2)/log(10) + log10(d2) + * + * This suggests computing an approximation k to log10(d) by + * + * k = (i - Bias)*0.301029995663981 + * + ( (d2-1.5)*0.289529654602168 + 0.176091259055681 ); + * + * We want k to be too large rather than too small. + * The error in the first-order Taylor series approximation + * is in our favor, so we just round up the constant enough + * to compensate for any error in the multiplication of + * (i - Bias) by 0.301029995663981; since |i - Bias| <= 1077, + * and 1077 * 0.30103 * 2^-52 ~=~ 7.2e-14, + * adding 1e-13 to the constant term more than suffices. + * Hence we adjust the constant term to 0.1760912590558. + * (We could get a more accurate k by invoking log10, + * but this is probably not worthwhile.) + */ + + i -= Bias; + denorm = 0; + } + else { + /* d is denormalized */ + + i = bbits + be + (Bias + (P-1) - 1); + x = i > 32 ? word0(&u) << (64 - i) | word1(&u) >> (i - 32) + : word1(&u) << (32 - i); + dval(&d2) = x; + word0(&d2) -= 31*Exp_msk1; /* adjust exponent */ + i -= (Bias + (P-1) - 1) + 1; + denorm = 1; + } + ds = (dval(&d2)-1.5)*0.289529654602168 + 0.1760912590558 + + i*0.301029995663981; + k = (int)ds; + if (ds < 0. && ds != k) + k--; /* want k = floor(ds) */ + k_check = 1; + if (k >= 0 && k <= Ten_pmax) { + if (dval(&u) < tens[k]) + k--; + k_check = 0; + } + j = bbits - i - 1; + if (j >= 0) { + b2 = 0; + s2 = j; + } + else { + b2 = -j; + s2 = 0; + } + if (k >= 0) { + b5 = 0; + s5 = k; + s2 += k; + } + else { + b2 -= k; + b5 = -k; + s5 = 0; + } + if (mode < 0 || mode > 9) + mode = 0; + + try_quick = 1; + + if (mode > 5) { + mode -= 4; + try_quick = 0; + } + leftright = 1; + ilim = ilim1 = -1; /* Values for cases 0 and 1; done here to */ + /* silence erroneous "gcc -Wall" warning. */ + switch(mode) { + case 0: + case 1: + i = 18; + ndigits = 0; + break; + case 2: + leftright = 0; + /* no break */ + case 4: + if (ndigits <= 0) + ndigits = 1; + ilim = ilim1 = i = ndigits; + break; + case 3: + leftright = 0; + /* no break */ + case 5: + i = ndigits + k + 1; + ilim = i; + ilim1 = i - 1; + if (i <= 0) + i = 1; + } + s0 = rv_alloc(i); + if (s0 == NULL) + goto failed_malloc; + s = s0; + + + if (ilim >= 0 && ilim <= Quick_max && try_quick) { + + /* Try to get by with floating-point arithmetic. */ + + i = 0; + dval(&d2) = dval(&u); + k0 = k; + ilim0 = ilim; + ieps = 2; /* conservative */ + if (k > 0) { + ds = tens[k&0xf]; + j = k >> 4; + if (j & Bletch) { + /* prevent overflows */ + j &= Bletch - 1; + dval(&u) /= bigtens[n_bigtens-1]; + ieps++; + } + for(; j; j >>= 1, i++) + if (j & 1) { + ieps++; + ds *= bigtens[i]; + } + dval(&u) /= ds; + } + else if ((j1 = -k)) { + dval(&u) *= tens[j1 & 0xf]; + for(j = j1 >> 4; j; j >>= 1, i++) + if (j & 1) { + ieps++; + dval(&u) *= bigtens[i]; + } + } + if (k_check && dval(&u) < 1. && ilim > 0) { + if (ilim1 <= 0) + goto fast_failed; + ilim = ilim1; + k--; + dval(&u) *= 10.; + ieps++; + } + dval(&eps) = ieps*dval(&u) + 7.; + word0(&eps) -= (P-1)*Exp_msk1; + if (ilim == 0) { + S = mhi = 0; + dval(&u) -= 5.; + if (dval(&u) > dval(&eps)) + goto one_digit; + if (dval(&u) < -dval(&eps)) + goto no_digits; + goto fast_failed; + } + if (leftright) { + /* Use Steele & White method of only + * generating digits needed. + */ + dval(&eps) = 0.5/tens[ilim-1] - dval(&eps); + for(i = 0;;) { + L = (Long)dval(&u); + dval(&u) -= L; + *s++ = '0' + (int)L; + if (dval(&u) < dval(&eps)) + goto ret1; + if (1. - dval(&u) < dval(&eps)) + goto bump_up; + if (++i >= ilim) + break; + dval(&eps) *= 10.; + dval(&u) *= 10.; + } + } + else { + /* Generate ilim digits, then fix them up. */ + dval(&eps) *= tens[ilim-1]; + for(i = 1;; i++, dval(&u) *= 10.) { + L = (Long)(dval(&u)); + if (!(dval(&u) -= L)) + ilim = i; + *s++ = '0' + (int)L; + if (i == ilim) { + if (dval(&u) > 0.5 + dval(&eps)) + goto bump_up; + else if (dval(&u) < 0.5 - dval(&eps)) { + while(*--s == '0'); + s++; + goto ret1; + } + break; + } + } + } + fast_failed: + s = s0; + dval(&u) = dval(&d2); + k = k0; + ilim = ilim0; + } + + /* Do we have a "small" integer? */ + + if (be >= 0 && k <= Int_max) { + /* Yes. */ + ds = tens[k]; + if (ndigits < 0 && ilim <= 0) { + S = mhi = 0; + if (ilim < 0 || dval(&u) <= 5*ds) + goto no_digits; + goto one_digit; + } + for(i = 1;; i++, dval(&u) *= 10.) { + L = (Long)(dval(&u) / ds); + dval(&u) -= L*ds; + *s++ = '0' + (int)L; + if (!dval(&u)) { + break; + } + if (i == ilim) { + dval(&u) += dval(&u); + if (dval(&u) > ds || (dval(&u) == ds && L & 1)) { + bump_up: + while(*--s == '9') + if (s == s0) { + k++; + *s = '0'; + break; + } + ++*s++; + } + break; + } + } + goto ret1; + } + + m2 = b2; + m5 = b5; + if (leftright) { + i = + denorm ? be + (Bias + (P-1) - 1 + 1) : + 1 + P - bbits; + b2 += i; + s2 += i; + mhi = i2b(1); + if (mhi == NULL) + goto failed_malloc; + } + if (m2 > 0 && s2 > 0) { + i = m2 < s2 ? m2 : s2; + b2 -= i; + m2 -= i; + s2 -= i; + } + if (b5 > 0) { + if (leftright) { + if (m5 > 0) { + mhi = pow5mult(mhi, m5); + if (mhi == NULL) + goto failed_malloc; + b1 = mult(mhi, b); + Bfree(b); + b = b1; + if (b == NULL) + goto failed_malloc; + } + if ((j = b5 - m5)) { + b = pow5mult(b, j); + if (b == NULL) + goto failed_malloc; + } + } + else { + b = pow5mult(b, b5); + if (b == NULL) + goto failed_malloc; + } + } + S = i2b(1); + if (S == NULL) + goto failed_malloc; + if (s5 > 0) { + S = pow5mult(S, s5); + if (S == NULL) + goto failed_malloc; + } + + /* Check for special case that d is a normalized power of 2. */ + + spec_case = 0; + if ((mode < 2 || leftright) + ) { + if (!word1(&u) && !(word0(&u) & Bndry_mask) + && word0(&u) & (Exp_mask & ~Exp_msk1) + ) { + /* The special case */ + b2 += Log2P; + s2 += Log2P; + spec_case = 1; + } + } + + /* Arrange for convenient computation of quotients: + * shift left if necessary so divisor has 4 leading 0 bits. + * + * Perhaps we should just compute leading 28 bits of S once + * and for all and pass them and a shift to quorem, so it + * can do shifts and ors to compute the numerator for q. + */ +#define iInc 28 + i = dshift(S, s2); + b2 += i; + m2 += i; + s2 += i; + if (b2 > 0) { + b = lshift(b, b2); + if (b == NULL) + goto failed_malloc; + } + if (s2 > 0) { + S = lshift(S, s2); + if (S == NULL) + goto failed_malloc; + } + if (k_check) { + if (cmp(b,S) < 0) { + k--; + b = multadd(b, 10, 0); /* we botched the k estimate */ + if (b == NULL) + goto failed_malloc; + if (leftright) { + mhi = multadd(mhi, 10, 0); + if (mhi == NULL) + goto failed_malloc; + } + ilim = ilim1; + } + } + if (ilim <= 0 && (mode == 3 || mode == 5)) { + if (ilim < 0) { + /* no digits, fcvt style */ + no_digits: + k = -1 - ndigits; + goto ret; + } + else { + S = multadd(S, 5, 0); + if (S == NULL) + goto failed_malloc; + if (cmp(b, S) <= 0) + goto no_digits; + } + one_digit: + *s++ = '1'; + k++; + goto ret; + } + if (leftright) { + if (m2 > 0) { + mhi = lshift(mhi, m2); + if (mhi == NULL) + goto failed_malloc; + } + + /* Compute mlo -- check for special case + * that d is a normalized power of 2. + */ + + mlo = mhi; + if (spec_case) { + mhi = Balloc(mhi->k); + if (mhi == NULL) + goto failed_malloc; + Bcopy(mhi, mlo); + mhi = lshift(mhi, Log2P); + if (mhi == NULL) + goto failed_malloc; + } + + for(i = 1;;i++) { + dig = quorem(b,S) + '0'; + /* Do we yet have the shortest decimal string + * that will round to d? + */ + j = cmp(b, mlo); + delta = diff(S, mhi); + if (delta == NULL) + goto failed_malloc; + j1 = delta->sign ? 1 : cmp(b, delta); + Bfree(delta); + if (j1 == 0 && mode != 1 && !(word1(&u) & 1) + ) { + if (dig == '9') + goto round_9_up; + if (j > 0) + dig++; + *s++ = dig; + goto ret; + } + if (j < 0 || (j == 0 && mode != 1 + && !(word1(&u) & 1) + )) { + if (!b->x[0] && b->wds <= 1) { + goto accept_dig; + } + if (j1 > 0) { + b = lshift(b, 1); + if (b == NULL) + goto failed_malloc; + j1 = cmp(b, S); + if ((j1 > 0 || (j1 == 0 && dig & 1)) + && dig++ == '9') + goto round_9_up; + } + accept_dig: + *s++ = dig; + goto ret; + } + if (j1 > 0) { + if (dig == '9') { /* possible if i == 1 */ + round_9_up: + *s++ = '9'; + goto roundoff; + } + *s++ = dig + 1; + goto ret; + } + *s++ = dig; + if (i == ilim) + break; + b = multadd(b, 10, 0); + if (b == NULL) + goto failed_malloc; + if (mlo == mhi) { + mlo = mhi = multadd(mhi, 10, 0); + if (mlo == NULL) + goto failed_malloc; + } + else { + mlo = multadd(mlo, 10, 0); + if (mlo == NULL) + goto failed_malloc; + mhi = multadd(mhi, 10, 0); + if (mhi == NULL) + goto failed_malloc; + } + } + } + else + for(i = 1;; i++) { + *s++ = dig = quorem(b,S) + '0'; + if (!b->x[0] && b->wds <= 1) { + goto ret; + } + if (i >= ilim) + break; + b = multadd(b, 10, 0); + if (b == NULL) + goto failed_malloc; + } + + /* Round off last digit */ + + b = lshift(b, 1); + if (b == NULL) + goto failed_malloc; + j = cmp(b, S); + if (j > 0 || (j == 0 && dig & 1)) { + roundoff: + while(*--s == '9') + if (s == s0) { + k++; + *s++ = '1'; + goto ret; + } + ++*s++; + } + else { + while(*--s == '0'); + s++; + } + ret: + Bfree(S); + if (mhi) { + if (mlo && mlo != mhi) + Bfree(mlo); + Bfree(mhi); + } + ret1: + Bfree(b); + *s = 0; + *decpt = k + 1; + if (rve) + *rve = s; + return s0; + failed_malloc: + if (S) + Bfree(S); + if (mlo && mlo != mhi) + Bfree(mlo); + if (mhi) + Bfree(mhi); + if (b) + Bfree(b); + if (s0) + _Py_dg_freedtoa(s0); + return NULL; +} +#ifdef __cplusplus +} +#endif + +#endif /* PY_NO_SHORT_FLOAT_REPR */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/dynload_stub.c b/AppPkg/Applications/Python/Python-2.7.10/Python/dynload_stub.c new file mode 100644 index 0000000000..80f4abf84b --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/dynload_stub.c @@ -0,0 +1,11 @@ + +/* This module provides the necessary stubs for when dynamic loading is + not present. */ + +#include "Python.h" +#include "importdl.h" + + +const struct filedescr _PyImport_DynLoadFiletab[] = { + {0, 0} +}; diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/errors.c b/AppPkg/Applications/Python/Python-2.7.10/Python/errors.c new file mode 100644 index 0000000000..8e9b5da0c8 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/errors.c @@ -0,0 +1,827 @@ + +/* Error handling */ + +#include "Python.h" + +#ifndef __STDC__ +#ifndef MS_WINDOWS +extern char *strerror(int); +#endif +#endif + +#ifdef MS_WINDOWS +#include "windows.h" +#include "winbase.h" +#endif + +#include + +#ifdef __cplusplus +extern "C" { +#endif + + +void +PyErr_Restore(PyObject *type, PyObject *value, PyObject *traceback) +{ + PyThreadState *tstate = PyThreadState_GET(); + PyObject *oldtype, *oldvalue, *oldtraceback; + + if (traceback != NULL && !PyTraceBack_Check(traceback)) { + /* XXX Should never happen -- fatal error instead? */ + /* Well, it could be None. */ + Py_DECREF(traceback); + traceback = NULL; + } + + /* Save these in locals to safeguard against recursive + invocation through Py_XDECREF */ + oldtype = tstate->curexc_type; + oldvalue = tstate->curexc_value; + oldtraceback = tstate->curexc_traceback; + + tstate->curexc_type = type; + tstate->curexc_value = value; + tstate->curexc_traceback = traceback; + + Py_XDECREF(oldtype); + Py_XDECREF(oldvalue); + Py_XDECREF(oldtraceback); +} + +void +PyErr_SetObject(PyObject *exception, PyObject *value) +{ + Py_XINCREF(exception); + Py_XINCREF(value); + PyErr_Restore(exception, value, (PyObject *)NULL); +} + +void +PyErr_SetNone(PyObject *exception) +{ + PyErr_SetObject(exception, (PyObject *)NULL); +} + +void +PyErr_SetString(PyObject *exception, const char *string) +{ + PyObject *value = PyString_FromString(string); + PyErr_SetObject(exception, value); + Py_XDECREF(value); +} + + +PyObject * +PyErr_Occurred(void) +{ + PyThreadState *tstate = PyThreadState_GET(); + + return tstate->curexc_type; +} + + +int +PyErr_GivenExceptionMatches(PyObject *err, PyObject *exc) +{ + if (err == NULL || exc == NULL) { + /* maybe caused by "import exceptions" that failed early on */ + return 0; + } + if (PyTuple_Check(exc)) { + Py_ssize_t i, n; + n = PyTuple_Size(exc); + for (i = 0; i < n; i++) { + /* Test recursively */ + if (PyErr_GivenExceptionMatches( + err, PyTuple_GET_ITEM(exc, i))) + { + return 1; + } + } + return 0; + } + /* err might be an instance, so check its class. */ + if (PyExceptionInstance_Check(err)) + err = PyExceptionInstance_Class(err); + + if (PyExceptionClass_Check(err) && PyExceptionClass_Check(exc)) { + int res = 0, reclimit; + PyObject *exception, *value, *tb; + PyErr_Fetch(&exception, &value, &tb); + /* Temporarily bump the recursion limit, so that in the most + common case PyObject_IsSubclass will not raise a recursion + error we have to ignore anyway. Don't do it when the limit + is already insanely high, to avoid overflow */ + reclimit = Py_GetRecursionLimit(); + if (reclimit < (1 << 30)) + Py_SetRecursionLimit(reclimit + 5); + res = PyObject_IsSubclass(err, exc); + Py_SetRecursionLimit(reclimit); + /* This function must not fail, so print the error here */ + if (res == -1) { + PyErr_WriteUnraisable(err); + res = 0; + } + PyErr_Restore(exception, value, tb); + return res; + } + + return err == exc; +} + + +int +PyErr_ExceptionMatches(PyObject *exc) +{ + return PyErr_GivenExceptionMatches(PyErr_Occurred(), exc); +} + + +/* Used in many places to normalize a raised exception, including in + eval_code2(), do_raise(), and PyErr_Print() +*/ +void +PyErr_NormalizeException(PyObject **exc, PyObject **val, PyObject **tb) +{ + PyObject *type = *exc; + PyObject *value = *val; + PyObject *inclass = NULL; + PyObject *initial_tb = NULL; + PyThreadState *tstate = NULL; + + if (type == NULL) { + /* There was no exception, so nothing to do. */ + return; + } + + /* If PyErr_SetNone() was used, the value will have been actually + set to NULL. + */ + if (!value) { + value = Py_None; + Py_INCREF(value); + } + + if (PyExceptionInstance_Check(value)) + inclass = PyExceptionInstance_Class(value); + + /* Normalize the exception so that if the type is a class, the + value will be an instance. + */ + if (PyExceptionClass_Check(type)) { + /* if the value was not an instance, or is not an instance + whose class is (or is derived from) type, then use the + value as an argument to instantiation of the type + class. + */ + if (!inclass || !PyObject_IsSubclass(inclass, type)) { + PyObject *args, *res; + + if (value == Py_None) + args = PyTuple_New(0); + else if (PyTuple_Check(value)) { + Py_INCREF(value); + args = value; + } + else + args = PyTuple_Pack(1, value); + + if (args == NULL) + goto finally; + res = PyEval_CallObject(type, args); + Py_DECREF(args); + if (res == NULL) + goto finally; + Py_DECREF(value); + value = res; + } + /* if the class of the instance doesn't exactly match the + class of the type, believe the instance + */ + else if (inclass != type) { + Py_DECREF(type); + type = inclass; + Py_INCREF(type); + } + } + *exc = type; + *val = value; + return; +finally: + Py_DECREF(type); + Py_DECREF(value); + /* If the new exception doesn't set a traceback and the old + exception had a traceback, use the old traceback for the + new exception. It's better than nothing. + */ + initial_tb = *tb; + PyErr_Fetch(exc, val, tb); + if (initial_tb != NULL) { + if (*tb == NULL) + *tb = initial_tb; + else + Py_DECREF(initial_tb); + } + /* normalize recursively */ + tstate = PyThreadState_GET(); + if (++tstate->recursion_depth > Py_GetRecursionLimit()) { + --tstate->recursion_depth; + /* throw away the old exception... */ + Py_DECREF(*exc); + Py_DECREF(*val); + /* ... and use the recursion error instead */ + *exc = PyExc_RuntimeError; + *val = PyExc_RecursionErrorInst; + Py_INCREF(*exc); + Py_INCREF(*val); + /* just keeping the old traceback */ + return; + } + PyErr_NormalizeException(exc, val, tb); + --tstate->recursion_depth; +} + + +void +PyErr_Fetch(PyObject **p_type, PyObject **p_value, PyObject **p_traceback) +{ + PyThreadState *tstate = PyThreadState_GET(); + + *p_type = tstate->curexc_type; + *p_value = tstate->curexc_value; + *p_traceback = tstate->curexc_traceback; + + tstate->curexc_type = NULL; + tstate->curexc_value = NULL; + tstate->curexc_traceback = NULL; +} + +void +PyErr_Clear(void) +{ + PyErr_Restore(NULL, NULL, NULL); +} + +/* Restore previously fetched exception if an exception is not set, + otherwise drop previously fetched exception. + Like _PyErr_ChainExceptions() in Python 3, but doesn't set the context. + */ +void +_PyErr_ReplaceException(PyObject *exc, PyObject *val, PyObject *tb) +{ + if (exc == NULL) + return; + + if (PyErr_Occurred()) { + Py_DECREF(exc); + Py_XDECREF(val); + Py_XDECREF(tb); + } + else { + PyErr_Restore(exc, val, tb); + } +} + +/* Convenience functions to set a type error exception and return 0 */ + +int +PyErr_BadArgument(void) +{ + PyErr_SetString(PyExc_TypeError, + "bad argument type for built-in operation"); + return 0; +} + +PyObject * +PyErr_NoMemory(void) +{ + if (PyErr_ExceptionMatches(PyExc_MemoryError)) + /* already current */ + return NULL; + + /* raise the pre-allocated instance if it still exists */ + if (PyExc_MemoryErrorInst) + PyErr_SetObject(PyExc_MemoryError, PyExc_MemoryErrorInst); + else + /* this will probably fail since there's no memory and hee, + hee, we have to instantiate this class + */ + PyErr_SetNone(PyExc_MemoryError); + + return NULL; +} + +PyObject * +PyErr_SetFromErrnoWithFilenameObject(PyObject *exc, PyObject *filenameObject) +{ + PyObject *v; + char *s; + int i = errno; +#ifdef PLAN9 + char errbuf[ERRMAX]; +#endif +#ifdef MS_WINDOWS + char *s_buf = NULL; + char s_small_buf[28]; /* Room for "Windows Error 0xFFFFFFFF" */ +#endif +#ifdef EINTR + if (i == EINTR && PyErr_CheckSignals()) + return NULL; +#endif +#ifdef PLAN9 + rerrstr(errbuf, sizeof errbuf); + s = errbuf; +#else + if (i == 0) + s = "Error"; /* Sometimes errno didn't get set */ + else +#ifndef MS_WINDOWS + s = strerror(i); +#else + { + /* Note that the Win32 errors do not lineup with the + errno error. So if the error is in the MSVC error + table, we use it, otherwise we assume it really _is_ + a Win32 error code + */ + if (i > 0 && i < _sys_nerr) { + s = _sys_errlist[i]; + } + else { + int len = FormatMessage( + FORMAT_MESSAGE_ALLOCATE_BUFFER | + FORMAT_MESSAGE_FROM_SYSTEM | + FORMAT_MESSAGE_IGNORE_INSERTS, + NULL, /* no message source */ + i, + MAKELANGID(LANG_NEUTRAL, + SUBLANG_DEFAULT), + /* Default language */ + (LPTSTR) &s_buf, + 0, /* size not used */ + NULL); /* no args */ + if (len==0) { + /* Only ever seen this in out-of-mem + situations */ + sprintf(s_small_buf, "Windows Error 0x%X", i); + s = s_small_buf; + s_buf = NULL; + } else { + s = s_buf; + /* remove trailing cr/lf and dots */ + while (len > 0 && (s[len-1] <= ' ' || s[len-1] == '.')) + s[--len] = '\0'; + } + } + } +#endif /* Unix/Windows */ +#endif /* PLAN 9*/ + if (filenameObject != NULL) + v = Py_BuildValue("(isO)", i, s, filenameObject); + else + v = Py_BuildValue("(is)", i, s); + if (v != NULL) { + PyErr_SetObject(exc, v); + Py_DECREF(v); + } +#ifdef MS_WINDOWS + LocalFree(s_buf); +#endif + return NULL; +} + + +PyObject * +PyErr_SetFromErrnoWithFilename(PyObject *exc, const char *filename) +{ + PyObject *name = filename ? PyString_FromString(filename) : NULL; + PyObject *result = PyErr_SetFromErrnoWithFilenameObject(exc, name); + Py_XDECREF(name); + return result; +} + +#ifdef MS_WINDOWS +PyObject * +PyErr_SetFromErrnoWithUnicodeFilename(PyObject *exc, const Py_UNICODE *filename) +{ + PyObject *name = filename ? + PyUnicode_FromUnicode(filename, wcslen(filename)) : + NULL; + PyObject *result = PyErr_SetFromErrnoWithFilenameObject(exc, name); + Py_XDECREF(name); + return result; +} +#endif /* MS_WINDOWS */ + +PyObject * +PyErr_SetFromErrno(PyObject *exc) +{ + return PyErr_SetFromErrnoWithFilenameObject(exc, NULL); +} + +#ifdef MS_WINDOWS +/* Windows specific error code handling */ +PyObject *PyErr_SetExcFromWindowsErrWithFilenameObject( + PyObject *exc, + int ierr, + PyObject *filenameObject) +{ + int len; + char *s; + char *s_buf = NULL; /* Free via LocalFree */ + char s_small_buf[28]; /* Room for "Windows Error 0xFFFFFFFF" */ + PyObject *v; + DWORD err = (DWORD)ierr; + if (err==0) err = GetLastError(); + len = FormatMessage( + /* Error API error */ + FORMAT_MESSAGE_ALLOCATE_BUFFER | + FORMAT_MESSAGE_FROM_SYSTEM | + FORMAT_MESSAGE_IGNORE_INSERTS, + NULL, /* no message source */ + err, + MAKELANGID(LANG_NEUTRAL, + SUBLANG_DEFAULT), /* Default language */ + (LPTSTR) &s_buf, + 0, /* size not used */ + NULL); /* no args */ + if (len==0) { + /* Only seen this in out of mem situations */ + sprintf(s_small_buf, "Windows Error 0x%X", err); + s = s_small_buf; + s_buf = NULL; + } else { + s = s_buf; + /* remove trailing cr/lf and dots */ + while (len > 0 && (s[len-1] <= ' ' || s[len-1] == '.')) + s[--len] = '\0'; + } + if (filenameObject != NULL) + v = Py_BuildValue("(isO)", err, s, filenameObject); + else + v = Py_BuildValue("(is)", err, s); + if (v != NULL) { + PyErr_SetObject(exc, v); + Py_DECREF(v); + } + LocalFree(s_buf); + return NULL; +} + +PyObject *PyErr_SetExcFromWindowsErrWithFilename( + PyObject *exc, + int ierr, + const char *filename) +{ + PyObject *name = filename ? PyString_FromString(filename) : NULL; + PyObject *ret = PyErr_SetExcFromWindowsErrWithFilenameObject(exc, + ierr, + name); + Py_XDECREF(name); + return ret; +} + +PyObject *PyErr_SetExcFromWindowsErrWithUnicodeFilename( + PyObject *exc, + int ierr, + const Py_UNICODE *filename) +{ + PyObject *name = filename ? + PyUnicode_FromUnicode(filename, wcslen(filename)) : + NULL; + PyObject *ret = PyErr_SetExcFromWindowsErrWithFilenameObject(exc, + ierr, + name); + Py_XDECREF(name); + return ret; +} + +PyObject *PyErr_SetExcFromWindowsErr(PyObject *exc, int ierr) +{ + return PyErr_SetExcFromWindowsErrWithFilename(exc, ierr, NULL); +} + +PyObject *PyErr_SetFromWindowsErr(int ierr) +{ + return PyErr_SetExcFromWindowsErrWithFilename(PyExc_WindowsError, + ierr, NULL); +} +PyObject *PyErr_SetFromWindowsErrWithFilename( + int ierr, + const char *filename) +{ + PyObject *name = filename ? PyString_FromString(filename) : NULL; + PyObject *result = PyErr_SetExcFromWindowsErrWithFilenameObject( + PyExc_WindowsError, + ierr, name); + Py_XDECREF(name); + return result; +} + +PyObject *PyErr_SetFromWindowsErrWithUnicodeFilename( + int ierr, + const Py_UNICODE *filename) +{ + PyObject *name = filename ? + PyUnicode_FromUnicode(filename, wcslen(filename)) : + NULL; + PyObject *result = PyErr_SetExcFromWindowsErrWithFilenameObject( + PyExc_WindowsError, + ierr, name); + Py_XDECREF(name); + return result; +} +#endif /* MS_WINDOWS */ + +void +_PyErr_BadInternalCall(char *filename, int lineno) +{ + PyErr_Format(PyExc_SystemError, + "%s:%d: bad argument to internal function", + filename, lineno); +} + +/* Remove the preprocessor macro for PyErr_BadInternalCall() so that we can + export the entry point for existing object code: */ +#undef PyErr_BadInternalCall +void +PyErr_BadInternalCall(void) +{ + PyErr_Format(PyExc_SystemError, + "bad argument to internal function"); +} +#define PyErr_BadInternalCall() _PyErr_BadInternalCall(__FILE__, __LINE__) + + + +PyObject * +PyErr_Format(PyObject *exception, const char *format, ...) +{ + va_list vargs; + PyObject* string; + +#ifdef HAVE_STDARG_PROTOTYPES + va_start(vargs, format); +#else + va_start(vargs); +#endif + + string = PyString_FromFormatV(format, vargs); + PyErr_SetObject(exception, string); + Py_XDECREF(string); + va_end(vargs); + return NULL; +} + + + +PyObject * +PyErr_NewException(char *name, PyObject *base, PyObject *dict) +{ + char *dot; + PyObject *modulename = NULL; + PyObject *classname = NULL; + PyObject *mydict = NULL; + PyObject *bases = NULL; + PyObject *result = NULL; + dot = strrchr(name, '.'); + if (dot == NULL) { + PyErr_SetString(PyExc_SystemError, + "PyErr_NewException: name must be module.class"); + return NULL; + } + if (base == NULL) + base = PyExc_Exception; + if (dict == NULL) { + dict = mydict = PyDict_New(); + if (dict == NULL) + goto failure; + } + if (PyDict_GetItemString(dict, "__module__") == NULL) { + modulename = PyString_FromStringAndSize(name, + (Py_ssize_t)(dot-name)); + if (modulename == NULL) + goto failure; + if (PyDict_SetItemString(dict, "__module__", modulename) != 0) + goto failure; + } + if (PyTuple_Check(base)) { + bases = base; + /* INCREF as we create a new ref in the else branch */ + Py_INCREF(bases); + } else { + bases = PyTuple_Pack(1, base); + if (bases == NULL) + goto failure; + } + /* Create a real new-style class. */ + result = PyObject_CallFunction((PyObject *)&PyType_Type, "sOO", + dot+1, bases, dict); + failure: + Py_XDECREF(bases); + Py_XDECREF(mydict); + Py_XDECREF(classname); + Py_XDECREF(modulename); + return result; +} + + +/* Create an exception with docstring */ +PyObject * +PyErr_NewExceptionWithDoc(char *name, char *doc, PyObject *base, PyObject *dict) +{ + int result; + PyObject *ret = NULL; + PyObject *mydict = NULL; /* points to the dict only if we create it */ + PyObject *docobj; + + if (dict == NULL) { + dict = mydict = PyDict_New(); + if (dict == NULL) { + return NULL; + } + } + + if (doc != NULL) { + docobj = PyString_FromString(doc); + if (docobj == NULL) + goto failure; + result = PyDict_SetItemString(dict, "__doc__", docobj); + Py_DECREF(docobj); + if (result < 0) + goto failure; + } + + ret = PyErr_NewException(name, base, dict); + failure: + Py_XDECREF(mydict); + return ret; +} + + +/* Call when an exception has occurred but there is no way for Python + to handle it. Examples: exception in __del__ or during GC. */ +void +PyErr_WriteUnraisable(PyObject *obj) +{ + PyObject *f, *t, *v, *tb; + PyErr_Fetch(&t, &v, &tb); + f = PySys_GetObject("stderr"); + if (f != NULL) { + PyFile_WriteString("Exception ", f); + if (t) { + PyObject* moduleName; + char* className; + assert(PyExceptionClass_Check(t)); + className = PyExceptionClass_Name(t); + if (className != NULL) { + char *dot = strrchr(className, '.'); + if (dot != NULL) + className = dot+1; + } + + moduleName = PyObject_GetAttrString(t, "__module__"); + if (moduleName == NULL) + PyFile_WriteString("", f); + else { + char* modstr = PyString_AsString(moduleName); + if (modstr && + strcmp(modstr, "exceptions") != 0) + { + PyFile_WriteString(modstr, f); + PyFile_WriteString(".", f); + } + } + if (className == NULL) + PyFile_WriteString("", f); + else + PyFile_WriteString(className, f); + if (v && v != Py_None) { + PyFile_WriteString(": ", f); + PyFile_WriteObject(v, f, 0); + } + Py_XDECREF(moduleName); + } + PyFile_WriteString(" in ", f); + PyFile_WriteObject(obj, f, 0); + PyFile_WriteString(" ignored\n", f); + PyErr_Clear(); /* Just in case */ + } + Py_XDECREF(t); + Py_XDECREF(v); + Py_XDECREF(tb); +} + +extern PyObject *PyModule_GetWarningsModule(void); + + +/* Set file and line information for the current exception. + If the exception is not a SyntaxError, also sets additional attributes + to make printing of exceptions believe it is a syntax error. */ + +void +PyErr_SyntaxLocation(const char *filename, int lineno) +{ + PyObject *exc, *v, *tb, *tmp; + + /* add attributes for the line number and filename for the error */ + PyErr_Fetch(&exc, &v, &tb); + PyErr_NormalizeException(&exc, &v, &tb); + /* XXX check that it is, indeed, a syntax error. It might not + * be, though. */ + tmp = PyInt_FromLong(lineno); + if (tmp == NULL) + PyErr_Clear(); + else { + if (PyObject_SetAttrString(v, "lineno", tmp)) + PyErr_Clear(); + Py_DECREF(tmp); + } + if (filename != NULL) { + tmp = PyString_FromString(filename); + if (tmp == NULL) + PyErr_Clear(); + else { + if (PyObject_SetAttrString(v, "filename", tmp)) + PyErr_Clear(); + Py_DECREF(tmp); + } + + tmp = PyErr_ProgramText(filename, lineno); + if (tmp) { + if (PyObject_SetAttrString(v, "text", tmp)) + PyErr_Clear(); + Py_DECREF(tmp); + } + } + if (PyObject_SetAttrString(v, "offset", Py_None)) { + PyErr_Clear(); + } + if (exc != PyExc_SyntaxError) { + if (!PyObject_HasAttrString(v, "msg")) { + tmp = PyObject_Str(v); + if (tmp) { + if (PyObject_SetAttrString(v, "msg", tmp)) + PyErr_Clear(); + Py_DECREF(tmp); + } else { + PyErr_Clear(); + } + } + if (!PyObject_HasAttrString(v, "print_file_and_line")) { + if (PyObject_SetAttrString(v, "print_file_and_line", + Py_None)) + PyErr_Clear(); + } + } + PyErr_Restore(exc, v, tb); +} + +/* com_fetch_program_text will attempt to load the line of text that + the exception refers to. If it fails, it will return NULL but will + not set an exception. + + XXX The functionality of this function is quite similar to the + functionality in tb_displayline() in traceback.c. +*/ + +PyObject * +PyErr_ProgramText(const char *filename, int lineno) +{ + FILE *fp; + int i; + char linebuf[1000]; + + if (filename == NULL || *filename == '\0' || lineno <= 0) + return NULL; + fp = fopen(filename, "r" PY_STDIOTEXTMODE); + if (fp == NULL) + return NULL; + for (i = 0; i < lineno; i++) { + char *pLastChar = &linebuf[sizeof(linebuf) - 2]; + do { + *pLastChar = '\0'; + if (Py_UniversalNewlineFgets(linebuf, sizeof linebuf, fp, NULL) == NULL) + break; + /* fgets read *something*; if it didn't get as + far as pLastChar, it must have found a newline + or hit the end of the file; if pLastChar is \n, + it obviously found a newline; else we haven't + yet seen a newline, so must continue */ + } while (*pLastChar != '\0' && *pLastChar != '\n'); + } + fclose(fp); + if (i == lineno) { + char *p = linebuf; + while (*p == ' ' || *p == '\t' || *p == '\014') + p++; + return PyString_FromString(p); + } + return NULL; +} + +#ifdef __cplusplus +} +#endif + diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/formatter_string.c b/AppPkg/Applications/Python/Python-2.7.10/Python/formatter_string.c new file mode 100644 index 0000000000..1ab52e7772 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/formatter_string.c @@ -0,0 +1,17 @@ +/***********************************************************************/ +/* Implements the string (as opposed to unicode) version of the + built-in formatters for string, int, float. That is, the versions + of int.__format__, etc., that take and return string objects */ + +#include "Python.h" +#include "../Objects/stringlib/stringdefs.h" + +#define FORMAT_STRING _PyBytes_FormatAdvanced +#define FORMAT_LONG _PyLong_FormatAdvanced +#define FORMAT_INT _PyInt_FormatAdvanced +#define FORMAT_FLOAT _PyFloat_FormatAdvanced +#ifndef WITHOUT_COMPLEX +#define FORMAT_COMPLEX _PyComplex_FormatAdvanced +#endif + +#include "../Objects/stringlib/formatter.h" diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/formatter_unicode.c b/AppPkg/Applications/Python/Python-2.7.10/Python/formatter_unicode.c new file mode 100644 index 0000000000..c43163927d --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/formatter_unicode.c @@ -0,0 +1,18 @@ +/* Implements the unicode (as opposed to string) version of the + built-in formatter for unicode. That is, unicode.__format__(). */ + +#include "Python.h" + +#ifdef Py_USING_UNICODE + +#include "../Objects/stringlib/unicodedefs.h" + +#define FORMAT_STRING _PyUnicode_FormatAdvanced + +/* don't define FORMAT_LONG, FORMAT_FLOAT, and FORMAT_COMPLEX, since + we can live with only the string versions of those. The builtin + format() will convert them to unicode. */ + +#include "../Objects/stringlib/formatter.h" + +#endif diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/frozen.c b/AppPkg/Applications/Python/Python-2.7.10/Python/frozen.c new file mode 100644 index 0000000000..1ec3603436 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/frozen.c @@ -0,0 +1,38 @@ + +/* Dummy frozen modules initializer */ + +#include "Python.h" + +/* In order to test the support for frozen modules, by default we + define a single frozen module, __hello__. Loading it will print + some famous words... */ + +/* To regenerate this data after the bytecode or marshal format has changed, + go to ../Tools/freeze/ and freeze the hello.py file; then copy and paste + the appropriate bytes from M___main__.c. */ + +static unsigned char M___hello__[] = { + 99,0,0,0,0,0,0,0,0,1,0,0,0,0,0,0, + 0,115,9,0,0,0,100,0,0,71,72,100,1,0,83,40, + 2,0,0,0,115,14,0,0,0,72,101,108,108,111,32,119, + 111,114,108,100,46,46,46,78,40,0,0,0,0,40,0,0, + 0,0,40,0,0,0,0,40,0,0,0,0,115,8,0,0, + 0,104,101,108,108,111,46,112,121,115,1,0,0,0,63,1, + 0,0,0,115,0,0,0,0, +}; + +#define SIZE (int)sizeof(M___hello__) + +static struct _frozen _PyImport_FrozenModules[] = { + /* Test module */ + {"__hello__", M___hello__, SIZE}, + /* Test package (negative size indicates package-ness) */ + {"__phello__", M___hello__, -SIZE}, + {"__phello__.spam", M___hello__, SIZE}, + {0, 0, 0} /* sentinel */ +}; + +/* Embedding apps may change this pointer to point to their favorite + collection of frozen modules: */ + +struct _frozen *PyImport_FrozenModules = _PyImport_FrozenModules; diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/future.c b/AppPkg/Applications/Python/Python-2.7.10/Python/future.c new file mode 100644 index 0000000000..740678d97f --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/future.c @@ -0,0 +1,137 @@ +#include "Python.h" +#include "Python-ast.h" +#include "node.h" +#include "token.h" +#include "graminit.h" +#include "code.h" +#include "compile.h" +#include "symtable.h" + +#define UNDEFINED_FUTURE_FEATURE "future feature %.100s is not defined" +#define ERR_LATE_FUTURE \ +"from __future__ imports must occur at the beginning of the file" + +static int +future_check_features(PyFutureFeatures *ff, stmt_ty s, const char *filename) +{ + int i; + asdl_seq *names; + + assert(s->kind == ImportFrom_kind); + + names = s->v.ImportFrom.names; + for (i = 0; i < asdl_seq_LEN(names); i++) { + alias_ty name = (alias_ty)asdl_seq_GET(names, i); + const char *feature = PyString_AsString(name->name); + if (!feature) + return 0; + if (strcmp(feature, FUTURE_NESTED_SCOPES) == 0) { + continue; + } else if (strcmp(feature, FUTURE_GENERATORS) == 0) { + continue; + } else if (strcmp(feature, FUTURE_DIVISION) == 0) { + ff->ff_features |= CO_FUTURE_DIVISION; + } else if (strcmp(feature, FUTURE_ABSOLUTE_IMPORT) == 0) { + ff->ff_features |= CO_FUTURE_ABSOLUTE_IMPORT; + } else if (strcmp(feature, FUTURE_WITH_STATEMENT) == 0) { + ff->ff_features |= CO_FUTURE_WITH_STATEMENT; + } else if (strcmp(feature, FUTURE_PRINT_FUNCTION) == 0) { + ff->ff_features |= CO_FUTURE_PRINT_FUNCTION; + } else if (strcmp(feature, FUTURE_UNICODE_LITERALS) == 0) { + ff->ff_features |= CO_FUTURE_UNICODE_LITERALS; + } else if (strcmp(feature, "braces") == 0) { + PyErr_SetString(PyExc_SyntaxError, + "not a chance"); + PyErr_SyntaxLocation(filename, s->lineno); + return 0; + } else { + PyErr_Format(PyExc_SyntaxError, + UNDEFINED_FUTURE_FEATURE, feature); + PyErr_SyntaxLocation(filename, s->lineno); + return 0; + } + } + return 1; +} + +static int +future_parse(PyFutureFeatures *ff, mod_ty mod, const char *filename) +{ + int i, found_docstring = 0, done = 0, prev_line = 0; + + if (!(mod->kind == Module_kind || mod->kind == Interactive_kind)) + return 1; + + /* A subsequent pass will detect future imports that don't + appear at the beginning of the file. There's one case, + however, that is easier to handle here: A series of imports + joined by semi-colons, where the first import is a future + statement but some subsequent import has the future form + but is preceded by a regular import. + */ + + + for (i = 0; i < asdl_seq_LEN(mod->v.Module.body); i++) { + stmt_ty s = (stmt_ty)asdl_seq_GET(mod->v.Module.body, i); + + if (done && s->lineno > prev_line) + return 1; + prev_line = s->lineno; + + /* The tests below will return from this function unless it is + still possible to find a future statement. The only things + that can precede a future statement are another future + statement and a doc string. + */ + + if (s->kind == ImportFrom_kind) { + identifier modname = s->v.ImportFrom.module; + if (modname && PyString_GET_SIZE(modname) == 10 && + !strcmp(PyString_AS_STRING(modname), "__future__")) { + if (done) { + PyErr_SetString(PyExc_SyntaxError, + ERR_LATE_FUTURE); + PyErr_SyntaxLocation(filename, + s->lineno); + return 0; + } + if (!future_check_features(ff, s, filename)) + return 0; + ff->ff_lineno = s->lineno; + } + else + done = 1; + } + else if (s->kind == Expr_kind && !found_docstring) { + expr_ty e = s->v.Expr.value; + if (e->kind != Str_kind) + done = 1; + else + found_docstring = 1; + } + else + done = 1; + } + return 1; +} + + +PyFutureFeatures * +PyFuture_FromAST(mod_ty mod, const char *filename) +{ + PyFutureFeatures *ff; + + ff = (PyFutureFeatures *)PyObject_Malloc(sizeof(PyFutureFeatures)); + if (ff == NULL) { + PyErr_NoMemory(); + return NULL; + } + ff->ff_features = 0; + ff->ff_lineno = -1; + + if (!future_parse(ff, mod, filename)) { + PyObject_Free(ff); + return NULL; + } + return ff; +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/getargs.c b/AppPkg/Applications/Python/Python-2.7.10/Python/getargs.c new file mode 100644 index 0000000000..debec57bac --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/getargs.c @@ -0,0 +1,1908 @@ + +/* New getargs implementation */ + +#include "Python.h" + +#include + + +#ifdef __cplusplus +extern "C" { +#endif +int PyArg_Parse(PyObject *, const char *, ...); +int PyArg_ParseTuple(PyObject *, const char *, ...); +int PyArg_VaParse(PyObject *, const char *, va_list); + +int PyArg_ParseTupleAndKeywords(PyObject *, PyObject *, + const char *, char **, ...); +int PyArg_VaParseTupleAndKeywords(PyObject *, PyObject *, + const char *, char **, va_list); + +#ifdef HAVE_DECLSPEC_DLL +/* Export functions */ +PyAPI_FUNC(int) _PyArg_Parse_SizeT(PyObject *, char *, ...); +PyAPI_FUNC(int) _PyArg_ParseTuple_SizeT(PyObject *, char *, ...); +PyAPI_FUNC(int) _PyArg_ParseTupleAndKeywords_SizeT(PyObject *, PyObject *, + const char *, char **, ...); +PyAPI_FUNC(PyObject *) _Py_BuildValue_SizeT(const char *, ...); +PyAPI_FUNC(int) _PyArg_VaParse_SizeT(PyObject *, char *, va_list); +PyAPI_FUNC(int) _PyArg_VaParseTupleAndKeywords_SizeT(PyObject *, PyObject *, + const char *, char **, va_list); +#endif + +#define FLAG_COMPAT 1 +#define FLAG_SIZE_T 2 + + +/* Forward */ +static int vgetargs1(PyObject *, const char *, va_list *, int); +static void seterror(int, const char *, int *, const char *, const char *); +static char *convertitem(PyObject *, const char **, va_list *, int, int *, + char *, size_t, PyObject **); +static char *converttuple(PyObject *, const char **, va_list *, int, + int *, char *, size_t, int, PyObject **); +static char *convertsimple(PyObject *, const char **, va_list *, int, char *, + size_t, PyObject **); +static Py_ssize_t convertbuffer(PyObject *, void **p, char **); +static int getbuffer(PyObject *, Py_buffer *, char**); + +static int vgetargskeywords(PyObject *, PyObject *, + const char *, char **, va_list *, int); +static char *skipitem(const char **, va_list *, int); + +int +PyArg_Parse(PyObject *args, const char *format, ...) +{ + int retval; + va_list va; + + va_start(va, format); + retval = vgetargs1(args, format, &va, FLAG_COMPAT); + va_end(va); + return retval; +} + +int +_PyArg_Parse_SizeT(PyObject *args, char *format, ...) +{ + int retval; + va_list va; + + va_start(va, format); + retval = vgetargs1(args, format, &va, FLAG_COMPAT|FLAG_SIZE_T); + va_end(va); + return retval; +} + + +int +PyArg_ParseTuple(PyObject *args, const char *format, ...) +{ + int retval; + va_list va; + + va_start(va, format); + retval = vgetargs1(args, format, &va, 0); + va_end(va); + return retval; +} + +int +_PyArg_ParseTuple_SizeT(PyObject *args, char *format, ...) +{ + int retval; + va_list va; + + va_start(va, format); + retval = vgetargs1(args, format, &va, FLAG_SIZE_T); + va_end(va); + return retval; +} + + +int +PyArg_VaParse(PyObject *args, const char *format, va_list va) +{ + va_list lva; + +#ifdef VA_LIST_IS_ARRAY + memcpy(lva, va, sizeof(va_list)); +#else +#ifdef __va_copy + __va_copy(lva, va); +#else + lva = va; +#endif +#endif + + return vgetargs1(args, format, &lva, 0); +} + +int +_PyArg_VaParse_SizeT(PyObject *args, char *format, va_list va) +{ + va_list lva; + +#ifdef VA_LIST_IS_ARRAY + memcpy(lva, va, sizeof(va_list)); +#else +#ifdef __va_copy + __va_copy(lva, va); +#else + lva = va; +#endif +#endif + + return vgetargs1(args, format, &lva, FLAG_SIZE_T); +} + + +/* Handle cleanup of allocated memory in case of exception */ + +#define GETARGS_CAPSULE_NAME_CLEANUP_PTR "getargs.cleanup_ptr" +#define GETARGS_CAPSULE_NAME_CLEANUP_BUFFER "getargs.cleanup_buffer" + +static void +cleanup_ptr(PyObject *self) +{ + void *ptr = PyCapsule_GetPointer(self, GETARGS_CAPSULE_NAME_CLEANUP_PTR); + if (ptr) { + PyMem_FREE(ptr); + } +} + +static void +cleanup_buffer(PyObject *self) +{ + Py_buffer *ptr = (Py_buffer *)PyCapsule_GetPointer(self, GETARGS_CAPSULE_NAME_CLEANUP_BUFFER); + if (ptr) { + PyBuffer_Release(ptr); + } +} + +static int +addcleanup(void *ptr, PyObject **freelist, PyCapsule_Destructor destr) +{ + PyObject *cobj; + const char *name; + + if (!*freelist) { + *freelist = PyList_New(0); + if (!*freelist) { + destr(ptr); + return -1; + } + } + + if (destr == cleanup_ptr) { + name = GETARGS_CAPSULE_NAME_CLEANUP_PTR; + } else if (destr == cleanup_buffer) { + name = GETARGS_CAPSULE_NAME_CLEANUP_BUFFER; + } else { + return -1; + } + cobj = PyCapsule_New(ptr, name, destr); + if (!cobj) { + destr(ptr); + return -1; + } + if (PyList_Append(*freelist, cobj)) { + Py_DECREF(cobj); + return -1; + } + Py_DECREF(cobj); + return 0; +} + +static int +cleanreturn(int retval, PyObject *freelist) +{ + if (freelist && retval != 0) { + /* We were successful, reset the destructors so that they + don't get called. */ + Py_ssize_t len = PyList_GET_SIZE(freelist), i; + for (i = 0; i < len; i++) + PyCapsule_SetDestructor(PyList_GET_ITEM(freelist, i), NULL); + } + Py_XDECREF(freelist); + return retval; +} + + +static int +vgetargs1(PyObject *args, const char *format, va_list *p_va, int flags) +{ + char msgbuf[256]; + int levels[32]; + const char *fname = NULL; + const char *message = NULL; + int min = -1; + int max = 0; + int level = 0; + int endfmt = 0; + const char *formatsave = format; + Py_ssize_t i, len; + char *msg; + PyObject *freelist = NULL; + int compat = flags & FLAG_COMPAT; + + assert(compat || (args != (PyObject*)NULL)); + flags = flags & ~FLAG_COMPAT; + + while (endfmt == 0) { + int c = *format++; + switch (c) { + case '(': + if (level == 0) + max++; + level++; + if (level >= 30) + Py_FatalError("too many tuple nesting levels " + "in argument format string"); + break; + case ')': + if (level == 0) + Py_FatalError("excess ')' in getargs format"); + else + level--; + break; + case '\0': + endfmt = 1; + break; + case ':': + fname = format; + endfmt = 1; + break; + case ';': + message = format; + endfmt = 1; + break; + default: + if (level == 0) { + if (c == 'O') + max++; + else if (isalpha(Py_CHARMASK(c))) { + if (c != 'e') /* skip encoded */ + max++; + } else if (c == '|') + min = max; + } + break; + } + } + + if (level != 0) + Py_FatalError(/* '(' */ "missing ')' in getargs format"); + + if (min < 0) + min = max; + + format = formatsave; + + if (compat) { + if (max == 0) { + if (args == NULL) + return 1; + PyOS_snprintf(msgbuf, sizeof(msgbuf), + "%.200s%s takes no arguments", + fname==NULL ? "function" : fname, + fname==NULL ? "" : "()"); + PyErr_SetString(PyExc_TypeError, msgbuf); + return 0; + } + else if (min == 1 && max == 1) { + if (args == NULL) { + PyOS_snprintf(msgbuf, sizeof(msgbuf), + "%.200s%s takes at least one argument", + fname==NULL ? "function" : fname, + fname==NULL ? "" : "()"); + PyErr_SetString(PyExc_TypeError, msgbuf); + return 0; + } + msg = convertitem(args, &format, p_va, flags, levels, + msgbuf, sizeof(msgbuf), &freelist); + if (msg == NULL) + return cleanreturn(1, freelist); + seterror(levels[0], msg, levels+1, fname, message); + return cleanreturn(0, freelist); + } + else { + PyErr_SetString(PyExc_SystemError, + "old style getargs format uses new features"); + return 0; + } + } + + if (!PyTuple_Check(args)) { + PyErr_SetString(PyExc_SystemError, + "new style getargs format but argument is not a tuple"); + return 0; + } + + len = PyTuple_GET_SIZE(args); + + if (len < min || max < len) { + if (message == NULL) { + PyOS_snprintf(msgbuf, sizeof(msgbuf), + "%.150s%s takes %s %d argument%s " + "(%ld given)", + fname==NULL ? "function" : fname, + fname==NULL ? "" : "()", + min==max ? "exactly" + : len < min ? "at least" : "at most", + len < min ? min : max, + (len < min ? min : max) == 1 ? "" : "s", + Py_SAFE_DOWNCAST(len, Py_ssize_t, long)); + message = msgbuf; + } + PyErr_SetString(PyExc_TypeError, message); + return 0; + } + + for (i = 0; i < len; i++) { + if (*format == '|') + format++; + msg = convertitem(PyTuple_GET_ITEM(args, i), &format, p_va, + flags, levels, msgbuf, + sizeof(msgbuf), &freelist); + if (msg) { + seterror(i+1, msg, levels, fname, msg); + return cleanreturn(0, freelist); + } + } + + if (*format != '\0' && !isalpha(Py_CHARMASK(*format)) && + *format != '(' && + *format != '|' && *format != ':' && *format != ';') { + PyErr_Format(PyExc_SystemError, + "bad format string: %.200s", formatsave); + return cleanreturn(0, freelist); + } + + return cleanreturn(1, freelist); +} + + + +static void +seterror(int iarg, const char *msg, int *levels, const char *fname, + const char *message) +{ + char buf[512]; + int i; + char *p = buf; + + if (PyErr_Occurred()) + return; + else if (message == NULL) { + if (fname != NULL) { + PyOS_snprintf(p, sizeof(buf), "%.200s() ", fname); + p += strlen(p); + } + if (iarg != 0) { + PyOS_snprintf(p, sizeof(buf) - (p - buf), + "argument %d", iarg); + i = 0; + p += strlen(p); + while (levels[i] > 0 && i < 32 && (int)(p-buf) < 220) { + PyOS_snprintf(p, sizeof(buf) - (p - buf), + ", item %d", levels[i]-1); + p += strlen(p); + i++; + } + } + else { + PyOS_snprintf(p, sizeof(buf) - (p - buf), "argument"); + p += strlen(p); + } + PyOS_snprintf(p, sizeof(buf) - (p - buf), " %.256s", msg); + message = buf; + } + PyErr_SetString(PyExc_TypeError, message); +} + + +/* Convert a tuple argument. + On entry, *p_format points to the character _after_ the opening '('. + On successful exit, *p_format points to the closing ')'. + If successful: + *p_format and *p_va are updated, + *levels and *msgbuf are untouched, + and NULL is returned. + If the argument is invalid: + *p_format is unchanged, + *p_va is undefined, + *levels is a 0-terminated list of item numbers, + *msgbuf contains an error message, whose format is: + "must be , not ", where: + is the name of the expected type, and + is the name of the actual type, + and msgbuf is returned. +*/ + +static char * +converttuple(PyObject *arg, const char **p_format, va_list *p_va, int flags, + int *levels, char *msgbuf, size_t bufsize, int toplevel, + PyObject **freelist) +{ + int level = 0; + int n = 0; + const char *format = *p_format; + int i; + + for (;;) { + int c = *format++; + if (c == '(') { + if (level == 0) + n++; + level++; + } + else if (c == ')') { + if (level == 0) + break; + level--; + } + else if (c == ':' || c == ';' || c == '\0') + break; + else if (level == 0 && isalpha(Py_CHARMASK(c))) + n++; + } + + if (!PySequence_Check(arg) || PyString_Check(arg)) { + levels[0] = 0; + PyOS_snprintf(msgbuf, bufsize, + toplevel ? "expected %d arguments, not %.50s" : + "must be %d-item sequence, not %.50s", + n, + arg == Py_None ? "None" : arg->ob_type->tp_name); + return msgbuf; + } + + if ((i = PySequence_Size(arg)) != n) { + levels[0] = 0; + PyOS_snprintf(msgbuf, bufsize, + toplevel ? "expected %d arguments, not %d" : + "must be sequence of length %d, not %d", + n, i); + return msgbuf; + } + + format = *p_format; + for (i = 0; i < n; i++) { + char *msg; + PyObject *item; + item = PySequence_GetItem(arg, i); + if (item == NULL) { + PyErr_Clear(); + levels[0] = i+1; + levels[1] = 0; + strncpy(msgbuf, "is not retrievable", bufsize); + return msgbuf; + } + msg = convertitem(item, &format, p_va, flags, levels+1, + msgbuf, bufsize, freelist); + /* PySequence_GetItem calls tp->sq_item, which INCREFs */ + Py_XDECREF(item); + if (msg != NULL) { + levels[0] = i+1; + return msg; + } + } + + *p_format = format; + return NULL; +} + + +/* Convert a single item. */ + +static char * +convertitem(PyObject *arg, const char **p_format, va_list *p_va, int flags, + int *levels, char *msgbuf, size_t bufsize, PyObject **freelist) +{ + char *msg; + const char *format = *p_format; + + if (*format == '(' /* ')' */) { + format++; + msg = converttuple(arg, &format, p_va, flags, levels, msgbuf, + bufsize, 0, freelist); + if (msg == NULL) + format++; + } + else { + msg = convertsimple(arg, &format, p_va, flags, + msgbuf, bufsize, freelist); + if (msg != NULL) + levels[0] = 0; + } + if (msg == NULL) + *p_format = format; + return msg; +} + + + +#define UNICODE_DEFAULT_ENCODING(arg) \ + _PyUnicode_AsDefaultEncodedString(arg, NULL) + +/* Format an error message generated by convertsimple(). */ + +static char * +converterr(const char *expected, PyObject *arg, char *msgbuf, size_t bufsize) +{ + assert(expected != NULL); + assert(arg != NULL); + PyOS_snprintf(msgbuf, bufsize, + "must be %.50s, not %.50s", expected, + arg == Py_None ? "None" : arg->ob_type->tp_name); + return msgbuf; +} + +#define CONV_UNICODE "(unicode conversion error)" + +/* explicitly check for float arguments when integers are expected. For now + * signal a warning. Returns true if an exception was raised. */ +static int +float_argument_warning(PyObject *arg) +{ + if (PyFloat_Check(arg) && + PyErr_Warn(PyExc_DeprecationWarning, + "integer argument expected, got float" )) + return 1; + else + return 0; +} + +/* explicitly check for float arguments when integers are expected. Raises + TypeError and returns true for float arguments. */ +static int +float_argument_error(PyObject *arg) +{ + if (PyFloat_Check(arg)) { + PyErr_SetString(PyExc_TypeError, + "integer argument expected, got float"); + return 1; + } + else + return 0; +} + +/* Convert a non-tuple argument. Return NULL if conversion went OK, + or a string with a message describing the failure. The message is + formatted as "must be , not ". + When failing, an exception may or may not have been raised. + Don't call if a tuple is expected. + + When you add new format codes, please don't forget poor skipitem() below. +*/ + +static char * +convertsimple(PyObject *arg, const char **p_format, va_list *p_va, int flags, + char *msgbuf, size_t bufsize, PyObject **freelist) +{ + /* For # codes */ +#define FETCH_SIZE int *q=NULL;Py_ssize_t *q2=NULL;\ + if (flags & FLAG_SIZE_T) q2=va_arg(*p_va, Py_ssize_t*); \ + else q=va_arg(*p_va, int*); +#define STORE_SIZE(s) \ + if (flags & FLAG_SIZE_T) \ + *q2=s; \ + else { \ + if (INT_MAX < s) { \ + PyErr_SetString(PyExc_OverflowError, \ + "size does not fit in an int"); \ + return converterr("", arg, msgbuf, bufsize); \ + } \ + *q=s; \ + } +#define BUFFER_LEN ((flags & FLAG_SIZE_T) ? *q2:*q) + + const char *format = *p_format; + char c = *format++; +#ifdef Py_USING_UNICODE + PyObject *uarg; +#endif + + switch (c) { + + case 'b': { /* unsigned byte -- very short int */ + char *p = va_arg(*p_va, char *); + long ival; + if (float_argument_error(arg)) + return converterr("integer", arg, msgbuf, bufsize); + ival = PyInt_AsLong(arg); + if (ival == -1 && PyErr_Occurred()) + return converterr("integer", arg, msgbuf, bufsize); + else if (ival < 0) { + PyErr_SetString(PyExc_OverflowError, + "unsigned byte integer is less than minimum"); + return converterr("integer", arg, msgbuf, bufsize); + } + else if (ival > UCHAR_MAX) { + PyErr_SetString(PyExc_OverflowError, + "unsigned byte integer is greater than maximum"); + return converterr("integer", arg, msgbuf, bufsize); + } + else + *p = (unsigned char) ival; + break; + } + + case 'B': {/* byte sized bitfield - both signed and unsigned + values allowed */ + char *p = va_arg(*p_va, char *); + long ival; + if (float_argument_error(arg)) + return converterr("integer", arg, msgbuf, bufsize); + ival = PyInt_AsUnsignedLongMask(arg); + if (ival == -1 && PyErr_Occurred()) + return converterr("integer", arg, msgbuf, bufsize); + else + *p = (unsigned char) ival; + break; + } + + case 'h': {/* signed short int */ + short *p = va_arg(*p_va, short *); + long ival; + if (float_argument_error(arg)) + return converterr("integer", arg, msgbuf, bufsize); + ival = PyInt_AsLong(arg); + if (ival == -1 && PyErr_Occurred()) + return converterr("integer", arg, msgbuf, bufsize); + else if (ival < SHRT_MIN) { + PyErr_SetString(PyExc_OverflowError, + "signed short integer is less than minimum"); + return converterr("integer", arg, msgbuf, bufsize); + } + else if (ival > SHRT_MAX) { + PyErr_SetString(PyExc_OverflowError, + "signed short integer is greater than maximum"); + return converterr("integer", arg, msgbuf, bufsize); + } + else + *p = (short) ival; + break; + } + + case 'H': { /* short int sized bitfield, both signed and + unsigned allowed */ + unsigned short *p = va_arg(*p_va, unsigned short *); + long ival; + if (float_argument_error(arg)) + return converterr("integer", arg, msgbuf, bufsize); + ival = PyInt_AsUnsignedLongMask(arg); + if (ival == -1 && PyErr_Occurred()) + return converterr("integer", arg, msgbuf, bufsize); + else + *p = (unsigned short) ival; + break; + } + + case 'i': {/* signed int */ + int *p = va_arg(*p_va, int *); + long ival; + if (float_argument_error(arg)) + return converterr("integer", arg, msgbuf, bufsize); + ival = PyInt_AsLong(arg); + if (ival == -1 && PyErr_Occurred()) + return converterr("integer", arg, msgbuf, bufsize); + else if (ival > INT_MAX) { + PyErr_SetString(PyExc_OverflowError, + "signed integer is greater than maximum"); + return converterr("integer", arg, msgbuf, bufsize); + } + else if (ival < INT_MIN) { + PyErr_SetString(PyExc_OverflowError, + "signed integer is less than minimum"); + return converterr("integer", arg, msgbuf, bufsize); + } + else + *p = ival; + break; + } + + case 'I': { /* int sized bitfield, both signed and + unsigned allowed */ + unsigned int *p = va_arg(*p_va, unsigned int *); + unsigned int ival; + if (float_argument_error(arg)) + return converterr("integer", arg, msgbuf, bufsize); + ival = (unsigned int)PyInt_AsUnsignedLongMask(arg); + if (ival == (unsigned int)-1 && PyErr_Occurred()) + return converterr("integer", arg, msgbuf, bufsize); + else + *p = ival; + break; + } + + case 'n': /* Py_ssize_t */ +#if SIZEOF_SIZE_T != SIZEOF_LONG + { + Py_ssize_t *p = va_arg(*p_va, Py_ssize_t *); + Py_ssize_t ival; + if (float_argument_error(arg)) + return converterr("integer", arg, msgbuf, bufsize); + ival = PyInt_AsSsize_t(arg); + if (ival == -1 && PyErr_Occurred()) + return converterr("integer", arg, msgbuf, bufsize); + *p = ival; + break; + } +#endif + /* Fall through from 'n' to 'l' if Py_ssize_t is int */ + case 'l': {/* long int */ + long *p = va_arg(*p_va, long *); + long ival; + if (float_argument_error(arg)) + return converterr("integer", arg, msgbuf, bufsize); + ival = PyInt_AsLong(arg); + if (ival == -1 && PyErr_Occurred()) + return converterr("integer", arg, msgbuf, bufsize); + else + *p = ival; + break; + } + + case 'k': { /* long sized bitfield */ + unsigned long *p = va_arg(*p_va, unsigned long *); + unsigned long ival; + if (PyInt_Check(arg)) + ival = PyInt_AsUnsignedLongMask(arg); + else if (PyLong_Check(arg)) + ival = PyLong_AsUnsignedLongMask(arg); + else + return converterr("integer", arg, msgbuf, bufsize); + *p = ival; + break; + } + +#ifdef HAVE_LONG_LONG + case 'L': {/* PY_LONG_LONG */ + PY_LONG_LONG *p = va_arg( *p_va, PY_LONG_LONG * ); + PY_LONG_LONG ival; + if (float_argument_warning(arg)) + return converterr("long", arg, msgbuf, bufsize); + ival = PyLong_AsLongLong(arg); + if (ival == (PY_LONG_LONG)-1 && PyErr_Occurred() ) { + return converterr("long", arg, msgbuf, bufsize); + } else { + *p = ival; + } + break; + } + + case 'K': { /* long long sized bitfield */ + unsigned PY_LONG_LONG *p = va_arg(*p_va, unsigned PY_LONG_LONG *); + unsigned PY_LONG_LONG ival; + if (PyInt_Check(arg)) + ival = PyInt_AsUnsignedLongMask(arg); + else if (PyLong_Check(arg)) + ival = PyLong_AsUnsignedLongLongMask(arg); + else + return converterr("integer", arg, msgbuf, bufsize); + *p = ival; + break; + } +#endif + + case 'f': {/* float */ + float *p = va_arg(*p_va, float *); + double dval = PyFloat_AsDouble(arg); + if (PyErr_Occurred()) + return converterr("float", arg, msgbuf, bufsize); + else + *p = (float) dval; + break; + } + + case 'd': {/* double */ + double *p = va_arg(*p_va, double *); + double dval = PyFloat_AsDouble(arg); + if (PyErr_Occurred()) + return converterr("float", arg, msgbuf, bufsize); + else + *p = dval; + break; + } + +#ifndef WITHOUT_COMPLEX + case 'D': {/* complex double */ + Py_complex *p = va_arg(*p_va, Py_complex *); + Py_complex cval; + cval = PyComplex_AsCComplex(arg); + if (PyErr_Occurred()) + return converterr("complex", arg, msgbuf, bufsize); + else + *p = cval; + break; + } +#endif /* WITHOUT_COMPLEX */ + + case 'c': {/* char */ + char *p = va_arg(*p_va, char *); + if (PyString_Check(arg) && PyString_Size(arg) == 1) + *p = PyString_AS_STRING(arg)[0]; + else + return converterr("char", arg, msgbuf, bufsize); + break; + } + + case 's': {/* string */ + if (*format == '*') { + Py_buffer *p = (Py_buffer *)va_arg(*p_va, Py_buffer *); + + if (PyString_Check(arg)) { + PyBuffer_FillInfo(p, arg, + PyString_AS_STRING(arg), PyString_GET_SIZE(arg), + 1, 0); + } +#ifdef Py_USING_UNICODE + else if (PyUnicode_Check(arg)) { + uarg = UNICODE_DEFAULT_ENCODING(arg); + if (uarg == NULL) + return converterr(CONV_UNICODE, + arg, msgbuf, bufsize); + PyBuffer_FillInfo(p, arg, + PyString_AS_STRING(uarg), PyString_GET_SIZE(uarg), + 1, 0); + } +#endif + else { /* any buffer-like object */ + char *buf; + if (getbuffer(arg, p, &buf) < 0) + return converterr(buf, arg, msgbuf, bufsize); + } + if (addcleanup(p, freelist, cleanup_buffer)) { + return converterr( + "(cleanup problem)", + arg, msgbuf, bufsize); + } + format++; + } else if (*format == '#') { + void **p = (void **)va_arg(*p_va, char **); + FETCH_SIZE; + + if (PyString_Check(arg)) { + *p = PyString_AS_STRING(arg); + STORE_SIZE(PyString_GET_SIZE(arg)); + } +#ifdef Py_USING_UNICODE + else if (PyUnicode_Check(arg)) { + uarg = UNICODE_DEFAULT_ENCODING(arg); + if (uarg == NULL) + return converterr(CONV_UNICODE, + arg, msgbuf, bufsize); + *p = PyString_AS_STRING(uarg); + STORE_SIZE(PyString_GET_SIZE(uarg)); + } +#endif + else { /* any buffer-like object */ + char *buf; + Py_ssize_t count = convertbuffer(arg, p, &buf); + if (count < 0) + return converterr(buf, arg, msgbuf, bufsize); + STORE_SIZE(count); + } + format++; + } else { + char **p = va_arg(*p_va, char **); + + if (PyString_Check(arg)) + *p = PyString_AS_STRING(arg); +#ifdef Py_USING_UNICODE + else if (PyUnicode_Check(arg)) { + uarg = UNICODE_DEFAULT_ENCODING(arg); + if (uarg == NULL) + return converterr(CONV_UNICODE, + arg, msgbuf, bufsize); + *p = PyString_AS_STRING(uarg); + } +#endif + else + return converterr("string", arg, msgbuf, bufsize); + if ((Py_ssize_t)strlen(*p) != PyString_Size(arg)) + return converterr("string without null bytes", + arg, msgbuf, bufsize); + } + break; + } + + case 'z': {/* string, may be NULL (None) */ + if (*format == '*') { + Py_buffer *p = (Py_buffer *)va_arg(*p_va, Py_buffer *); + + if (arg == Py_None) + PyBuffer_FillInfo(p, NULL, NULL, 0, 1, 0); + else if (PyString_Check(arg)) { + PyBuffer_FillInfo(p, arg, + PyString_AS_STRING(arg), PyString_GET_SIZE(arg), + 1, 0); + } +#ifdef Py_USING_UNICODE + else if (PyUnicode_Check(arg)) { + uarg = UNICODE_DEFAULT_ENCODING(arg); + if (uarg == NULL) + return converterr(CONV_UNICODE, + arg, msgbuf, bufsize); + PyBuffer_FillInfo(p, arg, + PyString_AS_STRING(uarg), PyString_GET_SIZE(uarg), + 1, 0); + } +#endif + else { /* any buffer-like object */ + char *buf; + if (getbuffer(arg, p, &buf) < 0) + return converterr(buf, arg, msgbuf, bufsize); + } + if (addcleanup(p, freelist, cleanup_buffer)) { + return converterr( + "(cleanup problem)", + arg, msgbuf, bufsize); + } + format++; + } else if (*format == '#') { /* any buffer-like object */ + void **p = (void **)va_arg(*p_va, char **); + FETCH_SIZE; + + if (arg == Py_None) { + *p = 0; + STORE_SIZE(0); + } + else if (PyString_Check(arg)) { + *p = PyString_AS_STRING(arg); + STORE_SIZE(PyString_GET_SIZE(arg)); + } +#ifdef Py_USING_UNICODE + else if (PyUnicode_Check(arg)) { + uarg = UNICODE_DEFAULT_ENCODING(arg); + if (uarg == NULL) + return converterr(CONV_UNICODE, + arg, msgbuf, bufsize); + *p = PyString_AS_STRING(uarg); + STORE_SIZE(PyString_GET_SIZE(uarg)); + } +#endif + else { /* any buffer-like object */ + char *buf; + Py_ssize_t count = convertbuffer(arg, p, &buf); + if (count < 0) + return converterr(buf, arg, msgbuf, bufsize); + STORE_SIZE(count); + } + format++; + } else { + char **p = va_arg(*p_va, char **); + + if (arg == Py_None) + *p = 0; + else if (PyString_Check(arg)) + *p = PyString_AS_STRING(arg); +#ifdef Py_USING_UNICODE + else if (PyUnicode_Check(arg)) { + uarg = UNICODE_DEFAULT_ENCODING(arg); + if (uarg == NULL) + return converterr(CONV_UNICODE, + arg, msgbuf, bufsize); + *p = PyString_AS_STRING(uarg); + } +#endif + else + return converterr("string or None", + arg, msgbuf, bufsize); + if (*format == '#') { + FETCH_SIZE; + assert(0); /* XXX redundant with if-case */ + if (arg == Py_None) { + STORE_SIZE(0); + } else { + STORE_SIZE(PyString_Size(arg)); + } + format++; + } + else if (*p != NULL && + (Py_ssize_t)strlen(*p) != PyString_Size(arg)) + return converterr( + "string without null bytes or None", + arg, msgbuf, bufsize); + } + break; + } + + case 'e': {/* encoded string */ + char **buffer; + const char *encoding; + PyObject *s; + Py_ssize_t size; + int recode_strings; + + /* Get 'e' parameter: the encoding name */ + encoding = (const char *)va_arg(*p_va, const char *); +#ifdef Py_USING_UNICODE + if (encoding == NULL) + encoding = PyUnicode_GetDefaultEncoding(); +#endif + + /* Get output buffer parameter: + 's' (recode all objects via Unicode) or + 't' (only recode non-string objects) + */ + if (*format == 's') + recode_strings = 1; + else if (*format == 't') + recode_strings = 0; + else + return converterr( + "(unknown parser marker combination)", + arg, msgbuf, bufsize); + buffer = (char **)va_arg(*p_va, char **); + format++; + if (buffer == NULL) + return converterr("(buffer is NULL)", + arg, msgbuf, bufsize); + + /* Encode object */ + if (!recode_strings && PyString_Check(arg)) { + s = arg; + Py_INCREF(s); + } + else { +#ifdef Py_USING_UNICODE + PyObject *u; + + /* Convert object to Unicode */ + u = PyUnicode_FromObject(arg); + if (u == NULL) + return converterr( + "string or unicode or text buffer", + arg, msgbuf, bufsize); + + /* Encode object; use default error handling */ + s = PyUnicode_AsEncodedString(u, + encoding, + NULL); + Py_DECREF(u); + if (s == NULL) + return converterr("(encoding failed)", + arg, msgbuf, bufsize); + if (!PyString_Check(s)) { + Py_DECREF(s); + return converterr( + "(encoder failed to return a string)", + arg, msgbuf, bufsize); + } +#else + return converterr("string", arg, msgbuf, bufsize); +#endif + } + size = PyString_GET_SIZE(s); + + /* Write output; output is guaranteed to be 0-terminated */ + if (*format == '#') { + /* Using buffer length parameter '#': + + - if *buffer is NULL, a new buffer of the + needed size is allocated and the data + copied into it; *buffer is updated to point + to the new buffer; the caller is + responsible for PyMem_Free()ing it after + usage + + - if *buffer is not NULL, the data is + copied to *buffer; *buffer_len has to be + set to the size of the buffer on input; + buffer overflow is signalled with an error; + buffer has to provide enough room for the + encoded string plus the trailing 0-byte + + - in both cases, *buffer_len is updated to + the size of the buffer /excluding/ the + trailing 0-byte + + */ + FETCH_SIZE; + + format++; + if (q == NULL && q2 == NULL) { + Py_DECREF(s); + return converterr( + "(buffer_len is NULL)", + arg, msgbuf, bufsize); + } + if (*buffer == NULL) { + *buffer = PyMem_NEW(char, size + 1); + if (*buffer == NULL) { + Py_DECREF(s); + return converterr( + "(memory error)", + arg, msgbuf, bufsize); + } + if (addcleanup(*buffer, freelist, cleanup_ptr)) { + Py_DECREF(s); + return converterr( + "(cleanup problem)", + arg, msgbuf, bufsize); + } + } else { + if (size + 1 > BUFFER_LEN) { + Py_DECREF(s); + return converterr( + "(buffer overflow)", + arg, msgbuf, bufsize); + } + } + memcpy(*buffer, + PyString_AS_STRING(s), + size + 1); + STORE_SIZE(size); + } else { + /* Using a 0-terminated buffer: + + - the encoded string has to be 0-terminated + for this variant to work; if it is not, an + error raised + + - a new buffer of the needed size is + allocated and the data copied into it; + *buffer is updated to point to the new + buffer; the caller is responsible for + PyMem_Free()ing it after usage + + */ + if ((Py_ssize_t)strlen(PyString_AS_STRING(s)) + != size) { + Py_DECREF(s); + return converterr( + "encoded string without NULL bytes", + arg, msgbuf, bufsize); + } + *buffer = PyMem_NEW(char, size + 1); + if (*buffer == NULL) { + Py_DECREF(s); + return converterr("(memory error)", + arg, msgbuf, bufsize); + } + if (addcleanup(*buffer, freelist, cleanup_ptr)) { + Py_DECREF(s); + return converterr("(cleanup problem)", + arg, msgbuf, bufsize); + } + memcpy(*buffer, + PyString_AS_STRING(s), + size + 1); + } + Py_DECREF(s); + break; + } + +#ifdef Py_USING_UNICODE + case 'u': {/* raw unicode buffer (Py_UNICODE *) */ + if (*format == '#') { /* any buffer-like object */ + void **p = (void **)va_arg(*p_va, char **); + FETCH_SIZE; + if (PyUnicode_Check(arg)) { + *p = PyUnicode_AS_UNICODE(arg); + STORE_SIZE(PyUnicode_GET_SIZE(arg)); + } + else { + return converterr("cannot convert raw buffers", + arg, msgbuf, bufsize); + } + format++; + } else { + Py_UNICODE **p = va_arg(*p_va, Py_UNICODE **); + if (PyUnicode_Check(arg)) + *p = PyUnicode_AS_UNICODE(arg); + else + return converterr("unicode", arg, msgbuf, bufsize); + } + break; + } +#endif + + case 'S': { /* string object */ + PyObject **p = va_arg(*p_va, PyObject **); + if (PyString_Check(arg)) + *p = arg; + else + return converterr("string", arg, msgbuf, bufsize); + break; + } + +#ifdef Py_USING_UNICODE + case 'U': { /* Unicode object */ + PyObject **p = va_arg(*p_va, PyObject **); + if (PyUnicode_Check(arg)) + *p = arg; + else + return converterr("unicode", arg, msgbuf, bufsize); + break; + } +#endif + + case 'O': { /* object */ + PyTypeObject *type; + PyObject **p; + if (*format == '!') { + type = va_arg(*p_va, PyTypeObject*); + p = va_arg(*p_va, PyObject **); + format++; + if (PyType_IsSubtype(arg->ob_type, type)) + *p = arg; + else + return converterr(type->tp_name, arg, msgbuf, bufsize); + + } + else if (*format == '?') { + inquiry pred = va_arg(*p_va, inquiry); + p = va_arg(*p_va, PyObject **); + format++; + if ((*pred)(arg)) + *p = arg; + else + return converterr("(unspecified)", + arg, msgbuf, bufsize); + + } + else if (*format == '&') { + typedef int (*converter)(PyObject *, void *); + converter convert = va_arg(*p_va, converter); + void *addr = va_arg(*p_va, void *); + format++; + if (! (*convert)(arg, addr)) + return converterr("(unspecified)", + arg, msgbuf, bufsize); + } + else { + p = va_arg(*p_va, PyObject **); + *p = arg; + } + break; + } + + + case 'w': { /* memory buffer, read-write access */ + void **p = va_arg(*p_va, void **); + void *res; + PyBufferProcs *pb = arg->ob_type->tp_as_buffer; + Py_ssize_t count; + + if (pb && pb->bf_releasebuffer && *format != '*') + /* Buffer must be released, yet caller does not use + the Py_buffer protocol. */ + return converterr("pinned buffer", arg, msgbuf, bufsize); + + if (pb && pb->bf_getbuffer && *format == '*') { + /* Caller is interested in Py_buffer, and the object + supports it directly. */ + format++; + if (pb->bf_getbuffer(arg, (Py_buffer*)p, PyBUF_WRITABLE) < 0) { + PyErr_Clear(); + return converterr("read-write buffer", arg, msgbuf, bufsize); + } + if (addcleanup(p, freelist, cleanup_buffer)) { + return converterr( + "(cleanup problem)", + arg, msgbuf, bufsize); + } + if (!PyBuffer_IsContiguous((Py_buffer*)p, 'C')) + return converterr("contiguous buffer", arg, msgbuf, bufsize); + break; + } + + if (pb == NULL || + pb->bf_getwritebuffer == NULL || + pb->bf_getsegcount == NULL) + return converterr("read-write buffer", arg, msgbuf, bufsize); + if ((*pb->bf_getsegcount)(arg, NULL) != 1) + return converterr("single-segment read-write buffer", + arg, msgbuf, bufsize); + if ((count = pb->bf_getwritebuffer(arg, 0, &res)) < 0) + return converterr("(unspecified)", arg, msgbuf, bufsize); + if (*format == '*') { + PyBuffer_FillInfo((Py_buffer*)p, arg, res, count, 1, 0); + format++; + } + else { + *p = res; + if (*format == '#') { + FETCH_SIZE; + STORE_SIZE(count); + format++; + } + } + break; + } + + case 't': { /* 8-bit character buffer, read-only access */ + char **p = va_arg(*p_va, char **); + PyBufferProcs *pb = arg->ob_type->tp_as_buffer; + Py_ssize_t count; + + if (*format++ != '#') + return converterr( + "invalid use of 't' format character", + arg, msgbuf, bufsize); + if (!PyType_HasFeature(arg->ob_type, + Py_TPFLAGS_HAVE_GETCHARBUFFER) || + pb == NULL || pb->bf_getcharbuffer == NULL || + pb->bf_getsegcount == NULL) + return converterr( + "string or read-only character buffer", + arg, msgbuf, bufsize); + + if (pb->bf_getsegcount(arg, NULL) != 1) + return converterr( + "string or single-segment read-only buffer", + arg, msgbuf, bufsize); + + if (pb->bf_releasebuffer) + return converterr( + "string or pinned buffer", + arg, msgbuf, bufsize); + + count = pb->bf_getcharbuffer(arg, 0, p); + if (count < 0) + return converterr("(unspecified)", arg, msgbuf, bufsize); + { + FETCH_SIZE; + STORE_SIZE(count); + } + break; + } + + default: + return converterr("impossible", arg, msgbuf, bufsize); + + } + + *p_format = format; + return NULL; +} + +static Py_ssize_t +convertbuffer(PyObject *arg, void **p, char **errmsg) +{ + PyBufferProcs *pb = arg->ob_type->tp_as_buffer; + Py_ssize_t count; + if (pb == NULL || + pb->bf_getreadbuffer == NULL || + pb->bf_getsegcount == NULL || + pb->bf_releasebuffer != NULL) { + *errmsg = "string or read-only buffer"; + return -1; + } + if ((*pb->bf_getsegcount)(arg, NULL) != 1) { + *errmsg = "string or single-segment read-only buffer"; + return -1; + } + if ((count = (*pb->bf_getreadbuffer)(arg, 0, p)) < 0) { + *errmsg = "(unspecified)"; + } + return count; +} + +static int +getbuffer(PyObject *arg, Py_buffer *view, char **errmsg) +{ + void *buf; + Py_ssize_t count; + PyBufferProcs *pb = arg->ob_type->tp_as_buffer; + if (pb == NULL) { + *errmsg = "string or buffer"; + return -1; + } + if (pb->bf_getbuffer) { + if (pb->bf_getbuffer(arg, view, 0) < 0) { + *errmsg = "convertible to a buffer"; + return -1; + } + if (!PyBuffer_IsContiguous(view, 'C')) { + *errmsg = "contiguous buffer"; + return -1; + } + return 0; + } + + count = convertbuffer(arg, &buf, errmsg); + if (count < 0) { + *errmsg = "convertible to a buffer"; + return count; + } + PyBuffer_FillInfo(view, arg, buf, count, 1, 0); + return 0; +} + +/* Support for keyword arguments donated by + Geoff Philbrick */ + +/* Return false (0) for error, else true. */ +int +PyArg_ParseTupleAndKeywords(PyObject *args, + PyObject *keywords, + const char *format, + char **kwlist, ...) +{ + int retval; + va_list va; + + if ((args == NULL || !PyTuple_Check(args)) || + (keywords != NULL && !PyDict_Check(keywords)) || + format == NULL || + kwlist == NULL) + { + PyErr_BadInternalCall(); + return 0; + } + + va_start(va, kwlist); + retval = vgetargskeywords(args, keywords, format, kwlist, &va, 0); + va_end(va); + return retval; +} + +int +_PyArg_ParseTupleAndKeywords_SizeT(PyObject *args, + PyObject *keywords, + const char *format, + char **kwlist, ...) +{ + int retval; + va_list va; + + if ((args == NULL || !PyTuple_Check(args)) || + (keywords != NULL && !PyDict_Check(keywords)) || + format == NULL || + kwlist == NULL) + { + PyErr_BadInternalCall(); + return 0; + } + + va_start(va, kwlist); + retval = vgetargskeywords(args, keywords, format, + kwlist, &va, FLAG_SIZE_T); + va_end(va); + return retval; +} + + +int +PyArg_VaParseTupleAndKeywords(PyObject *args, + PyObject *keywords, + const char *format, + char **kwlist, va_list va) +{ + int retval; + va_list lva; + + if ((args == NULL || !PyTuple_Check(args)) || + (keywords != NULL && !PyDict_Check(keywords)) || + format == NULL || + kwlist == NULL) + { + PyErr_BadInternalCall(); + return 0; + } + +#ifdef VA_LIST_IS_ARRAY + memcpy(lva, va, sizeof(va_list)); +#else +#ifdef __va_copy + __va_copy(lva, va); +#else + lva = va; +#endif +#endif + + retval = vgetargskeywords(args, keywords, format, kwlist, &lva, 0); + return retval; +} + +int +_PyArg_VaParseTupleAndKeywords_SizeT(PyObject *args, + PyObject *keywords, + const char *format, + char **kwlist, va_list va) +{ + int retval; + va_list lva; + + if ((args == NULL || !PyTuple_Check(args)) || + (keywords != NULL && !PyDict_Check(keywords)) || + format == NULL || + kwlist == NULL) + { + PyErr_BadInternalCall(); + return 0; + } + +#ifdef VA_LIST_IS_ARRAY + memcpy(lva, va, sizeof(va_list)); +#else +#ifdef __va_copy + __va_copy(lva, va); +#else + lva = va; +#endif +#endif + + retval = vgetargskeywords(args, keywords, format, + kwlist, &lva, FLAG_SIZE_T); + return retval; +} + +#define IS_END_OF_FORMAT(c) (c == '\0' || c == ';' || c == ':') + +static int +vgetargskeywords(PyObject *args, PyObject *keywords, const char *format, + char **kwlist, va_list *p_va, int flags) +{ + char msgbuf[512]; + int levels[32]; + const char *fname, *msg, *custom_msg, *keyword; + int min = INT_MAX; + int i, len, nargs, nkeywords; + PyObject *freelist = NULL, *current_arg; + + assert(args != NULL && PyTuple_Check(args)); + assert(keywords == NULL || PyDict_Check(keywords)); + assert(format != NULL); + assert(kwlist != NULL); + assert(p_va != NULL); + + /* grab the function name or custom error msg first (mutually exclusive) */ + fname = strchr(format, ':'); + if (fname) { + fname++; + custom_msg = NULL; + } + else { + custom_msg = strchr(format,';'); + if (custom_msg) + custom_msg++; + } + + /* scan kwlist and get greatest possible nbr of args */ + for (len=0; kwlist[len]; len++) + continue; + + nargs = PyTuple_GET_SIZE(args); + nkeywords = (keywords == NULL) ? 0 : PyDict_Size(keywords); + if (nargs + nkeywords > len) { + PyErr_Format(PyExc_TypeError, "%s%s takes at most %d " + "argument%s (%d given)", + (fname == NULL) ? "function" : fname, + (fname == NULL) ? "" : "()", + len, + (len == 1) ? "" : "s", + nargs + nkeywords); + return 0; + } + + /* convert tuple args and keyword args in same loop, using kwlist to drive process */ + for (i = 0; i < len; i++) { + keyword = kwlist[i]; + if (*format == '|') { + min = i; + format++; + } + if (IS_END_OF_FORMAT(*format)) { + PyErr_Format(PyExc_RuntimeError, + "More keyword list entries (%d) than " + "format specifiers (%d)", len, i); + return cleanreturn(0, freelist); + } + current_arg = NULL; + if (nkeywords) { + current_arg = PyDict_GetItemString(keywords, keyword); + } + if (current_arg) { + --nkeywords; + if (i < nargs) { + /* arg present in tuple and in dict */ + PyErr_Format(PyExc_TypeError, + "Argument given by name ('%s') " + "and position (%d)", + keyword, i+1); + return cleanreturn(0, freelist); + } + } + else if (nkeywords && PyErr_Occurred()) + return cleanreturn(0, freelist); + else if (i < nargs) + current_arg = PyTuple_GET_ITEM(args, i); + + if (current_arg) { + msg = convertitem(current_arg, &format, p_va, flags, + levels, msgbuf, sizeof(msgbuf), &freelist); + if (msg) { + seterror(i+1, msg, levels, fname, custom_msg); + return cleanreturn(0, freelist); + } + continue; + } + + if (i < min) { + PyErr_Format(PyExc_TypeError, "Required argument " + "'%s' (pos %d) not found", + keyword, i+1); + return cleanreturn(0, freelist); + } + /* current code reports success when all required args + * fulfilled and no keyword args left, with no further + * validation. XXX Maybe skip this in debug build ? + */ + if (!nkeywords) + return cleanreturn(1, freelist); + + /* We are into optional args, skip thru to any remaining + * keyword args */ + msg = skipitem(&format, p_va, flags); + if (msg) { + PyErr_Format(PyExc_RuntimeError, "%s: '%s'", msg, + format); + return cleanreturn(0, freelist); + } + } + + if (!IS_END_OF_FORMAT(*format) && *format != '|') { + PyErr_Format(PyExc_RuntimeError, + "more argument specifiers than keyword list entries " + "(remaining format:'%s')", format); + return cleanreturn(0, freelist); + } + + /* make sure there are no extraneous keyword arguments */ + if (nkeywords > 0) { + PyObject *key, *value; + Py_ssize_t pos = 0; + while (PyDict_Next(keywords, &pos, &key, &value)) { + int match = 0; + char *ks; + if (!PyString_Check(key)) { + PyErr_SetString(PyExc_TypeError, + "keywords must be strings"); + return cleanreturn(0, freelist); + } + ks = PyString_AsString(key); + for (i = 0; i < len; i++) { + if (!strcmp(ks, kwlist[i])) { + match = 1; + break; + } + } + if (!match) { + PyErr_Format(PyExc_TypeError, + "'%s' is an invalid keyword " + "argument for this function", + ks); + return cleanreturn(0, freelist); + } + } + } + + return cleanreturn(1, freelist); +} + + +static char * +skipitem(const char **p_format, va_list *p_va, int flags) +{ + const char *format = *p_format; + char c = *format++; + + switch (c) { + + /* simple codes + * The individual types (second arg of va_arg) are irrelevant */ + + case 'b': /* byte -- very short int */ + case 'B': /* byte as bitfield */ + case 'h': /* short int */ + case 'H': /* short int as bitfield */ + case 'i': /* int */ + case 'I': /* int sized bitfield */ + case 'l': /* long int */ + case 'k': /* long int sized bitfield */ +#ifdef HAVE_LONG_LONG + case 'L': /* PY_LONG_LONG */ + case 'K': /* PY_LONG_LONG sized bitfield */ +#endif + case 'f': /* float */ + case 'd': /* double */ +#ifndef WITHOUT_COMPLEX + case 'D': /* complex double */ +#endif + case 'c': /* char */ + { + (void) va_arg(*p_va, void *); + break; + } + + case 'n': /* Py_ssize_t */ + { + (void) va_arg(*p_va, Py_ssize_t *); + break; + } + + /* string codes */ + + case 'e': /* string with encoding */ + { + (void) va_arg(*p_va, const char *); + if (!(*format == 's' || *format == 't')) + /* after 'e', only 's' and 't' is allowed */ + goto err; + format++; + /* explicit fallthrough to string cases */ + } + + case 's': /* string */ + case 'z': /* string or None */ +#ifdef Py_USING_UNICODE + case 'u': /* unicode string */ +#endif + case 't': /* buffer, read-only */ + case 'w': /* buffer, read-write */ + { + (void) va_arg(*p_va, char **); + if (*format == '#') { + if (flags & FLAG_SIZE_T) + (void) va_arg(*p_va, Py_ssize_t *); + else + (void) va_arg(*p_va, int *); + format++; + } else if ((c == 's' || c == 'z') && *format == '*') { + format++; + } + break; + } + + /* object codes */ + + case 'S': /* string object */ +#ifdef Py_USING_UNICODE + case 'U': /* unicode string object */ +#endif + { + (void) va_arg(*p_va, PyObject **); + break; + } + + case 'O': /* object */ + { + if (*format == '!') { + format++; + (void) va_arg(*p_va, PyTypeObject*); + (void) va_arg(*p_va, PyObject **); + } + else if (*format == '&') { + typedef int (*converter)(PyObject *, void *); + (void) va_arg(*p_va, converter); + (void) va_arg(*p_va, void *); + format++; + } + else { + (void) va_arg(*p_va, PyObject **); + } + break; + } + + case '(': /* bypass tuple, not handled at all previously */ + { + char *msg; + for (;;) { + if (*format==')') + break; + if (IS_END_OF_FORMAT(*format)) + return "Unmatched left paren in format " + "string"; + msg = skipitem(&format, p_va, flags); + if (msg) + return msg; + } + format++; + break; + } + + case ')': + return "Unmatched right paren in format string"; + + default: +err: + return "impossible"; + + } + + *p_format = format; + return NULL; +} + + +int +PyArg_UnpackTuple(PyObject *args, const char *name, Py_ssize_t min, Py_ssize_t max, ...) +{ + Py_ssize_t i, l; + PyObject **o; + va_list vargs; + +#ifdef HAVE_STDARG_PROTOTYPES + va_start(vargs, max); +#else + va_start(vargs); +#endif + + assert(min >= 0); + assert(min <= max); + if (!PyTuple_Check(args)) { + va_end(vargs); + PyErr_SetString(PyExc_SystemError, + "PyArg_UnpackTuple() argument list is not a tuple"); + return 0; + } + l = PyTuple_GET_SIZE(args); + if (l < min) { + if (name != NULL) + PyErr_Format( + PyExc_TypeError, + "%s expected %s%zd arguments, got %zd", + name, (min == max ? "" : "at least "), min, l); + else + PyErr_Format( + PyExc_TypeError, + "unpacked tuple should have %s%zd elements," + " but has %zd", + (min == max ? "" : "at least "), min, l); + va_end(vargs); + return 0; + } + if (l > max) { + if (name != NULL) + PyErr_Format( + PyExc_TypeError, + "%s expected %s%zd arguments, got %zd", + name, (min == max ? "" : "at most "), max, l); + else + PyErr_Format( + PyExc_TypeError, + "unpacked tuple should have %s%zd elements," + " but has %zd", + (min == max ? "" : "at most "), max, l); + va_end(vargs); + return 0; + } + for (i = 0; i < l; i++) { + o = va_arg(vargs, PyObject **); + *o = PyTuple_GET_ITEM(args, i); + } + va_end(vargs); + return 1; +} + + +/* For type constructors that don't take keyword args + * + * Sets a TypeError and returns 0 if the kwds dict is + * not empty, returns 1 otherwise + */ +int +_PyArg_NoKeywords(const char *funcname, PyObject *kw) +{ + if (kw == NULL) + return 1; + if (!PyDict_CheckExact(kw)) { + PyErr_BadInternalCall(); + return 0; + } + if (PyDict_Size(kw) == 0) + return 1; + + PyErr_Format(PyExc_TypeError, "%s does not take keyword arguments", + funcname); + return 0; +} +#ifdef __cplusplus +}; +#endif diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/getcompiler.c b/AppPkg/Applications/Python/Python-2.7.10/Python/getcompiler.c new file mode 100644 index 0000000000..33a7639aa9 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/getcompiler.c @@ -0,0 +1,28 @@ + +/* Return the compiler identification, if possible. */ + +#include "Python.h" + +#ifndef COMPILER + +#ifdef __GNUC__ +#define COMPILER "\n[GCC " __VERSION__ "]" +#endif + +#endif /* !COMPILER */ + +#ifndef COMPILER + +#ifdef __cplusplus +#define COMPILER "[C++]" +#else +#define COMPILER "[C]" +#endif + +#endif /* !COMPILER */ + +const char * +Py_GetCompiler(void) +{ + return COMPILER; +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/getopt.c b/AppPkg/Applications/Python/Python-2.7.10/Python/getopt.c new file mode 100644 index 0000000000..af6f5dc825 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/getopt.c @@ -0,0 +1,136 @@ +/*---------------------------------------------------------------------------* + * + * + * C++ Library + * + * Copyright 1992-1994, David Gottner + * + * All Rights Reserved + * + * Permission to use, copy, modify, and distribute this software and its + * documentation for any purpose and without fee is hereby granted, + * provided that the above copyright notice, this permission notice and + * the following disclaimer notice appear unmodified in all copies. + * + * I DISCLAIM ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING ALL + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL I + * BE LIABLE FOR ANY SPECIAL, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY + * DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA, OR PROFITS, WHETHER + * IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT + * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + * Nevertheless, I would like to know about bugs in this library or + * suggestions for improvment. Send bug reports and feedback to + * davegottner@delphi.com. + *---------------------------------------------------------------------------*/ + +/* Modified to support --help and --version, as well as /? on Windows + * by Georg Brandl. */ + +#include +#include + +#ifdef __cplusplus +extern "C" { +#endif + +int _PyOS_opterr = 1; /* generate error messages */ +int _PyOS_optind = 1; /* index into argv array */ +char *_PyOS_optarg = NULL; /* optional argument */ +static char *opt_ptr = ""; + +void _PyOS_ResetGetOpt(void) +{ + _PyOS_opterr = 1; + _PyOS_optind = 1; + _PyOS_optarg = NULL; + opt_ptr = ""; +} + +int _PyOS_GetOpt(int argc, char **argv, char *optstring) +{ + char *ptr; + int option; + + if (*opt_ptr == '\0') { + + if (_PyOS_optind >= argc) + return -1; +#ifdef MS_WINDOWS + else if (strcmp(argv[_PyOS_optind], "/?") == 0) { + ++_PyOS_optind; + return 'h'; + } +#endif + + else if (argv[_PyOS_optind][0] != '-' || + argv[_PyOS_optind][1] == '\0' /* lone dash */ ) + return -1; + + else if (strcmp(argv[_PyOS_optind], "--") == 0) { + ++_PyOS_optind; + return -1; + } + + else if (strcmp(argv[_PyOS_optind], "--help") == 0) { + ++_PyOS_optind; + return 'h'; + } + + else if (strcmp(argv[_PyOS_optind], "--version") == 0) { + ++_PyOS_optind; + return 'V'; + } + + + opt_ptr = &argv[_PyOS_optind++][1]; + } + + if ((option = *opt_ptr++) == '\0') + return -1; + + if (option == 'J') { + if (_PyOS_opterr) + fprintf(stderr, "-J is reserved for Jython\n"); + return '_'; + } + + if (option == 'X') { + if (_PyOS_opterr) + fprintf(stderr, + "-X is reserved for implementation-specific arguments\n"); + return '_'; + } + + if ((ptr = strchr(optstring, option)) == NULL) { + if (_PyOS_opterr) + fprintf(stderr, "Unknown option: -%c\n", option); + + return '_'; + } + + if (*(ptr + 1) == ':') { + if (*opt_ptr != '\0') { + _PyOS_optarg = opt_ptr; + opt_ptr = ""; + } + + else { + if (_PyOS_optind >= argc) { + if (_PyOS_opterr) + fprintf(stderr, + "Argument expected for the -%c option\n", option); + return '_'; + } + + _PyOS_optarg = argv[_PyOS_optind++]; + } + } + + return option; +} + +#ifdef __cplusplus +} +#endif + diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/getplatform.c b/AppPkg/Applications/Python/Python-2.7.10/Python/getplatform.c new file mode 100644 index 0000000000..ce79ffe2d7 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/getplatform.c @@ -0,0 +1,12 @@ + +#include "Python.h" + +#ifndef PLATFORM +#define PLATFORM "unknown" +#endif + +const char * +Py_GetPlatform(void) +{ + return PLATFORM; +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/getversion.c b/AppPkg/Applications/Python/Python-2.7.10/Python/getversion.c new file mode 100644 index 0000000000..7c75348f7f --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/getversion.c @@ -0,0 +1,15 @@ + +/* Return the full version string. */ + +#include "Python.h" + +#include "patchlevel.h" + +const char * +Py_GetVersion(void) +{ + static char version[250]; + PyOS_snprintf(version, sizeof(version), "%.80s (%.80s) %.80s", + PY_VERSION, Py_GetBuildInfo(), Py_GetCompiler()); + return version; +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/graminit.c b/AppPkg/Applications/Python/Python-2.7.10/Python/graminit.c new file mode 100644 index 0000000000..db2e9a7504 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/graminit.c @@ -0,0 +1,2177 @@ +/* Generated by Parser/pgen */ + +#include "pgenheaders.h" +#include "grammar.h" +PyAPI_DATA(grammar) _PyParser_Grammar; +static arc arcs_0_0[3] = { + {2, 1}, + {3, 1}, + {4, 2}, +}; +static arc arcs_0_1[1] = { + {0, 1}, +}; +static arc arcs_0_2[1] = { + {2, 1}, +}; +static state states_0[3] = { + {3, arcs_0_0}, + {1, arcs_0_1}, + {1, arcs_0_2}, +}; +static arc arcs_1_0[3] = { + {2, 0}, + {6, 0}, + {7, 1}, +}; +static arc arcs_1_1[1] = { + {0, 1}, +}; +static state states_1[2] = { + {3, arcs_1_0}, + {1, arcs_1_1}, +}; +static arc arcs_2_0[1] = { + {9, 1}, +}; +static arc arcs_2_1[2] = { + {2, 1}, + {7, 2}, +}; +static arc arcs_2_2[1] = { + {0, 2}, +}; +static state states_2[3] = { + {1, arcs_2_0}, + {2, arcs_2_1}, + {1, arcs_2_2}, +}; +static arc arcs_3_0[1] = { + {11, 1}, +}; +static arc arcs_3_1[1] = { + {12, 2}, +}; +static arc arcs_3_2[2] = { + {13, 3}, + {2, 4}, +}; +static arc arcs_3_3[2] = { + {14, 5}, + {15, 6}, +}; +static arc arcs_3_4[1] = { + {0, 4}, +}; +static arc arcs_3_5[1] = { + {15, 6}, +}; +static arc arcs_3_6[1] = { + {2, 4}, +}; +static state states_3[7] = { + {1, arcs_3_0}, + {1, arcs_3_1}, + {2, arcs_3_2}, + {2, arcs_3_3}, + {1, arcs_3_4}, + {1, arcs_3_5}, + {1, arcs_3_6}, +}; +static arc arcs_4_0[1] = { + {10, 1}, +}; +static arc arcs_4_1[2] = { + {10, 1}, + {0, 1}, +}; +static state states_4[2] = { + {1, arcs_4_0}, + {2, arcs_4_1}, +}; +static arc arcs_5_0[1] = { + {16, 1}, +}; +static arc arcs_5_1[2] = { + {18, 2}, + {19, 2}, +}; +static arc arcs_5_2[1] = { + {0, 2}, +}; +static state states_5[3] = { + {1, arcs_5_0}, + {2, arcs_5_1}, + {1, arcs_5_2}, +}; +static arc arcs_6_0[1] = { + {20, 1}, +}; +static arc arcs_6_1[1] = { + {21, 2}, +}; +static arc arcs_6_2[1] = { + {22, 3}, +}; +static arc arcs_6_3[1] = { + {23, 4}, +}; +static arc arcs_6_4[1] = { + {24, 5}, +}; +static arc arcs_6_5[1] = { + {0, 5}, +}; +static state states_6[6] = { + {1, arcs_6_0}, + {1, arcs_6_1}, + {1, arcs_6_2}, + {1, arcs_6_3}, + {1, arcs_6_4}, + {1, arcs_6_5}, +}; +static arc arcs_7_0[1] = { + {13, 1}, +}; +static arc arcs_7_1[2] = { + {25, 2}, + {15, 3}, +}; +static arc arcs_7_2[1] = { + {15, 3}, +}; +static arc arcs_7_3[1] = { + {0, 3}, +}; +static state states_7[4] = { + {1, arcs_7_0}, + {2, arcs_7_1}, + {1, arcs_7_2}, + {1, arcs_7_3}, +}; +static arc arcs_8_0[3] = { + {26, 1}, + {30, 2}, + {31, 3}, +}; +static arc arcs_8_1[3] = { + {27, 4}, + {29, 5}, + {0, 1}, +}; +static arc arcs_8_2[1] = { + {21, 6}, +}; +static arc arcs_8_3[1] = { + {21, 7}, +}; +static arc arcs_8_4[1] = { + {28, 8}, +}; +static arc arcs_8_5[4] = { + {26, 1}, + {30, 2}, + {31, 3}, + {0, 5}, +}; +static arc arcs_8_6[2] = { + {29, 9}, + {0, 6}, +}; +static arc arcs_8_7[1] = { + {0, 7}, +}; +static arc arcs_8_8[2] = { + {29, 5}, + {0, 8}, +}; +static arc arcs_8_9[1] = { + {31, 3}, +}; +static state states_8[10] = { + {3, arcs_8_0}, + {3, arcs_8_1}, + {1, arcs_8_2}, + {1, arcs_8_3}, + {1, arcs_8_4}, + {4, arcs_8_5}, + {2, arcs_8_6}, + {1, arcs_8_7}, + {2, arcs_8_8}, + {1, arcs_8_9}, +}; +static arc arcs_9_0[2] = { + {21, 1}, + {13, 2}, +}; +static arc arcs_9_1[1] = { + {0, 1}, +}; +static arc arcs_9_2[1] = { + {32, 3}, +}; +static arc arcs_9_3[1] = { + {15, 1}, +}; +static state states_9[4] = { + {2, arcs_9_0}, + {1, arcs_9_1}, + {1, arcs_9_2}, + {1, arcs_9_3}, +}; +static arc arcs_10_0[1] = { + {26, 1}, +}; +static arc arcs_10_1[2] = { + {29, 2}, + {0, 1}, +}; +static arc arcs_10_2[2] = { + {26, 1}, + {0, 2}, +}; +static state states_10[3] = { + {1, arcs_10_0}, + {2, arcs_10_1}, + {2, arcs_10_2}, +}; +static arc arcs_11_0[2] = { + {3, 1}, + {4, 1}, +}; +static arc arcs_11_1[1] = { + {0, 1}, +}; +static state states_11[2] = { + {2, arcs_11_0}, + {1, arcs_11_1}, +}; +static arc arcs_12_0[1] = { + {33, 1}, +}; +static arc arcs_12_1[2] = { + {34, 2}, + {2, 3}, +}; +static arc arcs_12_2[2] = { + {33, 1}, + {2, 3}, +}; +static arc arcs_12_3[1] = { + {0, 3}, +}; +static state states_12[4] = { + {1, arcs_12_0}, + {2, arcs_12_1}, + {2, arcs_12_2}, + {1, arcs_12_3}, +}; +static arc arcs_13_0[9] = { + {35, 1}, + {36, 1}, + {37, 1}, + {38, 1}, + {39, 1}, + {40, 1}, + {41, 1}, + {42, 1}, + {43, 1}, +}; +static arc arcs_13_1[1] = { + {0, 1}, +}; +static state states_13[2] = { + {9, arcs_13_0}, + {1, arcs_13_1}, +}; +static arc arcs_14_0[1] = { + {9, 1}, +}; +static arc arcs_14_1[3] = { + {44, 2}, + {27, 3}, + {0, 1}, +}; +static arc arcs_14_2[2] = { + {45, 4}, + {9, 4}, +}; +static arc arcs_14_3[2] = { + {45, 5}, + {9, 5}, +}; +static arc arcs_14_4[1] = { + {0, 4}, +}; +static arc arcs_14_5[2] = { + {27, 3}, + {0, 5}, +}; +static state states_14[6] = { + {1, arcs_14_0}, + {3, arcs_14_1}, + {2, arcs_14_2}, + {2, arcs_14_3}, + {1, arcs_14_4}, + {2, arcs_14_5}, +}; +static arc arcs_15_0[12] = { + {46, 1}, + {47, 1}, + {48, 1}, + {49, 1}, + {50, 1}, + {51, 1}, + {52, 1}, + {53, 1}, + {54, 1}, + {55, 1}, + {56, 1}, + {57, 1}, +}; +static arc arcs_15_1[1] = { + {0, 1}, +}; +static state states_15[2] = { + {12, arcs_15_0}, + {1, arcs_15_1}, +}; +static arc arcs_16_0[1] = { + {58, 1}, +}; +static arc arcs_16_1[3] = { + {28, 2}, + {59, 3}, + {0, 1}, +}; +static arc arcs_16_2[2] = { + {29, 4}, + {0, 2}, +}; +static arc arcs_16_3[1] = { + {28, 5}, +}; +static arc arcs_16_4[2] = { + {28, 2}, + {0, 4}, +}; +static arc arcs_16_5[2] = { + {29, 6}, + {0, 5}, +}; +static arc arcs_16_6[1] = { + {28, 7}, +}; +static arc arcs_16_7[2] = { + {29, 8}, + {0, 7}, +}; +static arc arcs_16_8[2] = { + {28, 7}, + {0, 8}, +}; +static state states_16[9] = { + {1, arcs_16_0}, + {3, arcs_16_1}, + {2, arcs_16_2}, + {1, arcs_16_3}, + {2, arcs_16_4}, + {2, arcs_16_5}, + {1, arcs_16_6}, + {2, arcs_16_7}, + {2, arcs_16_8}, +}; +static arc arcs_17_0[1] = { + {60, 1}, +}; +static arc arcs_17_1[1] = { + {61, 2}, +}; +static arc arcs_17_2[1] = { + {0, 2}, +}; +static state states_17[3] = { + {1, arcs_17_0}, + {1, arcs_17_1}, + {1, arcs_17_2}, +}; +static arc arcs_18_0[1] = { + {62, 1}, +}; +static arc arcs_18_1[1] = { + {0, 1}, +}; +static state states_18[2] = { + {1, arcs_18_0}, + {1, arcs_18_1}, +}; +static arc arcs_19_0[5] = { + {63, 1}, + {64, 1}, + {65, 1}, + {66, 1}, + {67, 1}, +}; +static arc arcs_19_1[1] = { + {0, 1}, +}; +static state states_19[2] = { + {5, arcs_19_0}, + {1, arcs_19_1}, +}; +static arc arcs_20_0[1] = { + {68, 1}, +}; +static arc arcs_20_1[1] = { + {0, 1}, +}; +static state states_20[2] = { + {1, arcs_20_0}, + {1, arcs_20_1}, +}; +static arc arcs_21_0[1] = { + {69, 1}, +}; +static arc arcs_21_1[1] = { + {0, 1}, +}; +static state states_21[2] = { + {1, arcs_21_0}, + {1, arcs_21_1}, +}; +static arc arcs_22_0[1] = { + {70, 1}, +}; +static arc arcs_22_1[2] = { + {9, 2}, + {0, 1}, +}; +static arc arcs_22_2[1] = { + {0, 2}, +}; +static state states_22[3] = { + {1, arcs_22_0}, + {2, arcs_22_1}, + {1, arcs_22_2}, +}; +static arc arcs_23_0[1] = { + {45, 1}, +}; +static arc arcs_23_1[1] = { + {0, 1}, +}; +static state states_23[2] = { + {1, arcs_23_0}, + {1, arcs_23_1}, +}; +static arc arcs_24_0[1] = { + {71, 1}, +}; +static arc arcs_24_1[2] = { + {28, 2}, + {0, 1}, +}; +static arc arcs_24_2[2] = { + {29, 3}, + {0, 2}, +}; +static arc arcs_24_3[1] = { + {28, 4}, +}; +static arc arcs_24_4[2] = { + {29, 5}, + {0, 4}, +}; +static arc arcs_24_5[1] = { + {28, 6}, +}; +static arc arcs_24_6[1] = { + {0, 6}, +}; +static state states_24[7] = { + {1, arcs_24_0}, + {2, arcs_24_1}, + {2, arcs_24_2}, + {1, arcs_24_3}, + {2, arcs_24_4}, + {1, arcs_24_5}, + {1, arcs_24_6}, +}; +static arc arcs_25_0[2] = { + {72, 1}, + {73, 1}, +}; +static arc arcs_25_1[1] = { + {0, 1}, +}; +static state states_25[2] = { + {2, arcs_25_0}, + {1, arcs_25_1}, +}; +static arc arcs_26_0[1] = { + {74, 1}, +}; +static arc arcs_26_1[1] = { + {75, 2}, +}; +static arc arcs_26_2[1] = { + {0, 2}, +}; +static state states_26[3] = { + {1, arcs_26_0}, + {1, arcs_26_1}, + {1, arcs_26_2}, +}; +static arc arcs_27_0[1] = { + {76, 1}, +}; +static arc arcs_27_1[2] = { + {77, 2}, + {12, 3}, +}; +static arc arcs_27_2[3] = { + {77, 2}, + {12, 3}, + {74, 4}, +}; +static arc arcs_27_3[1] = { + {74, 4}, +}; +static arc arcs_27_4[3] = { + {30, 5}, + {13, 6}, + {78, 5}, +}; +static arc arcs_27_5[1] = { + {0, 5}, +}; +static arc arcs_27_6[1] = { + {78, 7}, +}; +static arc arcs_27_7[1] = { + {15, 5}, +}; +static state states_27[8] = { + {1, arcs_27_0}, + {2, arcs_27_1}, + {3, arcs_27_2}, + {1, arcs_27_3}, + {3, arcs_27_4}, + {1, arcs_27_5}, + {1, arcs_27_6}, + {1, arcs_27_7}, +}; +static arc arcs_28_0[1] = { + {21, 1}, +}; +static arc arcs_28_1[2] = { + {80, 2}, + {0, 1}, +}; +static arc arcs_28_2[1] = { + {21, 3}, +}; +static arc arcs_28_3[1] = { + {0, 3}, +}; +static state states_28[4] = { + {1, arcs_28_0}, + {2, arcs_28_1}, + {1, arcs_28_2}, + {1, arcs_28_3}, +}; +static arc arcs_29_0[1] = { + {12, 1}, +}; +static arc arcs_29_1[2] = { + {80, 2}, + {0, 1}, +}; +static arc arcs_29_2[1] = { + {21, 3}, +}; +static arc arcs_29_3[1] = { + {0, 3}, +}; +static state states_29[4] = { + {1, arcs_29_0}, + {2, arcs_29_1}, + {1, arcs_29_2}, + {1, arcs_29_3}, +}; +static arc arcs_30_0[1] = { + {79, 1}, +}; +static arc arcs_30_1[2] = { + {29, 2}, + {0, 1}, +}; +static arc arcs_30_2[2] = { + {79, 1}, + {0, 2}, +}; +static state states_30[3] = { + {1, arcs_30_0}, + {2, arcs_30_1}, + {2, arcs_30_2}, +}; +static arc arcs_31_0[1] = { + {81, 1}, +}; +static arc arcs_31_1[2] = { + {29, 0}, + {0, 1}, +}; +static state states_31[2] = { + {1, arcs_31_0}, + {2, arcs_31_1}, +}; +static arc arcs_32_0[1] = { + {21, 1}, +}; +static arc arcs_32_1[2] = { + {77, 0}, + {0, 1}, +}; +static state states_32[2] = { + {1, arcs_32_0}, + {2, arcs_32_1}, +}; +static arc arcs_33_0[1] = { + {82, 1}, +}; +static arc arcs_33_1[1] = { + {21, 2}, +}; +static arc arcs_33_2[2] = { + {29, 1}, + {0, 2}, +}; +static state states_33[3] = { + {1, arcs_33_0}, + {1, arcs_33_1}, + {2, arcs_33_2}, +}; +static arc arcs_34_0[1] = { + {83, 1}, +}; +static arc arcs_34_1[1] = { + {84, 2}, +}; +static arc arcs_34_2[2] = { + {85, 3}, + {0, 2}, +}; +static arc arcs_34_3[1] = { + {28, 4}, +}; +static arc arcs_34_4[2] = { + {29, 5}, + {0, 4}, +}; +static arc arcs_34_5[1] = { + {28, 6}, +}; +static arc arcs_34_6[1] = { + {0, 6}, +}; +static state states_34[7] = { + {1, arcs_34_0}, + {1, arcs_34_1}, + {2, arcs_34_2}, + {1, arcs_34_3}, + {2, arcs_34_4}, + {1, arcs_34_5}, + {1, arcs_34_6}, +}; +static arc arcs_35_0[1] = { + {86, 1}, +}; +static arc arcs_35_1[1] = { + {28, 2}, +}; +static arc arcs_35_2[2] = { + {29, 3}, + {0, 2}, +}; +static arc arcs_35_3[1] = { + {28, 4}, +}; +static arc arcs_35_4[1] = { + {0, 4}, +}; +static state states_35[5] = { + {1, arcs_35_0}, + {1, arcs_35_1}, + {2, arcs_35_2}, + {1, arcs_35_3}, + {1, arcs_35_4}, +}; +static arc arcs_36_0[8] = { + {87, 1}, + {88, 1}, + {89, 1}, + {90, 1}, + {91, 1}, + {19, 1}, + {18, 1}, + {17, 1}, +}; +static arc arcs_36_1[1] = { + {0, 1}, +}; +static state states_36[2] = { + {8, arcs_36_0}, + {1, arcs_36_1}, +}; +static arc arcs_37_0[1] = { + {92, 1}, +}; +static arc arcs_37_1[1] = { + {28, 2}, +}; +static arc arcs_37_2[1] = { + {23, 3}, +}; +static arc arcs_37_3[1] = { + {24, 4}, +}; +static arc arcs_37_4[3] = { + {93, 1}, + {94, 5}, + {0, 4}, +}; +static arc arcs_37_5[1] = { + {23, 6}, +}; +static arc arcs_37_6[1] = { + {24, 7}, +}; +static arc arcs_37_7[1] = { + {0, 7}, +}; +static state states_37[8] = { + {1, arcs_37_0}, + {1, arcs_37_1}, + {1, arcs_37_2}, + {1, arcs_37_3}, + {3, arcs_37_4}, + {1, arcs_37_5}, + {1, arcs_37_6}, + {1, arcs_37_7}, +}; +static arc arcs_38_0[1] = { + {95, 1}, +}; +static arc arcs_38_1[1] = { + {28, 2}, +}; +static arc arcs_38_2[1] = { + {23, 3}, +}; +static arc arcs_38_3[1] = { + {24, 4}, +}; +static arc arcs_38_4[2] = { + {94, 5}, + {0, 4}, +}; +static arc arcs_38_5[1] = { + {23, 6}, +}; +static arc arcs_38_6[1] = { + {24, 7}, +}; +static arc arcs_38_7[1] = { + {0, 7}, +}; +static state states_38[8] = { + {1, arcs_38_0}, + {1, arcs_38_1}, + {1, arcs_38_2}, + {1, arcs_38_3}, + {2, arcs_38_4}, + {1, arcs_38_5}, + {1, arcs_38_6}, + {1, arcs_38_7}, +}; +static arc arcs_39_0[1] = { + {96, 1}, +}; +static arc arcs_39_1[1] = { + {61, 2}, +}; +static arc arcs_39_2[1] = { + {85, 3}, +}; +static arc arcs_39_3[1] = { + {9, 4}, +}; +static arc arcs_39_4[1] = { + {23, 5}, +}; +static arc arcs_39_5[1] = { + {24, 6}, +}; +static arc arcs_39_6[2] = { + {94, 7}, + {0, 6}, +}; +static arc arcs_39_7[1] = { + {23, 8}, +}; +static arc arcs_39_8[1] = { + {24, 9}, +}; +static arc arcs_39_9[1] = { + {0, 9}, +}; +static state states_39[10] = { + {1, arcs_39_0}, + {1, arcs_39_1}, + {1, arcs_39_2}, + {1, arcs_39_3}, + {1, arcs_39_4}, + {1, arcs_39_5}, + {2, arcs_39_6}, + {1, arcs_39_7}, + {1, arcs_39_8}, + {1, arcs_39_9}, +}; +static arc arcs_40_0[1] = { + {97, 1}, +}; +static arc arcs_40_1[1] = { + {23, 2}, +}; +static arc arcs_40_2[1] = { + {24, 3}, +}; +static arc arcs_40_3[2] = { + {98, 4}, + {99, 5}, +}; +static arc arcs_40_4[1] = { + {23, 6}, +}; +static arc arcs_40_5[1] = { + {23, 7}, +}; +static arc arcs_40_6[1] = { + {24, 8}, +}; +static arc arcs_40_7[1] = { + {24, 9}, +}; +static arc arcs_40_8[4] = { + {98, 4}, + {94, 10}, + {99, 5}, + {0, 8}, +}; +static arc arcs_40_9[1] = { + {0, 9}, +}; +static arc arcs_40_10[1] = { + {23, 11}, +}; +static arc arcs_40_11[1] = { + {24, 12}, +}; +static arc arcs_40_12[2] = { + {99, 5}, + {0, 12}, +}; +static state states_40[13] = { + {1, arcs_40_0}, + {1, arcs_40_1}, + {1, arcs_40_2}, + {2, arcs_40_3}, + {1, arcs_40_4}, + {1, arcs_40_5}, + {1, arcs_40_6}, + {1, arcs_40_7}, + {4, arcs_40_8}, + {1, arcs_40_9}, + {1, arcs_40_10}, + {1, arcs_40_11}, + {2, arcs_40_12}, +}; +static arc arcs_41_0[1] = { + {100, 1}, +}; +static arc arcs_41_1[1] = { + {101, 2}, +}; +static arc arcs_41_2[2] = { + {29, 1}, + {23, 3}, +}; +static arc arcs_41_3[1] = { + {24, 4}, +}; +static arc arcs_41_4[1] = { + {0, 4}, +}; +static state states_41[5] = { + {1, arcs_41_0}, + {1, arcs_41_1}, + {2, arcs_41_2}, + {1, arcs_41_3}, + {1, arcs_41_4}, +}; +static arc arcs_42_0[1] = { + {28, 1}, +}; +static arc arcs_42_1[2] = { + {80, 2}, + {0, 1}, +}; +static arc arcs_42_2[1] = { + {84, 3}, +}; +static arc arcs_42_3[1] = { + {0, 3}, +}; +static state states_42[4] = { + {1, arcs_42_0}, + {2, arcs_42_1}, + {1, arcs_42_2}, + {1, arcs_42_3}, +}; +static arc arcs_43_0[1] = { + {102, 1}, +}; +static arc arcs_43_1[2] = { + {28, 2}, + {0, 1}, +}; +static arc arcs_43_2[3] = { + {80, 3}, + {29, 3}, + {0, 2}, +}; +static arc arcs_43_3[1] = { + {28, 4}, +}; +static arc arcs_43_4[1] = { + {0, 4}, +}; +static state states_43[5] = { + {1, arcs_43_0}, + {2, arcs_43_1}, + {3, arcs_43_2}, + {1, arcs_43_3}, + {1, arcs_43_4}, +}; +static arc arcs_44_0[2] = { + {3, 1}, + {2, 2}, +}; +static arc arcs_44_1[1] = { + {0, 1}, +}; +static arc arcs_44_2[1] = { + {103, 3}, +}; +static arc arcs_44_3[1] = { + {6, 4}, +}; +static arc arcs_44_4[2] = { + {6, 4}, + {104, 1}, +}; +static state states_44[5] = { + {2, arcs_44_0}, + {1, arcs_44_1}, + {1, arcs_44_2}, + {1, arcs_44_3}, + {2, arcs_44_4}, +}; +static arc arcs_45_0[1] = { + {106, 1}, +}; +static arc arcs_45_1[2] = { + {29, 2}, + {0, 1}, +}; +static arc arcs_45_2[1] = { + {106, 3}, +}; +static arc arcs_45_3[2] = { + {29, 4}, + {0, 3}, +}; +static arc arcs_45_4[2] = { + {106, 3}, + {0, 4}, +}; +static state states_45[5] = { + {1, arcs_45_0}, + {2, arcs_45_1}, + {1, arcs_45_2}, + {2, arcs_45_3}, + {2, arcs_45_4}, +}; +static arc arcs_46_0[2] = { + {107, 1}, + {108, 1}, +}; +static arc arcs_46_1[1] = { + {0, 1}, +}; +static state states_46[2] = { + {2, arcs_46_0}, + {1, arcs_46_1}, +}; +static arc arcs_47_0[1] = { + {109, 1}, +}; +static arc arcs_47_1[2] = { + {25, 2}, + {23, 3}, +}; +static arc arcs_47_2[1] = { + {23, 3}, +}; +static arc arcs_47_3[1] = { + {106, 4}, +}; +static arc arcs_47_4[1] = { + {0, 4}, +}; +static state states_47[5] = { + {1, arcs_47_0}, + {2, arcs_47_1}, + {1, arcs_47_2}, + {1, arcs_47_3}, + {1, arcs_47_4}, +}; +static arc arcs_48_0[2] = { + {107, 1}, + {110, 2}, +}; +static arc arcs_48_1[2] = { + {92, 3}, + {0, 1}, +}; +static arc arcs_48_2[1] = { + {0, 2}, +}; +static arc arcs_48_3[1] = { + {107, 4}, +}; +static arc arcs_48_4[1] = { + {94, 5}, +}; +static arc arcs_48_5[1] = { + {28, 2}, +}; +static state states_48[6] = { + {2, arcs_48_0}, + {2, arcs_48_1}, + {1, arcs_48_2}, + {1, arcs_48_3}, + {1, arcs_48_4}, + {1, arcs_48_5}, +}; +static arc arcs_49_0[1] = { + {111, 1}, +}; +static arc arcs_49_1[2] = { + {112, 0}, + {0, 1}, +}; +static state states_49[2] = { + {1, arcs_49_0}, + {2, arcs_49_1}, +}; +static arc arcs_50_0[1] = { + {113, 1}, +}; +static arc arcs_50_1[2] = { + {114, 0}, + {0, 1}, +}; +static state states_50[2] = { + {1, arcs_50_0}, + {2, arcs_50_1}, +}; +static arc arcs_51_0[2] = { + {115, 1}, + {116, 2}, +}; +static arc arcs_51_1[1] = { + {113, 2}, +}; +static arc arcs_51_2[1] = { + {0, 2}, +}; +static state states_51[3] = { + {2, arcs_51_0}, + {1, arcs_51_1}, + {1, arcs_51_2}, +}; +static arc arcs_52_0[1] = { + {84, 1}, +}; +static arc arcs_52_1[2] = { + {117, 0}, + {0, 1}, +}; +static state states_52[2] = { + {1, arcs_52_0}, + {2, arcs_52_1}, +}; +static arc arcs_53_0[10] = { + {118, 1}, + {119, 1}, + {120, 1}, + {121, 1}, + {122, 1}, + {123, 1}, + {124, 1}, + {85, 1}, + {115, 2}, + {125, 3}, +}; +static arc arcs_53_1[1] = { + {0, 1}, +}; +static arc arcs_53_2[1] = { + {85, 1}, +}; +static arc arcs_53_3[2] = { + {115, 1}, + {0, 3}, +}; +static state states_53[4] = { + {10, arcs_53_0}, + {1, arcs_53_1}, + {1, arcs_53_2}, + {2, arcs_53_3}, +}; +static arc arcs_54_0[1] = { + {126, 1}, +}; +static arc arcs_54_1[2] = { + {127, 0}, + {0, 1}, +}; +static state states_54[2] = { + {1, arcs_54_0}, + {2, arcs_54_1}, +}; +static arc arcs_55_0[1] = { + {128, 1}, +}; +static arc arcs_55_1[2] = { + {129, 0}, + {0, 1}, +}; +static state states_55[2] = { + {1, arcs_55_0}, + {2, arcs_55_1}, +}; +static arc arcs_56_0[1] = { + {130, 1}, +}; +static arc arcs_56_1[2] = { + {131, 0}, + {0, 1}, +}; +static state states_56[2] = { + {1, arcs_56_0}, + {2, arcs_56_1}, +}; +static arc arcs_57_0[1] = { + {132, 1}, +}; +static arc arcs_57_1[3] = { + {133, 0}, + {59, 0}, + {0, 1}, +}; +static state states_57[2] = { + {1, arcs_57_0}, + {3, arcs_57_1}, +}; +static arc arcs_58_0[1] = { + {134, 1}, +}; +static arc arcs_58_1[3] = { + {135, 0}, + {136, 0}, + {0, 1}, +}; +static state states_58[2] = { + {1, arcs_58_0}, + {3, arcs_58_1}, +}; +static arc arcs_59_0[1] = { + {137, 1}, +}; +static arc arcs_59_1[5] = { + {30, 0}, + {138, 0}, + {139, 0}, + {140, 0}, + {0, 1}, +}; +static state states_59[2] = { + {1, arcs_59_0}, + {5, arcs_59_1}, +}; +static arc arcs_60_0[4] = { + {135, 1}, + {136, 1}, + {141, 1}, + {142, 2}, +}; +static arc arcs_60_1[1] = { + {137, 2}, +}; +static arc arcs_60_2[1] = { + {0, 2}, +}; +static state states_60[3] = { + {4, arcs_60_0}, + {1, arcs_60_1}, + {1, arcs_60_2}, +}; +static arc arcs_61_0[1] = { + {143, 1}, +}; +static arc arcs_61_1[3] = { + {144, 1}, + {31, 2}, + {0, 1}, +}; +static arc arcs_61_2[1] = { + {137, 3}, +}; +static arc arcs_61_3[1] = { + {0, 3}, +}; +static state states_61[4] = { + {1, arcs_61_0}, + {3, arcs_61_1}, + {1, arcs_61_2}, + {1, arcs_61_3}, +}; +static arc arcs_62_0[7] = { + {13, 1}, + {146, 2}, + {149, 3}, + {152, 4}, + {21, 5}, + {154, 5}, + {155, 6}, +}; +static arc arcs_62_1[3] = { + {45, 7}, + {145, 7}, + {15, 5}, +}; +static arc arcs_62_2[2] = { + {147, 8}, + {148, 5}, +}; +static arc arcs_62_3[2] = { + {150, 9}, + {151, 5}, +}; +static arc arcs_62_4[1] = { + {153, 10}, +}; +static arc arcs_62_5[1] = { + {0, 5}, +}; +static arc arcs_62_6[2] = { + {155, 6}, + {0, 6}, +}; +static arc arcs_62_7[1] = { + {15, 5}, +}; +static arc arcs_62_8[1] = { + {148, 5}, +}; +static arc arcs_62_9[1] = { + {151, 5}, +}; +static arc arcs_62_10[1] = { + {152, 5}, +}; +static state states_62[11] = { + {7, arcs_62_0}, + {3, arcs_62_1}, + {2, arcs_62_2}, + {2, arcs_62_3}, + {1, arcs_62_4}, + {1, arcs_62_5}, + {2, arcs_62_6}, + {1, arcs_62_7}, + {1, arcs_62_8}, + {1, arcs_62_9}, + {1, arcs_62_10}, +}; +static arc arcs_63_0[1] = { + {28, 1}, +}; +static arc arcs_63_1[3] = { + {156, 2}, + {29, 3}, + {0, 1}, +}; +static arc arcs_63_2[1] = { + {0, 2}, +}; +static arc arcs_63_3[2] = { + {28, 4}, + {0, 3}, +}; +static arc arcs_63_4[2] = { + {29, 3}, + {0, 4}, +}; +static state states_63[5] = { + {1, arcs_63_0}, + {3, arcs_63_1}, + {1, arcs_63_2}, + {2, arcs_63_3}, + {2, arcs_63_4}, +}; +static arc arcs_64_0[1] = { + {28, 1}, +}; +static arc arcs_64_1[3] = { + {157, 2}, + {29, 3}, + {0, 1}, +}; +static arc arcs_64_2[1] = { + {0, 2}, +}; +static arc arcs_64_3[2] = { + {28, 4}, + {0, 3}, +}; +static arc arcs_64_4[2] = { + {29, 3}, + {0, 4}, +}; +static state states_64[5] = { + {1, arcs_64_0}, + {3, arcs_64_1}, + {1, arcs_64_2}, + {2, arcs_64_3}, + {2, arcs_64_4}, +}; +static arc arcs_65_0[1] = { + {109, 1}, +}; +static arc arcs_65_1[2] = { + {25, 2}, + {23, 3}, +}; +static arc arcs_65_2[1] = { + {23, 3}, +}; +static arc arcs_65_3[1] = { + {28, 4}, +}; +static arc arcs_65_4[1] = { + {0, 4}, +}; +static state states_65[5] = { + {1, arcs_65_0}, + {2, arcs_65_1}, + {1, arcs_65_2}, + {1, arcs_65_3}, + {1, arcs_65_4}, +}; +static arc arcs_66_0[3] = { + {13, 1}, + {146, 2}, + {77, 3}, +}; +static arc arcs_66_1[2] = { + {14, 4}, + {15, 5}, +}; +static arc arcs_66_2[1] = { + {158, 6}, +}; +static arc arcs_66_3[1] = { + {21, 5}, +}; +static arc arcs_66_4[1] = { + {15, 5}, +}; +static arc arcs_66_5[1] = { + {0, 5}, +}; +static arc arcs_66_6[1] = { + {148, 5}, +}; +static state states_66[7] = { + {3, arcs_66_0}, + {2, arcs_66_1}, + {1, arcs_66_2}, + {1, arcs_66_3}, + {1, arcs_66_4}, + {1, arcs_66_5}, + {1, arcs_66_6}, +}; +static arc arcs_67_0[1] = { + {159, 1}, +}; +static arc arcs_67_1[2] = { + {29, 2}, + {0, 1}, +}; +static arc arcs_67_2[2] = { + {159, 1}, + {0, 2}, +}; +static state states_67[3] = { + {1, arcs_67_0}, + {2, arcs_67_1}, + {2, arcs_67_2}, +}; +static arc arcs_68_0[3] = { + {77, 1}, + {28, 2}, + {23, 3}, +}; +static arc arcs_68_1[1] = { + {77, 4}, +}; +static arc arcs_68_2[2] = { + {23, 3}, + {0, 2}, +}; +static arc arcs_68_3[3] = { + {28, 5}, + {160, 6}, + {0, 3}, +}; +static arc arcs_68_4[1] = { + {77, 6}, +}; +static arc arcs_68_5[2] = { + {160, 6}, + {0, 5}, +}; +static arc arcs_68_6[1] = { + {0, 6}, +}; +static state states_68[7] = { + {3, arcs_68_0}, + {1, arcs_68_1}, + {2, arcs_68_2}, + {3, arcs_68_3}, + {1, arcs_68_4}, + {2, arcs_68_5}, + {1, arcs_68_6}, +}; +static arc arcs_69_0[1] = { + {23, 1}, +}; +static arc arcs_69_1[2] = { + {28, 2}, + {0, 1}, +}; +static arc arcs_69_2[1] = { + {0, 2}, +}; +static state states_69[3] = { + {1, arcs_69_0}, + {2, arcs_69_1}, + {1, arcs_69_2}, +}; +static arc arcs_70_0[1] = { + {84, 1}, +}; +static arc arcs_70_1[2] = { + {29, 2}, + {0, 1}, +}; +static arc arcs_70_2[2] = { + {84, 1}, + {0, 2}, +}; +static state states_70[3] = { + {1, arcs_70_0}, + {2, arcs_70_1}, + {2, arcs_70_2}, +}; +static arc arcs_71_0[1] = { + {28, 1}, +}; +static arc arcs_71_1[2] = { + {29, 2}, + {0, 1}, +}; +static arc arcs_71_2[2] = { + {28, 1}, + {0, 2}, +}; +static state states_71[3] = { + {1, arcs_71_0}, + {2, arcs_71_1}, + {2, arcs_71_2}, +}; +static arc arcs_72_0[1] = { + {28, 1}, +}; +static arc arcs_72_1[4] = { + {23, 2}, + {157, 3}, + {29, 4}, + {0, 1}, +}; +static arc arcs_72_2[1] = { + {28, 5}, +}; +static arc arcs_72_3[1] = { + {0, 3}, +}; +static arc arcs_72_4[2] = { + {28, 6}, + {0, 4}, +}; +static arc arcs_72_5[3] = { + {157, 3}, + {29, 7}, + {0, 5}, +}; +static arc arcs_72_6[2] = { + {29, 4}, + {0, 6}, +}; +static arc arcs_72_7[2] = { + {28, 8}, + {0, 7}, +}; +static arc arcs_72_8[1] = { + {23, 9}, +}; +static arc arcs_72_9[1] = { + {28, 10}, +}; +static arc arcs_72_10[2] = { + {29, 7}, + {0, 10}, +}; +static state states_72[11] = { + {1, arcs_72_0}, + {4, arcs_72_1}, + {1, arcs_72_2}, + {1, arcs_72_3}, + {2, arcs_72_4}, + {3, arcs_72_5}, + {2, arcs_72_6}, + {2, arcs_72_7}, + {1, arcs_72_8}, + {1, arcs_72_9}, + {2, arcs_72_10}, +}; +static arc arcs_73_0[1] = { + {161, 1}, +}; +static arc arcs_73_1[1] = { + {21, 2}, +}; +static arc arcs_73_2[2] = { + {13, 3}, + {23, 4}, +}; +static arc arcs_73_3[2] = { + {9, 5}, + {15, 6}, +}; +static arc arcs_73_4[1] = { + {24, 7}, +}; +static arc arcs_73_5[1] = { + {15, 6}, +}; +static arc arcs_73_6[1] = { + {23, 4}, +}; +static arc arcs_73_7[1] = { + {0, 7}, +}; +static state states_73[8] = { + {1, arcs_73_0}, + {1, arcs_73_1}, + {2, arcs_73_2}, + {2, arcs_73_3}, + {1, arcs_73_4}, + {1, arcs_73_5}, + {1, arcs_73_6}, + {1, arcs_73_7}, +}; +static arc arcs_74_0[3] = { + {162, 1}, + {30, 2}, + {31, 3}, +}; +static arc arcs_74_1[2] = { + {29, 4}, + {0, 1}, +}; +static arc arcs_74_2[1] = { + {28, 5}, +}; +static arc arcs_74_3[1] = { + {28, 6}, +}; +static arc arcs_74_4[4] = { + {162, 1}, + {30, 2}, + {31, 3}, + {0, 4}, +}; +static arc arcs_74_5[2] = { + {29, 7}, + {0, 5}, +}; +static arc arcs_74_6[1] = { + {0, 6}, +}; +static arc arcs_74_7[2] = { + {162, 5}, + {31, 3}, +}; +static state states_74[8] = { + {3, arcs_74_0}, + {2, arcs_74_1}, + {1, arcs_74_2}, + {1, arcs_74_3}, + {4, arcs_74_4}, + {2, arcs_74_5}, + {1, arcs_74_6}, + {2, arcs_74_7}, +}; +static arc arcs_75_0[1] = { + {28, 1}, +}; +static arc arcs_75_1[3] = { + {157, 2}, + {27, 3}, + {0, 1}, +}; +static arc arcs_75_2[1] = { + {0, 2}, +}; +static arc arcs_75_3[1] = { + {28, 2}, +}; +static state states_75[4] = { + {1, arcs_75_0}, + {3, arcs_75_1}, + {1, arcs_75_2}, + {1, arcs_75_3}, +}; +static arc arcs_76_0[2] = { + {156, 1}, + {164, 1}, +}; +static arc arcs_76_1[1] = { + {0, 1}, +}; +static state states_76[2] = { + {2, arcs_76_0}, + {1, arcs_76_1}, +}; +static arc arcs_77_0[1] = { + {96, 1}, +}; +static arc arcs_77_1[1] = { + {61, 2}, +}; +static arc arcs_77_2[1] = { + {85, 3}, +}; +static arc arcs_77_3[1] = { + {105, 4}, +}; +static arc arcs_77_4[2] = { + {163, 5}, + {0, 4}, +}; +static arc arcs_77_5[1] = { + {0, 5}, +}; +static state states_77[6] = { + {1, arcs_77_0}, + {1, arcs_77_1}, + {1, arcs_77_2}, + {1, arcs_77_3}, + {2, arcs_77_4}, + {1, arcs_77_5}, +}; +static arc arcs_78_0[1] = { + {92, 1}, +}; +static arc arcs_78_1[1] = { + {106, 2}, +}; +static arc arcs_78_2[2] = { + {163, 3}, + {0, 2}, +}; +static arc arcs_78_3[1] = { + {0, 3}, +}; +static state states_78[4] = { + {1, arcs_78_0}, + {1, arcs_78_1}, + {2, arcs_78_2}, + {1, arcs_78_3}, +}; +static arc arcs_79_0[2] = { + {157, 1}, + {166, 1}, +}; +static arc arcs_79_1[1] = { + {0, 1}, +}; +static state states_79[2] = { + {2, arcs_79_0}, + {1, arcs_79_1}, +}; +static arc arcs_80_0[1] = { + {96, 1}, +}; +static arc arcs_80_1[1] = { + {61, 2}, +}; +static arc arcs_80_2[1] = { + {85, 3}, +}; +static arc arcs_80_3[1] = { + {107, 4}, +}; +static arc arcs_80_4[2] = { + {165, 5}, + {0, 4}, +}; +static arc arcs_80_5[1] = { + {0, 5}, +}; +static state states_80[6] = { + {1, arcs_80_0}, + {1, arcs_80_1}, + {1, arcs_80_2}, + {1, arcs_80_3}, + {2, arcs_80_4}, + {1, arcs_80_5}, +}; +static arc arcs_81_0[1] = { + {92, 1}, +}; +static arc arcs_81_1[1] = { + {106, 2}, +}; +static arc arcs_81_2[2] = { + {165, 3}, + {0, 2}, +}; +static arc arcs_81_3[1] = { + {0, 3}, +}; +static state states_81[4] = { + {1, arcs_81_0}, + {1, arcs_81_1}, + {2, arcs_81_2}, + {1, arcs_81_3}, +}; +static arc arcs_82_0[1] = { + {28, 1}, +}; +static arc arcs_82_1[2] = { + {29, 0}, + {0, 1}, +}; +static state states_82[2] = { + {1, arcs_82_0}, + {2, arcs_82_1}, +}; +static arc arcs_83_0[1] = { + {21, 1}, +}; +static arc arcs_83_1[1] = { + {0, 1}, +}; +static state states_83[2] = { + {1, arcs_83_0}, + {1, arcs_83_1}, +}; +static arc arcs_84_0[1] = { + {168, 1}, +}; +static arc arcs_84_1[2] = { + {9, 2}, + {0, 1}, +}; +static arc arcs_84_2[1] = { + {0, 2}, +}; +static state states_84[3] = { + {1, arcs_84_0}, + {2, arcs_84_1}, + {1, arcs_84_2}, +}; +static dfa dfas[85] = { + {256, "single_input", 0, 3, states_0, + "\004\050\060\000\000\000\000\124\360\024\114\220\023\040\010\000\200\041\044\015\002\001"}, + {257, "file_input", 0, 2, states_1, + "\204\050\060\000\000\000\000\124\360\024\114\220\023\040\010\000\200\041\044\015\002\001"}, + {258, "eval_input", 0, 3, states_2, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\040\010\000\200\041\044\015\000\000"}, + {259, "decorator", 0, 7, states_3, + "\000\010\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {260, "decorators", 0, 2, states_4, + "\000\010\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {261, "decorated", 0, 3, states_5, + "\000\010\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {262, "funcdef", 0, 6, states_6, + "\000\000\020\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {263, "parameters", 0, 4, states_7, + "\000\040\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {264, "varargslist", 0, 10, states_8, + "\000\040\040\300\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {265, "fpdef", 0, 4, states_9, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {266, "fplist", 0, 3, states_10, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {267, "stmt", 0, 2, states_11, + "\000\050\060\000\000\000\000\124\360\024\114\220\023\040\010\000\200\041\044\015\002\001"}, + {268, "simple_stmt", 0, 4, states_12, + "\000\040\040\000\000\000\000\124\360\024\114\000\000\040\010\000\200\041\044\015\000\001"}, + {269, "small_stmt", 0, 2, states_13, + "\000\040\040\000\000\000\000\124\360\024\114\000\000\040\010\000\200\041\044\015\000\001"}, + {270, "expr_stmt", 0, 6, states_14, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\040\010\000\200\041\044\015\000\000"}, + {271, "augassign", 0, 2, states_15, + "\000\000\000\000\000\300\377\003\000\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {272, "print_stmt", 0, 9, states_16, + "\000\000\000\000\000\000\000\004\000\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {273, "del_stmt", 0, 3, states_17, + "\000\000\000\000\000\000\000\020\000\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {274, "pass_stmt", 0, 2, states_18, + "\000\000\000\000\000\000\000\100\000\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {275, "flow_stmt", 0, 2, states_19, + "\000\000\000\000\000\000\000\000\360\000\000\000\000\000\000\000\000\000\000\000\000\001"}, + {276, "break_stmt", 0, 2, states_20, + "\000\000\000\000\000\000\000\000\020\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {277, "continue_stmt", 0, 2, states_21, + "\000\000\000\000\000\000\000\000\040\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {278, "return_stmt", 0, 3, states_22, + "\000\000\000\000\000\000\000\000\100\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {279, "yield_stmt", 0, 2, states_23, + "\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\001"}, + {280, "raise_stmt", 0, 7, states_24, + "\000\000\000\000\000\000\000\000\200\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {281, "import_stmt", 0, 2, states_25, + "\000\000\000\000\000\000\000\000\000\024\000\000\000\000\000\000\000\000\000\000\000\000"}, + {282, "import_name", 0, 3, states_26, + "\000\000\000\000\000\000\000\000\000\004\000\000\000\000\000\000\000\000\000\000\000\000"}, + {283, "import_from", 0, 8, states_27, + "\000\000\000\000\000\000\000\000\000\020\000\000\000\000\000\000\000\000\000\000\000\000"}, + {284, "import_as_name", 0, 4, states_28, + "\000\000\040\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {285, "dotted_as_name", 0, 4, states_29, + "\000\000\040\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {286, "import_as_names", 0, 3, states_30, + "\000\000\040\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {287, "dotted_as_names", 0, 2, states_31, + "\000\000\040\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {288, "dotted_name", 0, 2, states_32, + "\000\000\040\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {289, "global_stmt", 0, 3, states_33, + "\000\000\000\000\000\000\000\000\000\000\004\000\000\000\000\000\000\000\000\000\000\000"}, + {290, "exec_stmt", 0, 7, states_34, + "\000\000\000\000\000\000\000\000\000\000\010\000\000\000\000\000\000\000\000\000\000\000"}, + {291, "assert_stmt", 0, 5, states_35, + "\000\000\000\000\000\000\000\000\000\000\100\000\000\000\000\000\000\000\000\000\000\000"}, + {292, "compound_stmt", 0, 2, states_36, + "\000\010\020\000\000\000\000\000\000\000\000\220\023\000\000\000\000\000\000\000\002\000"}, + {293, "if_stmt", 0, 8, states_37, + "\000\000\000\000\000\000\000\000\000\000\000\020\000\000\000\000\000\000\000\000\000\000"}, + {294, "while_stmt", 0, 8, states_38, + "\000\000\000\000\000\000\000\000\000\000\000\200\000\000\000\000\000\000\000\000\000\000"}, + {295, "for_stmt", 0, 10, states_39, + "\000\000\000\000\000\000\000\000\000\000\000\000\001\000\000\000\000\000\000\000\000\000"}, + {296, "try_stmt", 0, 13, states_40, + "\000\000\000\000\000\000\000\000\000\000\000\000\002\000\000\000\000\000\000\000\000\000"}, + {297, "with_stmt", 0, 5, states_41, + "\000\000\000\000\000\000\000\000\000\000\000\000\020\000\000\000\000\000\000\000\000\000"}, + {298, "with_item", 0, 4, states_42, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\040\010\000\200\041\044\015\000\000"}, + {299, "except_clause", 0, 5, states_43, + "\000\000\000\000\000\000\000\000\000\000\000\000\100\000\000\000\000\000\000\000\000\000"}, + {300, "suite", 0, 5, states_44, + "\004\040\040\000\000\000\000\124\360\024\114\000\000\040\010\000\200\041\044\015\000\001"}, + {301, "testlist_safe", 0, 5, states_45, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\040\010\000\200\041\044\015\000\000"}, + {302, "old_test", 0, 2, states_46, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\040\010\000\200\041\044\015\000\000"}, + {303, "old_lambdef", 0, 5, states_47, + "\000\000\000\000\000\000\000\000\000\000\000\000\000\040\000\000\000\000\000\000\000\000"}, + {304, "test", 0, 6, states_48, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\040\010\000\200\041\044\015\000\000"}, + {305, "or_test", 0, 2, states_49, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\000\010\000\200\041\044\015\000\000"}, + {306, "and_test", 0, 2, states_50, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\000\010\000\200\041\044\015\000\000"}, + {307, "not_test", 0, 3, states_51, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\000\010\000\200\041\044\015\000\000"}, + {308, "comparison", 0, 2, states_52, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\000\000\000\200\041\044\015\000\000"}, + {309, "comp_op", 0, 4, states_53, + "\000\000\000\000\000\000\000\000\000\000\040\000\000\000\310\077\000\000\000\000\000\000"}, + {310, "expr", 0, 2, states_54, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\000\000\000\200\041\044\015\000\000"}, + {311, "xor_expr", 0, 2, states_55, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\000\000\000\200\041\044\015\000\000"}, + {312, "and_expr", 0, 2, states_56, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\000\000\000\200\041\044\015\000\000"}, + {313, "shift_expr", 0, 2, states_57, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\000\000\000\200\041\044\015\000\000"}, + {314, "arith_expr", 0, 2, states_58, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\000\000\000\200\041\044\015\000\000"}, + {315, "term", 0, 2, states_59, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\000\000\000\200\041\044\015\000\000"}, + {316, "factor", 0, 3, states_60, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\000\000\000\200\041\044\015\000\000"}, + {317, "power", 0, 4, states_61, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\044\015\000\000"}, + {318, "atom", 0, 11, states_62, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\044\015\000\000"}, + {319, "listmaker", 0, 5, states_63, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\040\010\000\200\041\044\015\000\000"}, + {320, "testlist_comp", 0, 5, states_64, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\040\010\000\200\041\044\015\000\000"}, + {321, "lambdef", 0, 5, states_65, + "\000\000\000\000\000\000\000\000\000\000\000\000\000\040\000\000\000\000\000\000\000\000"}, + {322, "trailer", 0, 7, states_66, + "\000\040\000\000\000\000\000\000\000\040\000\000\000\000\000\000\000\000\004\000\000\000"}, + {323, "subscriptlist", 0, 3, states_67, + "\000\040\240\000\000\000\000\000\000\040\000\000\000\040\010\000\200\041\044\015\000\000"}, + {324, "subscript", 0, 7, states_68, + "\000\040\240\000\000\000\000\000\000\040\000\000\000\040\010\000\200\041\044\015\000\000"}, + {325, "sliceop", 0, 3, states_69, + "\000\000\200\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {326, "exprlist", 0, 3, states_70, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\000\000\000\200\041\044\015\000\000"}, + {327, "testlist", 0, 3, states_71, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\040\010\000\200\041\044\015\000\000"}, + {328, "dictorsetmaker", 0, 11, states_72, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\040\010\000\200\041\044\015\000\000"}, + {329, "classdef", 0, 8, states_73, + "\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\002\000"}, + {330, "arglist", 0, 8, states_74, + "\000\040\040\300\000\000\000\000\000\000\000\000\000\040\010\000\200\041\044\015\000\000"}, + {331, "argument", 0, 4, states_75, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\040\010\000\200\041\044\015\000\000"}, + {332, "list_iter", 0, 2, states_76, + "\000\000\000\000\000\000\000\000\000\000\000\020\001\000\000\000\000\000\000\000\000\000"}, + {333, "list_for", 0, 6, states_77, + "\000\000\000\000\000\000\000\000\000\000\000\000\001\000\000\000\000\000\000\000\000\000"}, + {334, "list_if", 0, 4, states_78, + "\000\000\000\000\000\000\000\000\000\000\000\020\000\000\000\000\000\000\000\000\000\000"}, + {335, "comp_iter", 0, 2, states_79, + "\000\000\000\000\000\000\000\000\000\000\000\020\001\000\000\000\000\000\000\000\000\000"}, + {336, "comp_for", 0, 6, states_80, + "\000\000\000\000\000\000\000\000\000\000\000\000\001\000\000\000\000\000\000\000\000\000"}, + {337, "comp_if", 0, 4, states_81, + "\000\000\000\000\000\000\000\000\000\000\000\020\000\000\000\000\000\000\000\000\000\000"}, + {338, "testlist1", 0, 2, states_82, + "\000\040\040\000\000\000\000\000\000\000\000\000\000\040\010\000\200\041\044\015\000\000"}, + {339, "encoding_decl", 0, 2, states_83, + "\000\000\040\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000"}, + {340, "yield_expr", 0, 3, states_84, + "\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\000\001"}, +}; +static label labels[169] = { + {0, "EMPTY"}, + {256, 0}, + {4, 0}, + {268, 0}, + {292, 0}, + {257, 0}, + {267, 0}, + {0, 0}, + {258, 0}, + {327, 0}, + {259, 0}, + {50, 0}, + {288, 0}, + {7, 0}, + {330, 0}, + {8, 0}, + {260, 0}, + {261, 0}, + {329, 0}, + {262, 0}, + {1, "def"}, + {1, 0}, + {263, 0}, + {11, 0}, + {300, 0}, + {264, 0}, + {265, 0}, + {22, 0}, + {304, 0}, + {12, 0}, + {16, 0}, + {36, 0}, + {266, 0}, + {269, 0}, + {13, 0}, + {270, 0}, + {272, 0}, + {273, 0}, + {274, 0}, + {275, 0}, + {281, 0}, + {289, 0}, + {290, 0}, + {291, 0}, + {271, 0}, + {340, 0}, + {37, 0}, + {38, 0}, + {39, 0}, + {40, 0}, + {41, 0}, + {42, 0}, + {43, 0}, + {44, 0}, + {45, 0}, + {46, 0}, + {47, 0}, + {49, 0}, + {1, "print"}, + {35, 0}, + {1, "del"}, + {326, 0}, + {1, "pass"}, + {276, 0}, + {277, 0}, + {278, 0}, + {280, 0}, + {279, 0}, + {1, "break"}, + {1, "continue"}, + {1, "return"}, + {1, "raise"}, + {282, 0}, + {283, 0}, + {1, "import"}, + {287, 0}, + {1, "from"}, + {23, 0}, + {286, 0}, + {284, 0}, + {1, "as"}, + {285, 0}, + {1, "global"}, + {1, "exec"}, + {310, 0}, + {1, "in"}, + {1, "assert"}, + {293, 0}, + {294, 0}, + {295, 0}, + {296, 0}, + {297, 0}, + {1, "if"}, + {1, "elif"}, + {1, "else"}, + {1, "while"}, + {1, "for"}, + {1, "try"}, + {299, 0}, + {1, "finally"}, + {1, "with"}, + {298, 0}, + {1, "except"}, + {5, 0}, + {6, 0}, + {301, 0}, + {302, 0}, + {305, 0}, + {303, 0}, + {1, "lambda"}, + {321, 0}, + {306, 0}, + {1, "or"}, + {307, 0}, + {1, "and"}, + {1, "not"}, + {308, 0}, + {309, 0}, + {20, 0}, + {21, 0}, + {28, 0}, + {31, 0}, + {30, 0}, + {29, 0}, + {29, 0}, + {1, "is"}, + {311, 0}, + {18, 0}, + {312, 0}, + {33, 0}, + {313, 0}, + {19, 0}, + {314, 0}, + {34, 0}, + {315, 0}, + {14, 0}, + {15, 0}, + {316, 0}, + {17, 0}, + {24, 0}, + {48, 0}, + {32, 0}, + {317, 0}, + {318, 0}, + {322, 0}, + {320, 0}, + {9, 0}, + {319, 0}, + {10, 0}, + {26, 0}, + {328, 0}, + {27, 0}, + {25, 0}, + {338, 0}, + {2, 0}, + {3, 0}, + {333, 0}, + {336, 0}, + {323, 0}, + {324, 0}, + {325, 0}, + {1, "class"}, + {331, 0}, + {332, 0}, + {334, 0}, + {335, 0}, + {337, 0}, + {339, 0}, + {1, "yield"}, +}; +grammar _PyParser_Grammar = { + 85, + dfas, + {169, labels}, + 256 +}; diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/import.c b/AppPkg/Applications/Python/Python-2.7.10/Python/import.c new file mode 100644 index 0000000000..6a95d4d981 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/import.c @@ -0,0 +1,3481 @@ + +/* Module definition and import implementation */ + +#include "Python.h" + +#include "Python-ast.h" +#undef Yield /* undefine macro conflicting with winbase.h */ +#include "pyarena.h" +#include "pythonrun.h" +#include "errcode.h" +#include "marshal.h" +#include "code.h" +#include "compile.h" +#include "eval.h" +#include "osdefs.h" +#include "importdl.h" + +#ifdef HAVE_FCNTL_H +#include +#endif +#ifdef __cplusplus +extern "C" { +#endif + +#ifdef MS_WINDOWS +/* for stat.st_mode */ +typedef unsigned short mode_t; +#endif + + +/* Magic word to reject .pyc files generated by other Python versions. + It should change for each incompatible change to the bytecode. + + The value of CR and LF is incorporated so if you ever read or write + a .pyc file in text mode the magic number will be wrong; also, the + Apple MPW compiler swaps their values, botching string constants. + + The magic numbers must be spaced apart atleast 2 values, as the + -U interpeter flag will cause MAGIC+1 being used. They have been + odd numbers for some time now. + + There were a variety of old schemes for setting the magic number. + The current working scheme is to increment the previous value by + 10. + + Known values: + Python 1.5: 20121 + Python 1.5.1: 20121 + Python 1.5.2: 20121 + Python 1.6: 50428 + Python 2.0: 50823 + Python 2.0.1: 50823 + Python 2.1: 60202 + Python 2.1.1: 60202 + Python 2.1.2: 60202 + Python 2.2: 60717 + Python 2.3a0: 62011 + Python 2.3a0: 62021 + Python 2.3a0: 62011 (!) + Python 2.4a0: 62041 + Python 2.4a3: 62051 + Python 2.4b1: 62061 + Python 2.5a0: 62071 + Python 2.5a0: 62081 (ast-branch) + Python 2.5a0: 62091 (with) + Python 2.5a0: 62092 (changed WITH_CLEANUP opcode) + Python 2.5b3: 62101 (fix wrong code: for x, in ...) + Python 2.5b3: 62111 (fix wrong code: x += yield) + Python 2.5c1: 62121 (fix wrong lnotab with for loops and + storing constants that should have been removed) + Python 2.5c2: 62131 (fix wrong code: for x, in ... in listcomp/genexp) + Python 2.6a0: 62151 (peephole optimizations and STORE_MAP opcode) + Python 2.6a1: 62161 (WITH_CLEANUP optimization) + Python 2.7a0: 62171 (optimize list comprehensions/change LIST_APPEND) + Python 2.7a0: 62181 (optimize conditional branches: + introduce POP_JUMP_IF_FALSE and POP_JUMP_IF_TRUE) + Python 2.7a0 62191 (introduce SETUP_WITH) + Python 2.7a0 62201 (introduce BUILD_SET) + Python 2.7a0 62211 (introduce MAP_ADD and SET_ADD) +. +*/ +#define MAGIC (62211 | ((long)'\r'<<16) | ((long)'\n'<<24)) + +/* Magic word as global; note that _PyImport_Init() can change the + value of this global to accommodate for alterations of how the + compiler works which are enabled by command line switches. */ +static long pyc_magic = MAGIC; + +/* See _PyImport_FixupExtension() below */ +static PyObject *extensions = NULL; + +/* This table is defined in config.c: */ +extern struct _inittab _PyImport_Inittab[]; + +struct _inittab *PyImport_Inittab = _PyImport_Inittab; + +/* these tables define the module suffixes that Python recognizes */ +struct filedescr * _PyImport_Filetab = NULL; + +#ifdef RISCOS +static const struct filedescr _PyImport_StandardFiletab[] = { + {"/py", "U", PY_SOURCE}, + {"/pyc", "rb", PY_COMPILED}, + {0, 0} +}; +#else +static const struct filedescr _PyImport_StandardFiletab[] = { + {".py", "U", PY_SOURCE}, +#ifdef MS_WINDOWS + {".pyw", "U", PY_SOURCE}, +#endif + {".pyc", "rb", PY_COMPILED}, + {0, 0} +}; +#endif + +#ifdef MS_WINDOWS +static int isdir(char *path) { + DWORD rv; + /* see issue1293 and issue3677: + * stat() on Windows doesn't recognise paths like + * "e:\\shared\\" and "\\\\whiterab-c2znlh\\shared" as dirs. + * Also reference issue6727: + * stat() on Windows is broken and doesn't resolve symlinks properly. + */ + rv = GetFileAttributesA(path); + return rv != INVALID_FILE_ATTRIBUTES && rv & FILE_ATTRIBUTE_DIRECTORY; +} +#else +#ifdef HAVE_STAT +static int isdir(char *path) { + struct stat statbuf; + return stat(path, &statbuf) == 0 && S_ISDIR(statbuf.st_mode); +} +#else +#ifdef RISCOS +/* with RISCOS, isdir is in unixstuff */ +#else +int isdir(char *path) { + return 0; +} +#endif /* RISCOS */ +#endif /* HAVE_STAT */ +#endif /* MS_WINDOWS */ + +/* Initialize things */ + +void +_PyImport_Init(void) +{ + const struct filedescr *scan; + struct filedescr *filetab; + int countD = 0; + int countS = 0; + + /* prepare _PyImport_Filetab: copy entries from + _PyImport_DynLoadFiletab and _PyImport_StandardFiletab. + */ +#ifdef HAVE_DYNAMIC_LOADING + for (scan = _PyImport_DynLoadFiletab; scan->suffix != NULL; ++scan) + ++countD; +#endif + for (scan = _PyImport_StandardFiletab; scan->suffix != NULL; ++scan) + ++countS; + filetab = PyMem_NEW(struct filedescr, countD + countS + 1); + if (filetab == NULL) + Py_FatalError("Can't initialize import file table."); +#ifdef HAVE_DYNAMIC_LOADING + memcpy(filetab, _PyImport_DynLoadFiletab, + countD * sizeof(struct filedescr)); +#endif + memcpy(filetab + countD, _PyImport_StandardFiletab, + countS * sizeof(struct filedescr)); + filetab[countD + countS].suffix = NULL; + + _PyImport_Filetab = filetab; + + if (Py_OptimizeFlag) { + /* Replace ".pyc" with ".pyo" in _PyImport_Filetab */ + for (; filetab->suffix != NULL; filetab++) { +#ifndef RISCOS + if (strcmp(filetab->suffix, ".pyc") == 0) + filetab->suffix = ".pyo"; +#else + if (strcmp(filetab->suffix, "/pyc") == 0) + filetab->suffix = "/pyo"; +#endif + } + } + + if (Py_UnicodeFlag) { + /* Fix the pyc_magic so that byte compiled code created + using the all-Unicode method doesn't interfere with + code created in normal operation mode. */ + pyc_magic = MAGIC + 1; + } +} + +void +_PyImportHooks_Init(void) +{ + PyObject *v, *path_hooks = NULL, *zimpimport; + int err = 0; + + /* adding sys.path_hooks and sys.path_importer_cache, setting up + zipimport */ + if (PyType_Ready(&PyNullImporter_Type) < 0) + goto error; + + if (Py_VerboseFlag) + PySys_WriteStderr("# installing zipimport hook\n"); + + v = PyList_New(0); + if (v == NULL) + goto error; + err = PySys_SetObject("meta_path", v); + Py_DECREF(v); + if (err) + goto error; + v = PyDict_New(); + if (v == NULL) + goto error; + err = PySys_SetObject("path_importer_cache", v); + Py_DECREF(v); + if (err) + goto error; + path_hooks = PyList_New(0); + if (path_hooks == NULL) + goto error; + err = PySys_SetObject("path_hooks", path_hooks); + if (err) { + error: + PyErr_Print(); + Py_FatalError("initializing sys.meta_path, sys.path_hooks, " + "path_importer_cache, or NullImporter failed" + ); + } + + zimpimport = PyImport_ImportModule("zipimport"); + if (zimpimport == NULL) { + PyErr_Clear(); /* No zip import module -- okay */ + if (Py_VerboseFlag) + PySys_WriteStderr("# can't import zipimport\n"); + } + else { + PyObject *zipimporter = PyObject_GetAttrString(zimpimport, + "zipimporter"); + Py_DECREF(zimpimport); + if (zipimporter == NULL) { + PyErr_Clear(); /* No zipimporter object -- okay */ + if (Py_VerboseFlag) + PySys_WriteStderr( + "# can't import zipimport.zipimporter\n"); + } + else { + /* sys.path_hooks.append(zipimporter) */ + err = PyList_Append(path_hooks, zipimporter); + Py_DECREF(zipimporter); + if (err) + goto error; + if (Py_VerboseFlag) + PySys_WriteStderr( + "# installed zipimport hook\n"); + } + } + Py_DECREF(path_hooks); +} + +void +_PyImport_Fini(void) +{ + Py_XDECREF(extensions); + extensions = NULL; + PyMem_DEL(_PyImport_Filetab); + _PyImport_Filetab = NULL; +} + + +/* Locking primitives to prevent parallel imports of the same module + in different threads to return with a partially loaded module. + These calls are serialized by the global interpreter lock. */ + +#ifdef WITH_THREAD + +#include "pythread.h" + +static PyThread_type_lock import_lock = 0; +static long import_lock_thread = -1; +static int import_lock_level = 0; + +void +_PyImport_AcquireLock(void) +{ + long me = PyThread_get_thread_ident(); + if (me == -1) + return; /* Too bad */ + if (import_lock == NULL) { + import_lock = PyThread_allocate_lock(); + if (import_lock == NULL) + return; /* Nothing much we can do. */ + } + if (import_lock_thread == me) { + import_lock_level++; + return; + } + if (import_lock_thread != -1 || !PyThread_acquire_lock(import_lock, 0)) + { + PyThreadState *tstate = PyEval_SaveThread(); + PyThread_acquire_lock(import_lock, 1); + PyEval_RestoreThread(tstate); + } + import_lock_thread = me; + import_lock_level = 1; +} + +int +_PyImport_ReleaseLock(void) +{ + long me = PyThread_get_thread_ident(); + if (me == -1 || import_lock == NULL) + return 0; /* Too bad */ + if (import_lock_thread != me) + return -1; + import_lock_level--; + if (import_lock_level == 0) { + import_lock_thread = -1; + PyThread_release_lock(import_lock); + } + return 1; +} + +/* This function is called from PyOS_AfterFork to ensure that newly + created child processes do not share locks with the parent. + We now acquire the import lock around fork() calls but on some platforms + (Solaris 9 and earlier? see isue7242) that still left us with problems. */ + +void +_PyImport_ReInitLock(void) +{ + if (import_lock != NULL) { + import_lock = PyThread_allocate_lock(); + if (import_lock == NULL) { + Py_FatalError("PyImport_ReInitLock failed to create a new lock"); + } + } + import_lock_thread = -1; + import_lock_level = 0; +} + +#endif + +static PyObject * +imp_lock_held(PyObject *self, PyObject *noargs) +{ +#ifdef WITH_THREAD + return PyBool_FromLong(import_lock_thread != -1); +#else + return PyBool_FromLong(0); +#endif +} + +static PyObject * +imp_acquire_lock(PyObject *self, PyObject *noargs) +{ +#ifdef WITH_THREAD + _PyImport_AcquireLock(); +#endif + Py_INCREF(Py_None); + return Py_None; +} + +static PyObject * +imp_release_lock(PyObject *self, PyObject *noargs) +{ +#ifdef WITH_THREAD + if (_PyImport_ReleaseLock() < 0) { + PyErr_SetString(PyExc_RuntimeError, + "not holding the import lock"); + return NULL; + } +#endif + Py_INCREF(Py_None); + return Py_None; +} + +static void +imp_modules_reloading_clear(void) +{ + PyInterpreterState *interp = PyThreadState_Get()->interp; + if (interp->modules_reloading != NULL) + PyDict_Clear(interp->modules_reloading); +} + +/* Helper for sys */ + +PyObject * +PyImport_GetModuleDict(void) +{ + PyInterpreterState *interp = PyThreadState_GET()->interp; + if (interp->modules == NULL) + Py_FatalError("PyImport_GetModuleDict: no module dictionary!"); + return interp->modules; +} + + +/* List of names to clear in sys */ +static char* sys_deletes[] = { + "path", "argv", "ps1", "ps2", "exitfunc", + "exc_type", "exc_value", "exc_traceback", + "last_type", "last_value", "last_traceback", + "path_hooks", "path_importer_cache", "meta_path", + /* misc stuff */ + "flags", "float_info", + NULL +}; + +static char* sys_files[] = { + "stdin", "__stdin__", + "stdout", "__stdout__", + "stderr", "__stderr__", + NULL +}; + + +/* Un-initialize things, as good as we can */ + +void +PyImport_Cleanup(void) +{ + Py_ssize_t pos, ndone; + char *name; + PyObject *key, *value, *dict; + PyInterpreterState *interp = PyThreadState_GET()->interp; + PyObject *modules = interp->modules; + + if (modules == NULL) + return; /* Already done */ + + /* Delete some special variables first. These are common + places where user values hide and people complain when their + destructors fail. Since the modules containing them are + deleted *last* of all, they would come too late in the normal + destruction order. Sigh. */ + + value = PyDict_GetItemString(modules, "__builtin__"); + if (value != NULL && PyModule_Check(value)) { + dict = PyModule_GetDict(value); + if (Py_VerboseFlag) + PySys_WriteStderr("# clear __builtin__._\n"); + PyDict_SetItemString(dict, "_", Py_None); + } + value = PyDict_GetItemString(modules, "sys"); + if (value != NULL && PyModule_Check(value)) { + char **p; + PyObject *v; + dict = PyModule_GetDict(value); + for (p = sys_deletes; *p != NULL; p++) { + if (Py_VerboseFlag) + PySys_WriteStderr("# clear sys.%s\n", *p); + PyDict_SetItemString(dict, *p, Py_None); + } + for (p = sys_files; *p != NULL; p+=2) { + if (Py_VerboseFlag) + PySys_WriteStderr("# restore sys.%s\n", *p); + v = PyDict_GetItemString(dict, *(p+1)); + if (v == NULL) + v = Py_None; + PyDict_SetItemString(dict, *p, v); + } + } + + /* First, delete __main__ */ + value = PyDict_GetItemString(modules, "__main__"); + if (value != NULL && PyModule_Check(value)) { + if (Py_VerboseFlag) + PySys_WriteStderr("# cleanup __main__\n"); + _PyModule_Clear(value); + PyDict_SetItemString(modules, "__main__", Py_None); + } + + /* The special treatment of __builtin__ here is because even + when it's not referenced as a module, its dictionary is + referenced by almost every module's __builtins__. Since + deleting a module clears its dictionary (even if there are + references left to it), we need to delete the __builtin__ + module last. Likewise, we don't delete sys until the very + end because it is implicitly referenced (e.g. by print). + + Also note that we 'delete' modules by replacing their entry + in the modules dict with None, rather than really deleting + them; this avoids a rehash of the modules dictionary and + also marks them as "non existent" so they won't be + re-imported. */ + + /* Next, repeatedly delete modules with a reference count of + one (skipping __builtin__ and sys) and delete them */ + do { + ndone = 0; + pos = 0; + while (PyDict_Next(modules, &pos, &key, &value)) { + if (value->ob_refcnt != 1) + continue; + if (PyString_Check(key) && PyModule_Check(value)) { + name = PyString_AS_STRING(key); + if (strcmp(name, "__builtin__") == 0) + continue; + if (strcmp(name, "sys") == 0) + continue; + if (Py_VerboseFlag) + PySys_WriteStderr( + "# cleanup[1] %s\n", name); + _PyModule_Clear(value); + PyDict_SetItem(modules, key, Py_None); + ndone++; + } + } + } while (ndone > 0); + + /* Next, delete all modules (still skipping __builtin__ and sys) */ + pos = 0; + while (PyDict_Next(modules, &pos, &key, &value)) { + if (PyString_Check(key) && PyModule_Check(value)) { + name = PyString_AS_STRING(key); + if (strcmp(name, "__builtin__") == 0) + continue; + if (strcmp(name, "sys") == 0) + continue; + if (Py_VerboseFlag) + PySys_WriteStderr("# cleanup[2] %s\n", name); + _PyModule_Clear(value); + PyDict_SetItem(modules, key, Py_None); + } + } + + /* Next, delete sys and __builtin__ (in that order) */ + value = PyDict_GetItemString(modules, "sys"); + if (value != NULL && PyModule_Check(value)) { + if (Py_VerboseFlag) + PySys_WriteStderr("# cleanup sys\n"); + _PyModule_Clear(value); + PyDict_SetItemString(modules, "sys", Py_None); + } + value = PyDict_GetItemString(modules, "__builtin__"); + if (value != NULL && PyModule_Check(value)) { + if (Py_VerboseFlag) + PySys_WriteStderr("# cleanup __builtin__\n"); + _PyModule_Clear(value); + PyDict_SetItemString(modules, "__builtin__", Py_None); + } + + /* Finally, clear and delete the modules directory */ + PyDict_Clear(modules); + interp->modules = NULL; + Py_DECREF(modules); + Py_CLEAR(interp->modules_reloading); +} + + +/* Helper for pythonrun.c -- return magic number */ + +long +PyImport_GetMagicNumber(void) +{ + return pyc_magic; +} + + +/* Magic for extension modules (built-in as well as dynamically + loaded). To prevent initializing an extension module more than + once, we keep a static dictionary 'extensions' keyed by module name + (for built-in modules) or by filename (for dynamically loaded + modules), containing these modules. A copy of the module's + dictionary is stored by calling _PyImport_FixupExtension() + immediately after the module initialization function succeeds. A + copy can be retrieved from there by calling + _PyImport_FindExtension(). */ + +PyObject * +_PyImport_FixupExtension(char *name, char *filename) +{ + PyObject *modules, *mod, *dict, *copy; + if (extensions == NULL) { + extensions = PyDict_New(); + if (extensions == NULL) + return NULL; + } + modules = PyImport_GetModuleDict(); + mod = PyDict_GetItemString(modules, name); + if (mod == NULL || !PyModule_Check(mod)) { + PyErr_Format(PyExc_SystemError, + "_PyImport_FixupExtension: module %.200s not loaded", name); + return NULL; + } + dict = PyModule_GetDict(mod); + if (dict == NULL) + return NULL; + copy = PyDict_Copy(dict); + if (copy == NULL) + return NULL; + PyDict_SetItemString(extensions, filename, copy); + Py_DECREF(copy); + return copy; +} + +PyObject * +_PyImport_FindExtension(char *name, char *filename) +{ + PyObject *dict, *mod, *mdict; + if (extensions == NULL) + return NULL; + dict = PyDict_GetItemString(extensions, filename); + if (dict == NULL) + return NULL; + mod = PyImport_AddModule(name); + if (mod == NULL) + return NULL; + mdict = PyModule_GetDict(mod); + if (mdict == NULL) + return NULL; + if (PyDict_Update(mdict, dict)) + return NULL; + if (Py_VerboseFlag) + PySys_WriteStderr("import %s # previously loaded (%s)\n", + name, filename); + return mod; +} + + +/* Get the module object corresponding to a module name. + First check the modules dictionary if there's one there, + if not, create a new one and insert it in the modules dictionary. + Because the former action is most common, THIS DOES NOT RETURN A + 'NEW' REFERENCE! */ + +PyObject * +PyImport_AddModule(const char *name) +{ + PyObject *modules = PyImport_GetModuleDict(); + PyObject *m; + + if ((m = PyDict_GetItemString(modules, name)) != NULL && + PyModule_Check(m)) + return m; + m = PyModule_New(name); + if (m == NULL) + return NULL; + if (PyDict_SetItemString(modules, name, m) != 0) { + Py_DECREF(m); + return NULL; + } + Py_DECREF(m); /* Yes, it still exists, in modules! */ + + return m; +} + +/* Remove name from sys.modules, if it's there. */ +static void +remove_module(const char *name) +{ + PyObject *modules = PyImport_GetModuleDict(); + if (PyDict_GetItemString(modules, name) == NULL) + return; + if (PyDict_DelItemString(modules, name) < 0) + Py_FatalError("import: deleting existing key in" + "sys.modules failed"); +} + +/* Execute a code object in a module and return the module object + * WITH INCREMENTED REFERENCE COUNT. If an error occurs, name is + * removed from sys.modules, to avoid leaving damaged module objects + * in sys.modules. The caller may wish to restore the original + * module object (if any) in this case; PyImport_ReloadModule is an + * example. + */ +PyObject * +PyImport_ExecCodeModule(char *name, PyObject *co) +{ + return PyImport_ExecCodeModuleEx(name, co, (char *)NULL); +} + +PyObject * +PyImport_ExecCodeModuleEx(char *name, PyObject *co, char *pathname) +{ + PyObject *modules = PyImport_GetModuleDict(); + PyObject *m, *d, *v; + + m = PyImport_AddModule(name); + if (m == NULL) + return NULL; + /* If the module is being reloaded, we get the old module back + and re-use its dict to exec the new code. */ + d = PyModule_GetDict(m); + if (PyDict_GetItemString(d, "__builtins__") == NULL) { + if (PyDict_SetItemString(d, "__builtins__", + PyEval_GetBuiltins()) != 0) + goto error; + } + /* Remember the filename as the __file__ attribute */ + v = NULL; + if (pathname != NULL) { + v = PyString_FromString(pathname); + if (v == NULL) + PyErr_Clear(); + } + if (v == NULL) { + v = ((PyCodeObject *)co)->co_filename; + Py_INCREF(v); + } + if (PyDict_SetItemString(d, "__file__", v) != 0) + PyErr_Clear(); /* Not important enough to report */ + Py_DECREF(v); + + v = PyEval_EvalCode((PyCodeObject *)co, d, d); + if (v == NULL) + goto error; + Py_DECREF(v); + + if ((m = PyDict_GetItemString(modules, name)) == NULL) { + PyErr_Format(PyExc_ImportError, + "Loaded module %.200s not found in sys.modules", + name); + return NULL; + } + + Py_INCREF(m); + + return m; + + error: + remove_module(name); + return NULL; +} + + +/* Given a pathname for a Python source file, fill a buffer with the + pathname for the corresponding compiled file. Return the pathname + for the compiled file, or NULL if there's no space in the buffer. + Doesn't set an exception. */ + +static char * +make_compiled_pathname(char *pathname, char *buf, size_t buflen) +{ + size_t len = strlen(pathname); + if (len+2 > buflen) + return NULL; + +#ifdef MS_WINDOWS + /* Treat .pyw as if it were .py. The case of ".pyw" must match + that used in _PyImport_StandardFiletab. */ + if (len >= 4 && strcmp(&pathname[len-4], ".pyw") == 0) + --len; /* pretend 'w' isn't there */ +#endif + memcpy(buf, pathname, len); + buf[len] = Py_OptimizeFlag ? 'o' : 'c'; + buf[len+1] = '\0'; + + return buf; +} + + +/* Given a pathname for a Python source file, its time of last + modification, and a pathname for a compiled file, check whether the + compiled file represents the same version of the source. If so, + return a FILE pointer for the compiled file, positioned just after + the header; if not, return NULL. + Doesn't set an exception. */ + +static FILE * +check_compiled_module(char *pathname, time_t mtime, char *cpathname) +{ + FILE *fp; + long magic; + long pyc_mtime; + + fp = fopen(cpathname, "rb"); + if (fp == NULL) + return NULL; + magic = PyMarshal_ReadLongFromFile(fp); + if (magic != pyc_magic) { + if (Py_VerboseFlag) + PySys_WriteStderr("# %s has bad magic\n", cpathname); + fclose(fp); + return NULL; + } + pyc_mtime = PyMarshal_ReadLongFromFile(fp); + if (pyc_mtime != mtime) { + if (Py_VerboseFlag) + PySys_WriteStderr("# %s has bad mtime\n", cpathname); + fclose(fp); + return NULL; + } + if (Py_VerboseFlag) + PySys_WriteStderr("# %s matches %s\n", cpathname, pathname); + return fp; +} + + +/* Read a code object from a file and check it for validity */ + +static PyCodeObject * +read_compiled_module(char *cpathname, FILE *fp) +{ + PyObject *co; + + co = PyMarshal_ReadLastObjectFromFile(fp); + if (co == NULL) + return NULL; + if (!PyCode_Check(co)) { + PyErr_Format(PyExc_ImportError, + "Non-code object in %.200s", cpathname); + Py_DECREF(co); + return NULL; + } + return (PyCodeObject *)co; +} + + +/* Load a module from a compiled file, execute it, and return its + module object WITH INCREMENTED REFERENCE COUNT */ + +static PyObject * +load_compiled_module(char *name, char *cpathname, FILE *fp) +{ + long magic; + PyCodeObject *co; + PyObject *m; + + magic = PyMarshal_ReadLongFromFile(fp); + if (magic != pyc_magic) { + PyErr_Format(PyExc_ImportError, + "Bad magic number in %.200s", cpathname); + return NULL; + } + (void) PyMarshal_ReadLongFromFile(fp); + co = read_compiled_module(cpathname, fp); + if (co == NULL) + return NULL; + if (Py_VerboseFlag) + PySys_WriteStderr("import %s # precompiled from %s\n", + name, cpathname); + m = PyImport_ExecCodeModuleEx(name, (PyObject *)co, cpathname); + Py_DECREF(co); + + return m; +} + +/* Parse a source file and return the corresponding code object */ + +static PyCodeObject * +parse_source_module(const char *pathname, FILE *fp) +{ + PyCodeObject *co = NULL; + mod_ty mod; + PyCompilerFlags flags; + PyArena *arena = PyArena_New(); + if (arena == NULL) + return NULL; + + flags.cf_flags = 0; + + mod = PyParser_ASTFromFile(fp, pathname, Py_file_input, 0, 0, &flags, + NULL, arena); + if (mod) { + co = PyAST_Compile(mod, pathname, NULL, arena); + } + PyArena_Free(arena); + return co; +} + + +/* Helper to open a bytecode file for writing in exclusive mode */ + +static FILE * +open_exclusive(char *filename, mode_t mode) +{ +#if defined(O_EXCL)&&defined(O_CREAT)&&defined(O_WRONLY)&&defined(O_TRUNC) + /* Use O_EXCL to avoid a race condition when another process tries to + write the same file. When that happens, our open() call fails, + which is just fine (since it's only a cache). + XXX If the file exists and is writable but the directory is not + writable, the file will never be written. Oh well. + */ + int fd; + (void) unlink(filename); + fd = open(filename, O_EXCL|O_CREAT|O_WRONLY|O_TRUNC +#ifdef O_BINARY + |O_BINARY /* necessary for Windows */ +#endif +#ifdef __VMS + , mode, "ctxt=bin", "shr=nil" +#else + , mode +#endif + ); + if (fd < 0) + return NULL; + return fdopen(fd, "wb"); +#else + /* Best we can do -- on Windows this can't happen anyway */ + return fopen(filename, "wb"); +#endif +} + + +/* Write a compiled module to a file, placing the time of last + modification of its source into the header. + Errors are ignored, if a write error occurs an attempt is made to + remove the file. */ + +static void +write_compiled_module(PyCodeObject *co, char *cpathname, struct stat *srcstat, time_t mtime) +{ + FILE *fp; +#ifdef MS_WINDOWS /* since Windows uses different permissions */ + mode_t mode = srcstat->st_mode & ~S_IEXEC; + /* Issue #6074: We ensure user write access, so we can delete it later + * when the source file changes. (On POSIX, this only requires write + * access to the directory, on Windows, we need write access to the file + * as well) + */ + mode |= _S_IWRITE; +#else + mode_t mode = srcstat->st_mode & ~S_IXUSR & ~S_IXGRP & ~S_IXOTH; +#endif + + fp = open_exclusive(cpathname, mode); + if (fp == NULL) { + if (Py_VerboseFlag) + PySys_WriteStderr( + "# can't create %s\n", cpathname); + return; + } + PyMarshal_WriteLongToFile(pyc_magic, fp, Py_MARSHAL_VERSION); + /* First write a 0 for mtime */ + PyMarshal_WriteLongToFile(0L, fp, Py_MARSHAL_VERSION); + PyMarshal_WriteObjectToFile((PyObject *)co, fp, Py_MARSHAL_VERSION); + if (fflush(fp) != 0 || ferror(fp)) { + if (Py_VerboseFlag) + PySys_WriteStderr("# can't write %s\n", cpathname); + /* Don't keep partial file */ + fclose(fp); + (void) unlink(cpathname); + return; + } + /* Now write the true mtime (as a 32-bit field) */ + fseek(fp, 4L, 0); + assert(mtime <= 0xFFFFFFFF); + PyMarshal_WriteLongToFile((long)mtime, fp, Py_MARSHAL_VERSION); + fflush(fp); + fclose(fp); + if (Py_VerboseFlag) + PySys_WriteStderr("# wrote %s\n", cpathname); +} + +static void +update_code_filenames(PyCodeObject *co, PyObject *oldname, PyObject *newname) +{ + PyObject *constants, *tmp; + Py_ssize_t i, n; + + if (!_PyString_Eq(co->co_filename, oldname)) + return; + + tmp = co->co_filename; + co->co_filename = newname; + Py_INCREF(co->co_filename); + Py_DECREF(tmp); + + constants = co->co_consts; + n = PyTuple_GET_SIZE(constants); + for (i = 0; i < n; i++) { + tmp = PyTuple_GET_ITEM(constants, i); + if (PyCode_Check(tmp)) + update_code_filenames((PyCodeObject *)tmp, + oldname, newname); + } +} + +static int +update_compiled_module(PyCodeObject *co, char *pathname) +{ + PyObject *oldname, *newname; + + if (strcmp(PyString_AsString(co->co_filename), pathname) == 0) + return 0; + + newname = PyString_FromString(pathname); + if (newname == NULL) + return -1; + + oldname = co->co_filename; + Py_INCREF(oldname); + update_code_filenames(co, oldname, newname); + Py_DECREF(oldname); + Py_DECREF(newname); + return 1; +} + +#ifdef MS_WINDOWS + +/* Seconds between 1.1.1601 and 1.1.1970 */ +static __int64 secs_between_epochs = 11644473600; + +/* Get mtime from file pointer. */ + +static time_t +win32_mtime(FILE *fp, char *pathname) +{ + __int64 filetime; + HANDLE fh; + BY_HANDLE_FILE_INFORMATION file_information; + + fh = (HANDLE)_get_osfhandle(fileno(fp)); + if (fh == INVALID_HANDLE_VALUE || + !GetFileInformationByHandle(fh, &file_information)) { + PyErr_Format(PyExc_RuntimeError, + "unable to get file status from '%s'", + pathname); + return -1; + } + /* filetime represents the number of 100ns intervals since + 1.1.1601 (UTC). Convert to seconds since 1.1.1970 (UTC). */ + filetime = (__int64)file_information.ftLastWriteTime.dwHighDateTime << 32 | + file_information.ftLastWriteTime.dwLowDateTime; + return filetime / 10000000 - secs_between_epochs; +} + +#endif /* #ifdef MS_WINDOWS */ + + +/* Load a source module from a given file and return its module + object WITH INCREMENTED REFERENCE COUNT. If there's a matching + byte-compiled file, use that instead. */ + +static PyObject * +load_source_module(char *name, char *pathname, FILE *fp) +{ + struct stat st; + FILE *fpc; + char *buf; + char *cpathname; + PyCodeObject *co = NULL; + PyObject *m; + time_t mtime; + + if (fstat(fileno(fp), &st) != 0) { + PyErr_Format(PyExc_RuntimeError, + "unable to get file status from '%s'", + pathname); + return NULL; + } + +#ifdef MS_WINDOWS + mtime = win32_mtime(fp, pathname); + if (mtime == (time_t)-1 && PyErr_Occurred()) + return NULL; +#else + mtime = st.st_mtime; +#endif + if (sizeof mtime > 4) { + /* Python's .pyc timestamp handling presumes that the timestamp fits + in 4 bytes. Since the code only does an equality comparison, + ordering is not important and we can safely ignore the higher bits + (collisions are extremely unlikely). + */ + mtime &= 0xFFFFFFFF; + } + buf = PyMem_MALLOC(MAXPATHLEN+1); + if (buf == NULL) { + return PyErr_NoMemory(); + } + cpathname = make_compiled_pathname(pathname, buf, + (size_t)MAXPATHLEN + 1); + if (cpathname != NULL && + (fpc = check_compiled_module(pathname, mtime, cpathname))) { + co = read_compiled_module(cpathname, fpc); + fclose(fpc); + if (co == NULL) + goto error_exit; + if (update_compiled_module(co, pathname) < 0) + goto error_exit; + if (Py_VerboseFlag) + PySys_WriteStderr("import %s # precompiled from %s\n", + name, cpathname); + pathname = cpathname; + } + else { + co = parse_source_module(pathname, fp); + if (co == NULL) + goto error_exit; + if (Py_VerboseFlag) + PySys_WriteStderr("import %s # from %s\n", + name, pathname); + if (cpathname) { + PyObject *ro = PySys_GetObject("dont_write_bytecode"); + int b = (ro == NULL) ? 0 : PyObject_IsTrue(ro); + if (b < 0) + goto error_exit; + if (!b) + write_compiled_module(co, cpathname, &st, mtime); + } + } + m = PyImport_ExecCodeModuleEx(name, (PyObject *)co, pathname); + Py_DECREF(co); + + PyMem_FREE(buf); + return m; + +error_exit: + Py_XDECREF(co); + PyMem_FREE(buf); + return NULL; +} + + +/* Forward */ +static PyObject *load_module(char *, FILE *, char *, int, PyObject *); +static struct filedescr *find_module(char *, char *, PyObject *, + char *, size_t, FILE **, PyObject **); +static struct _frozen *find_frozen(char *name); + +/* Load a package and return its module object WITH INCREMENTED + REFERENCE COUNT */ + +static PyObject * +load_package(char *name, char *pathname) +{ + PyObject *m, *d; + PyObject *file = NULL; + PyObject *path = NULL; + int err; + char *buf = NULL; + FILE *fp = NULL; + struct filedescr *fdp; + + m = PyImport_AddModule(name); + if (m == NULL) + return NULL; + if (Py_VerboseFlag) + PySys_WriteStderr("import %s # directory %s\n", + name, pathname); + d = PyModule_GetDict(m); + file = PyString_FromString(pathname); + if (file == NULL) + goto error; + path = Py_BuildValue("[O]", file); + if (path == NULL) + goto error; + err = PyDict_SetItemString(d, "__file__", file); + if (err == 0) + err = PyDict_SetItemString(d, "__path__", path); + if (err != 0) + goto error; + buf = PyMem_MALLOC(MAXPATHLEN+1); + if (buf == NULL) { + PyErr_NoMemory(); + goto error; + } + buf[0] = '\0'; + fdp = find_module(name, "__init__", path, buf, MAXPATHLEN+1, &fp, NULL); + if (fdp == NULL) { + if (PyErr_ExceptionMatches(PyExc_ImportError)) { + PyErr_Clear(); + Py_INCREF(m); + } + else + m = NULL; + goto cleanup; + } + m = load_module(name, fp, buf, fdp->type, NULL); + if (fp != NULL) + fclose(fp); + goto cleanup; + + error: + m = NULL; + cleanup: + if (buf) + PyMem_FREE(buf); + Py_XDECREF(path); + Py_XDECREF(file); + return m; +} + + +/* Helper to test for built-in module */ + +static int +is_builtin(char *name) +{ + int i; + for (i = 0; PyImport_Inittab[i].name != NULL; i++) { + if (strcmp(name, PyImport_Inittab[i].name) == 0) { + if (PyImport_Inittab[i].initfunc == NULL) + return -1; + else + return 1; + } + } + return 0; +} + + +/* Return an importer object for a sys.path/pkg.__path__ item 'p', + possibly by fetching it from the path_importer_cache dict. If it + wasn't yet cached, traverse path_hooks until a hook is found + that can handle the path item. Return None if no hook could; + this tells our caller it should fall back to the builtin + import mechanism. Cache the result in path_importer_cache. + Returns a borrowed reference. */ + +static PyObject * +get_path_importer(PyObject *path_importer_cache, PyObject *path_hooks, + PyObject *p) +{ + PyObject *importer; + Py_ssize_t j, nhooks; + + /* These conditions are the caller's responsibility: */ + assert(PyList_Check(path_hooks)); + assert(PyDict_Check(path_importer_cache)); + + nhooks = PyList_Size(path_hooks); + if (nhooks < 0) + return NULL; /* Shouldn't happen */ + + importer = PyDict_GetItem(path_importer_cache, p); + if (importer != NULL) + return importer; + + /* set path_importer_cache[p] to None to avoid recursion */ + if (PyDict_SetItem(path_importer_cache, p, Py_None) != 0) + return NULL; + + for (j = 0; j < nhooks; j++) { + PyObject *hook = PyList_GetItem(path_hooks, j); + if (hook == NULL) + return NULL; + importer = PyObject_CallFunctionObjArgs(hook, p, NULL); + if (importer != NULL) + break; + + if (!PyErr_ExceptionMatches(PyExc_ImportError)) { + return NULL; + } + PyErr_Clear(); + } + if (importer == NULL) { + importer = PyObject_CallFunctionObjArgs( + (PyObject *)&PyNullImporter_Type, p, NULL + ); + if (importer == NULL) { + if (PyErr_ExceptionMatches(PyExc_ImportError)) { + PyErr_Clear(); + return Py_None; + } + } + } + if (importer != NULL) { + int err = PyDict_SetItem(path_importer_cache, p, importer); + Py_DECREF(importer); + if (err != 0) + return NULL; + } + return importer; +} + +PyAPI_FUNC(PyObject *) +PyImport_GetImporter(PyObject *path) { + PyObject *importer=NULL, *path_importer_cache=NULL, *path_hooks=NULL; + + if ((path_importer_cache = PySys_GetObject("path_importer_cache"))) { + if ((path_hooks = PySys_GetObject("path_hooks"))) { + importer = get_path_importer(path_importer_cache, + path_hooks, path); + } + } + Py_XINCREF(importer); /* get_path_importer returns a borrowed reference */ + return importer; +} + +/* Search the path (default sys.path) for a module. Return the + corresponding filedescr struct, and (via return arguments) the + pathname and an open file. Return NULL if the module is not found. */ + +#ifdef MS_COREDLL +extern FILE *PyWin_FindRegisteredModule(const char *, struct filedescr **, + char *, Py_ssize_t); +#endif + +static int case_ok(char *, Py_ssize_t, Py_ssize_t, char *); +static int find_init_module(char *); /* Forward */ +static struct filedescr importhookdescr = {"", "", IMP_HOOK}; + +static struct filedescr * +find_module(char *fullname, char *subname, PyObject *path, char *buf, + size_t buflen, FILE **p_fp, PyObject **p_loader) +{ + Py_ssize_t i, npath; + size_t len, namelen; + struct filedescr *fdp = NULL; + char *filemode; + FILE *fp = NULL; + PyObject *path_hooks, *path_importer_cache; + static struct filedescr fd_frozen = {"", "", PY_FROZEN}; + static struct filedescr fd_builtin = {"", "", C_BUILTIN}; + static struct filedescr fd_package = {"", "", PKG_DIRECTORY}; + char *name; +#if defined(PYOS_OS2) + size_t saved_len; + size_t saved_namelen; + char *saved_buf = NULL; +#endif + if (p_loader != NULL) + *p_loader = NULL; + + if (strlen(subname) > MAXPATHLEN) { + PyErr_SetString(PyExc_OverflowError, + "module name is too long"); + return NULL; + } + name = PyMem_MALLOC(MAXPATHLEN+1); + if (name == NULL) { + PyErr_NoMemory(); + return NULL; + } + strcpy(name, subname); + + /* sys.meta_path import hook */ + if (p_loader != NULL) { + PyObject *meta_path; + + meta_path = PySys_GetObject("meta_path"); + if (meta_path == NULL || !PyList_Check(meta_path)) { + PyErr_SetString(PyExc_RuntimeError, + "sys.meta_path must be a list of " + "import hooks"); + goto error_exit; + } + Py_INCREF(meta_path); /* zap guard */ + npath = PyList_Size(meta_path); + for (i = 0; i < npath; i++) { + PyObject *loader; + PyObject *hook = PyList_GetItem(meta_path, i); + loader = PyObject_CallMethod(hook, "find_module", + "sO", fullname, + path != NULL ? + path : Py_None); + if (loader == NULL) { + Py_DECREF(meta_path); + goto error_exit; /* true error */ + } + if (loader != Py_None) { + /* a loader was found */ + *p_loader = loader; + Py_DECREF(meta_path); + PyMem_FREE(name); + return &importhookdescr; + } + Py_DECREF(loader); + } + Py_DECREF(meta_path); + } + + if (path != NULL && PyString_Check(path)) { + /* The only type of submodule allowed inside a "frozen" + package are other frozen modules or packages. */ + if (PyString_Size(path) + 1 + strlen(name) >= (size_t)buflen) { + PyErr_SetString(PyExc_ImportError, + "full frozen module name too long"); + goto error_exit; + } + strcpy(buf, PyString_AsString(path)); + strcat(buf, "."); + strcat(buf, name); + strcpy(name, buf); + if (find_frozen(name) != NULL) { + strcpy(buf, name); + PyMem_FREE(name); + return &fd_frozen; + } + PyErr_Format(PyExc_ImportError, + "No frozen submodule named %.200s", name); + goto error_exit; + } + if (path == NULL) { + if (is_builtin(name)) { + strcpy(buf, name); + PyMem_FREE(name); + return &fd_builtin; + } + if ((find_frozen(name)) != NULL) { + strcpy(buf, name); + PyMem_FREE(name); + return &fd_frozen; + } + +#ifdef MS_COREDLL + fp = PyWin_FindRegisteredModule(name, &fdp, buf, buflen); + if (fp != NULL) { + *p_fp = fp; + PyMem_FREE(name); + return fdp; + } +#endif + path = PySys_GetObject("path"); + } + if (path == NULL || !PyList_Check(path)) { + PyErr_SetString(PyExc_RuntimeError, + "sys.path must be a list of directory names"); + goto error_exit; + } + + path_hooks = PySys_GetObject("path_hooks"); + if (path_hooks == NULL || !PyList_Check(path_hooks)) { + PyErr_SetString(PyExc_RuntimeError, + "sys.path_hooks must be a list of " + "import hooks"); + goto error_exit; + } + path_importer_cache = PySys_GetObject("path_importer_cache"); + if (path_importer_cache == NULL || + !PyDict_Check(path_importer_cache)) { + PyErr_SetString(PyExc_RuntimeError, + "sys.path_importer_cache must be a dict"); + goto error_exit; + } + + npath = PyList_Size(path); + namelen = strlen(name); + for (i = 0; i < npath; i++) { + PyObject *copy = NULL; + PyObject *v = PyList_GetItem(path, i); + if (!v) + goto error_exit; +#ifdef Py_USING_UNICODE + if (PyUnicode_Check(v)) { + copy = PyUnicode_Encode(PyUnicode_AS_UNICODE(v), + PyUnicode_GET_SIZE(v), Py_FileSystemDefaultEncoding, NULL); + if (copy == NULL) + goto error_exit; + v = copy; + } + else +#endif + if (!PyString_Check(v)) + continue; + len = PyString_GET_SIZE(v); + if (len + 2 + namelen + MAXSUFFIXSIZE >= buflen) { + Py_XDECREF(copy); + continue; /* Too long */ + } + strcpy(buf, PyString_AS_STRING(v)); + if (strlen(buf) != len) { + Py_XDECREF(copy); + continue; /* v contains '\0' */ + } + + /* sys.path_hooks import hook */ + if (p_loader != NULL) { + PyObject *importer; + + importer = get_path_importer(path_importer_cache, + path_hooks, v); + if (importer == NULL) { + Py_XDECREF(copy); + goto error_exit; + } + /* Note: importer is a borrowed reference */ + if (importer != Py_None) { + PyObject *loader; + loader = PyObject_CallMethod(importer, + "find_module", + "s", fullname); + Py_XDECREF(copy); + if (loader == NULL) + goto error_exit; /* error */ + if (loader != Py_None) { + /* a loader was found */ + *p_loader = loader; + PyMem_FREE(name); + return &importhookdescr; + } + Py_DECREF(loader); + continue; + } + } + /* no hook was found, use builtin import */ + + if (len > 0 && buf[len-1] != SEP +#ifdef ALTSEP + && buf[len-1] != ALTSEP +#endif + ) + buf[len++] = SEP; + strcpy(buf+len, name); + len += namelen; + + /* Check for package import (buf holds a directory name, + and there's an __init__ module in that directory */ + if (isdir(buf) && /* it's an existing directory */ + case_ok(buf, len, namelen, name)) { /* case matches */ + if (find_init_module(buf)) { /* and has __init__.py */ + Py_XDECREF(copy); + PyMem_FREE(name); + return &fd_package; + } + else { + char warnstr[MAXPATHLEN+80]; + sprintf(warnstr, "Not importing directory " + "'%.*s': missing __init__.py", + MAXPATHLEN, buf); + if (PyErr_Warn(PyExc_ImportWarning, + warnstr)) { + Py_XDECREF(copy); + goto error_exit; + } + } + } +#if defined(PYOS_OS2) + /* take a snapshot of the module spec for restoration + * after the 8 character DLL hackery + */ + saved_buf = strdup(buf); + saved_len = len; + saved_namelen = namelen; +#endif /* PYOS_OS2 */ + for (fdp = _PyImport_Filetab; fdp->suffix != NULL; fdp++) { +#if defined(PYOS_OS2) && defined(HAVE_DYNAMIC_LOADING) + /* OS/2 limits DLLs to 8 character names (w/o + extension) + * so if the name is longer than that and its a + * dynamically loaded module we're going to try, + * truncate the name before trying + */ + if (strlen(subname) > 8) { + /* is this an attempt to load a C extension? */ + const struct filedescr *scan; + scan = _PyImport_DynLoadFiletab; + while (scan->suffix != NULL) { + if (!strcmp(scan->suffix, fdp->suffix)) + break; + else + scan++; + } + if (scan->suffix != NULL) { + /* yes, so truncate the name */ + namelen = 8; + len -= strlen(subname) - namelen; + buf[len] = '\0'; + } + } +#endif /* PYOS_OS2 */ + strcpy(buf+len, fdp->suffix); + if (Py_VerboseFlag > 1) + PySys_WriteStderr("# trying %s\n", buf); + filemode = fdp->mode; + if (filemode[0] == 'U') + filemode = "r" PY_STDIOTEXTMODE; + fp = fopen(buf, filemode); + if (fp != NULL) { + if (case_ok(buf, len, namelen, name)) + break; + else { /* continue search */ + fclose(fp); + fp = NULL; + } + } +#if defined(PYOS_OS2) + /* restore the saved snapshot */ + strcpy(buf, saved_buf); + len = saved_len; + namelen = saved_namelen; +#endif + } +#if defined(PYOS_OS2) + /* don't need/want the module name snapshot anymore */ + if (saved_buf) + { + free(saved_buf); + saved_buf = NULL; + } +#endif + Py_XDECREF(copy); + if (fp != NULL) + break; + } + if (fp == NULL) { + PyErr_Format(PyExc_ImportError, + "No module named %.200s", name); + goto error_exit; + } + *p_fp = fp; + PyMem_FREE(name); + return fdp; + +error_exit: + PyMem_FREE(name); + return NULL; +} + +/* Helpers for main.c + * Find the source file corresponding to a named module + */ +struct filedescr * +_PyImport_FindModule(const char *name, PyObject *path, char *buf, + size_t buflen, FILE **p_fp, PyObject **p_loader) +{ + return find_module((char *) name, (char *) name, path, + buf, buflen, p_fp, p_loader); +} + +PyAPI_FUNC(int) _PyImport_IsScript(struct filedescr * fd) +{ + return fd->type == PY_SOURCE || fd->type == PY_COMPILED; +} + +/* case_ok(char* buf, Py_ssize_t len, Py_ssize_t namelen, char* name) + * The arguments here are tricky, best shown by example: + * /a/b/c/d/e/f/g/h/i/j/k/some_long_module_name.py\0 + * ^ ^ ^ ^ + * |--------------------- buf ---------------------| + * |------------------- len ------------------| + * |------ name -------| + * |----- namelen -----| + * buf is the full path, but len only counts up to (& exclusive of) the + * extension. name is the module name, also exclusive of extension. + * + * We've already done a successful stat() or fopen() on buf, so know that + * there's some match, possibly case-insensitive. + * + * case_ok() is to return 1 if there's a case-sensitive match for + * name, else 0. case_ok() is also to return 1 if envar PYTHONCASEOK + * exists. + * + * case_ok() is used to implement case-sensitive import semantics even + * on platforms with case-insensitive filesystems. It's trivial to implement + * for case-sensitive filesystems. It's pretty much a cross-platform + * nightmare for systems with case-insensitive filesystems. + */ + +/* First we may need a pile of platform-specific header files; the sequence + * of #if's here should match the sequence in the body of case_ok(). + */ +#if defined(MS_WINDOWS) +#include + +#elif defined(DJGPP) +#include + +#elif (defined(__MACH__) && defined(__APPLE__) || defined(__CYGWIN__)) && defined(HAVE_DIRENT_H) +#include +#include + +#elif defined(PYOS_OS2) +#define INCL_DOS +#define INCL_DOSERRORS +#define INCL_NOPMAPI +#include + +#elif defined(RISCOS) +#include "oslib/osfscontrol.h" +#endif + +static int +case_ok(char *buf, Py_ssize_t len, Py_ssize_t namelen, char *name) +{ +/* Pick a platform-specific implementation; the sequence of #if's here should + * match the sequence just above. + */ + +/* MS_WINDOWS */ +#if defined(MS_WINDOWS) + WIN32_FIND_DATA data; + HANDLE h; + + if (Py_GETENV("PYTHONCASEOK") != NULL) + return 1; + + h = FindFirstFile(buf, &data); + if (h == INVALID_HANDLE_VALUE) { + PyErr_Format(PyExc_NameError, + "Can't find file for module %.100s\n(filename %.300s)", + name, buf); + return 0; + } + FindClose(h); + return strncmp(data.cFileName, name, namelen) == 0; + +/* DJGPP */ +#elif defined(DJGPP) + struct ffblk ffblk; + int done; + + if (Py_GETENV("PYTHONCASEOK") != NULL) + return 1; + + done = findfirst(buf, &ffblk, FA_ARCH|FA_RDONLY|FA_HIDDEN|FA_DIREC); + if (done) { + PyErr_Format(PyExc_NameError, + "Can't find file for module %.100s\n(filename %.300s)", + name, buf); + return 0; + } + return strncmp(ffblk.ff_name, name, namelen) == 0; + +/* new-fangled macintosh (macosx) or Cygwin */ +#elif (defined(__MACH__) && defined(__APPLE__) || defined(__CYGWIN__)) && defined(HAVE_DIRENT_H) + DIR *dirp; + struct dirent *dp; + char dirname[MAXPATHLEN + 1]; + const int dirlen = len - namelen - 1; /* don't want trailing SEP */ + + if (Py_GETENV("PYTHONCASEOK") != NULL) + return 1; + + /* Copy the dir component into dirname; substitute "." if empty */ + if (dirlen <= 0) { + dirname[0] = '.'; + dirname[1] = '\0'; + } + else { + assert(dirlen <= MAXPATHLEN); + memcpy(dirname, buf, dirlen); + dirname[dirlen] = '\0'; + } + /* Open the directory and search the entries for an exact match. */ + dirp = opendir(dirname); + if (dirp) { + char *nameWithExt = buf + len - namelen; + while ((dp = readdir(dirp)) != NULL) { + const int thislen = +#ifdef _DIRENT_HAVE_D_NAMELEN + dp->d_namlen; +#else + strlen(dp->d_name); +#endif + if (thislen >= namelen && + strcmp(dp->d_name, nameWithExt) == 0) { + (void)closedir(dirp); + return 1; /* Found */ + } + } + (void)closedir(dirp); + } + return 0 ; /* Not found */ + +/* RISC OS */ +#elif defined(RISCOS) + char canon[MAXPATHLEN+1]; /* buffer for the canonical form of the path */ + char buf2[MAXPATHLEN+2]; + char *nameWithExt = buf+len-namelen; + int canonlen; + os_error *e; + + if (Py_GETENV("PYTHONCASEOK") != NULL) + return 1; + + /* workaround: + append wildcard, otherwise case of filename wouldn't be touched */ + strcpy(buf2, buf); + strcat(buf2, "*"); + + e = xosfscontrol_canonicalise_path(buf2,canon,0,0,MAXPATHLEN+1,&canonlen); + canonlen = MAXPATHLEN+1-canonlen; + if (e || canonlen<=0 || canonlen>(MAXPATHLEN+1) ) + return 0; + if (strcmp(nameWithExt, canon+canonlen-strlen(nameWithExt))==0) + return 1; /* match */ + + return 0; + +/* OS/2 */ +#elif defined(PYOS_OS2) + HDIR hdir = 1; + ULONG srchcnt = 1; + FILEFINDBUF3 ffbuf; + APIRET rc; + + if (Py_GETENV("PYTHONCASEOK") != NULL) + return 1; + + rc = DosFindFirst(buf, + &hdir, + FILE_READONLY | FILE_HIDDEN | FILE_SYSTEM | FILE_DIRECTORY, + &ffbuf, sizeof(ffbuf), + &srchcnt, + FIL_STANDARD); + if (rc != NO_ERROR) + return 0; + return strncmp(ffbuf.achName, name, namelen) == 0; + +/* assuming it's a case-sensitive filesystem, so there's nothing to do! */ +#else + return 1; + +#endif +} + + +#ifdef HAVE_STAT +/* Helper to look for __init__.py or __init__.py[co] in potential package */ +static int +find_init_module(char *buf) +{ + const size_t save_len = strlen(buf); + size_t i = save_len; + char *pname; /* pointer to start of __init__ */ + struct stat statbuf; + +/* For calling case_ok(buf, len, namelen, name): + * /a/b/c/d/e/f/g/h/i/j/k/some_long_module_name.py\0 + * ^ ^ ^ ^ + * |--------------------- buf ---------------------| + * |------------------- len ------------------| + * |------ name -------| + * |----- namelen -----| + */ + if (save_len + 13 >= MAXPATHLEN) + return 0; + buf[i++] = SEP; + pname = buf + i; + strcpy(pname, "__init__.py"); + if (stat(buf, &statbuf) == 0) { + if (case_ok(buf, + save_len + 9, /* len("/__init__") */ + 8, /* len("__init__") */ + pname)) { + buf[save_len] = '\0'; + return 1; + } + } + i += strlen(pname); + strcpy(buf+i, Py_OptimizeFlag ? "o" : "c"); + if (stat(buf, &statbuf) == 0) { + if (case_ok(buf, + save_len + 9, /* len("/__init__") */ + 8, /* len("__init__") */ + pname)) { + buf[save_len] = '\0'; + return 1; + } + } + buf[save_len] = '\0'; + return 0; +} + +#else + +#ifdef RISCOS +static int +find_init_module(buf) + char *buf; +{ + int save_len = strlen(buf); + int i = save_len; + + if (save_len + 13 >= MAXPATHLEN) + return 0; + buf[i++] = SEP; + strcpy(buf+i, "__init__/py"); + if (isfile(buf)) { + buf[save_len] = '\0'; + return 1; + } + + if (Py_OptimizeFlag) + strcpy(buf+i, "o"); + else + strcpy(buf+i, "c"); + if (isfile(buf)) { + buf[save_len] = '\0'; + return 1; + } + buf[save_len] = '\0'; + return 0; +} +#endif /*RISCOS*/ + +#endif /* HAVE_STAT */ + + +static int init_builtin(char *); /* Forward */ + +/* Load an external module using the default search path and return + its module object WITH INCREMENTED REFERENCE COUNT */ + +static PyObject * +load_module(char *name, FILE *fp, char *pathname, int type, PyObject *loader) +{ + PyObject *modules; + PyObject *m; + int err; + + /* First check that there's an open file (if we need one) */ + switch (type) { + case PY_SOURCE: + case PY_COMPILED: + if (fp == NULL) { + PyErr_Format(PyExc_ValueError, + "file object required for import (type code %d)", + type); + return NULL; + } + } + + switch (type) { + + case PY_SOURCE: + m = load_source_module(name, pathname, fp); + break; + + case PY_COMPILED: + m = load_compiled_module(name, pathname, fp); + break; + +#ifdef HAVE_DYNAMIC_LOADING + case C_EXTENSION: + m = _PyImport_LoadDynamicModule(name, pathname, fp); + break; +#endif + + case PKG_DIRECTORY: + m = load_package(name, pathname); + break; + + case C_BUILTIN: + case PY_FROZEN: + if (pathname != NULL && pathname[0] != '\0') + name = pathname; + if (type == C_BUILTIN) + err = init_builtin(name); + else + err = PyImport_ImportFrozenModule(name); + if (err < 0) + return NULL; + if (err == 0) { + PyErr_Format(PyExc_ImportError, + "Purported %s module %.200s not found", + type == C_BUILTIN ? + "builtin" : "frozen", + name); + return NULL; + } + modules = PyImport_GetModuleDict(); + m = PyDict_GetItemString(modules, name); + if (m == NULL) { + PyErr_Format( + PyExc_ImportError, + "%s module %.200s not properly initialized", + type == C_BUILTIN ? + "builtin" : "frozen", + name); + return NULL; + } + Py_INCREF(m); + break; + + case IMP_HOOK: { + if (loader == NULL) { + PyErr_SetString(PyExc_ImportError, + "import hook without loader"); + return NULL; + } + m = PyObject_CallMethod(loader, "load_module", "s", name); + break; + } + + default: + PyErr_Format(PyExc_ImportError, + "Don't know how to import %.200s (type code %d)", + name, type); + m = NULL; + + } + + return m; +} + + +/* Initialize a built-in module. + Return 1 for success, 0 if the module is not found, and -1 with + an exception set if the initialization failed. */ + +static int +init_builtin(char *name) +{ + struct _inittab *p; + + if (_PyImport_FindExtension(name, name) != NULL) + return 1; + + for (p = PyImport_Inittab; p->name != NULL; p++) { + if (strcmp(name, p->name) == 0) { + if (p->initfunc == NULL) { + PyErr_Format(PyExc_ImportError, + "Cannot re-init internal module %.200s", + name); + return -1; + } + if (Py_VerboseFlag) + PySys_WriteStderr("import %s # builtin\n", name); + (*p->initfunc)(); + if (PyErr_Occurred()) + return -1; + if (_PyImport_FixupExtension(name, name) == NULL) + return -1; + return 1; + } + } + return 0; +} + + +/* Frozen modules */ + +static struct _frozen * +find_frozen(char *name) +{ + struct _frozen *p; + + for (p = PyImport_FrozenModules; ; p++) { + if (p->name == NULL) + return NULL; + if (strcmp(p->name, name) == 0) + break; + } + return p; +} + +static PyObject * +get_frozen_object(char *name) +{ + struct _frozen *p = find_frozen(name); + int size; + + if (p == NULL) { + PyErr_Format(PyExc_ImportError, + "No such frozen object named %.200s", + name); + return NULL; + } + if (p->code == NULL) { + PyErr_Format(PyExc_ImportError, + "Excluded frozen object named %.200s", + name); + return NULL; + } + size = p->size; + if (size < 0) + size = -size; + return PyMarshal_ReadObjectFromString((char *)p->code, size); +} + +/* Initialize a frozen module. + Return 1 for succes, 0 if the module is not found, and -1 with + an exception set if the initialization failed. + This function is also used from frozenmain.c */ + +int +PyImport_ImportFrozenModule(char *name) +{ + struct _frozen *p = find_frozen(name); + PyObject *co; + PyObject *m; + int ispackage; + int size; + + if (p == NULL) + return 0; + if (p->code == NULL) { + PyErr_Format(PyExc_ImportError, + "Excluded frozen object named %.200s", + name); + return -1; + } + size = p->size; + ispackage = (size < 0); + if (ispackage) + size = -size; + if (Py_VerboseFlag) + PySys_WriteStderr("import %s # frozen%s\n", + name, ispackage ? " package" : ""); + co = PyMarshal_ReadObjectFromString((char *)p->code, size); + if (co == NULL) + return -1; + if (!PyCode_Check(co)) { + PyErr_Format(PyExc_TypeError, + "frozen object %.200s is not a code object", + name); + goto err_return; + } + if (ispackage) { + /* Set __path__ to the package name */ + PyObject *d, *s; + int err; + m = PyImport_AddModule(name); + if (m == NULL) + goto err_return; + d = PyModule_GetDict(m); + s = PyString_InternFromString(name); + if (s == NULL) + goto err_return; + err = PyDict_SetItemString(d, "__path__", s); + Py_DECREF(s); + if (err != 0) + goto err_return; + } + m = PyImport_ExecCodeModuleEx(name, co, ""); + if (m == NULL) + goto err_return; + Py_DECREF(co); + Py_DECREF(m); + return 1; +err_return: + Py_DECREF(co); + return -1; +} + + +/* Import a module, either built-in, frozen, or external, and return + its module object WITH INCREMENTED REFERENCE COUNT */ + +PyObject * +PyImport_ImportModule(const char *name) +{ + PyObject *pname; + PyObject *result; + + pname = PyString_FromString(name); + if (pname == NULL) + return NULL; + result = PyImport_Import(pname); + Py_DECREF(pname); + return result; +} + +/* Import a module without blocking + * + * At first it tries to fetch the module from sys.modules. If the module was + * never loaded before it loads it with PyImport_ImportModule() unless another + * thread holds the import lock. In the latter case the function raises an + * ImportError instead of blocking. + * + * Returns the module object with incremented ref count. + */ +PyObject * +PyImport_ImportModuleNoBlock(const char *name) +{ + PyObject *result; + PyObject *modules; +#ifdef WITH_THREAD + long me; +#endif + + /* Try to get the module from sys.modules[name] */ + modules = PyImport_GetModuleDict(); + if (modules == NULL) + return NULL; + + result = PyDict_GetItemString(modules, name); + if (result != NULL) { + Py_INCREF(result); + return result; + } + else { + PyErr_Clear(); + } +#ifdef WITH_THREAD + /* check the import lock + * me might be -1 but I ignore the error here, the lock function + * takes care of the problem */ + me = PyThread_get_thread_ident(); + if (import_lock_thread == -1 || import_lock_thread == me) { + /* no thread or me is holding the lock */ + return PyImport_ImportModule(name); + } + else { + PyErr_Format(PyExc_ImportError, + "Failed to import %.200s because the import lock" + "is held by another thread.", + name); + return NULL; + } +#else + return PyImport_ImportModule(name); +#endif +} + +/* Forward declarations for helper routines */ +static PyObject *get_parent(PyObject *globals, char *buf, + Py_ssize_t *p_buflen, int level); +static PyObject *load_next(PyObject *mod, PyObject *altmod, + char **p_name, char *buf, Py_ssize_t *p_buflen); +static int mark_miss(char *name); +static int ensure_fromlist(PyObject *mod, PyObject *fromlist, + char *buf, Py_ssize_t buflen, int recursive); +static PyObject * import_submodule(PyObject *mod, char *name, char *fullname); + +/* The Magnum Opus of dotted-name import :-) */ + +static PyObject * +import_module_level(char *name, PyObject *globals, PyObject *locals, + PyObject *fromlist, int level) +{ + char *buf; + Py_ssize_t buflen = 0; + PyObject *parent, *head, *next, *tail; + + if (strchr(name, '/') != NULL +#ifdef MS_WINDOWS + || strchr(name, '\\') != NULL +#endif + ) { + PyErr_SetString(PyExc_ImportError, + "Import by filename is not supported."); + return NULL; + } + + buf = PyMem_MALLOC(MAXPATHLEN+1); + if (buf == NULL) { + return PyErr_NoMemory(); + } + parent = get_parent(globals, buf, &buflen, level); + if (parent == NULL) + goto error_exit; + + head = load_next(parent, level < 0 ? Py_None : parent, &name, buf, + &buflen); + if (head == NULL) + goto error_exit; + + tail = head; + Py_INCREF(tail); + while (name) { + next = load_next(tail, tail, &name, buf, &buflen); + Py_DECREF(tail); + if (next == NULL) { + Py_DECREF(head); + goto error_exit; + } + tail = next; + } + if (tail == Py_None) { + /* If tail is Py_None, both get_parent and load_next found + an empty module name: someone called __import__("") or + doctored faulty bytecode */ + Py_DECREF(tail); + Py_DECREF(head); + PyErr_SetString(PyExc_ValueError, + "Empty module name"); + goto error_exit; + } + + if (fromlist != NULL) { + int b = (fromlist == Py_None) ? 0 : PyObject_IsTrue(fromlist); + if (b < 0) { + Py_DECREF(tail); + Py_DECREF(head); + goto error_exit; + } + if (!b) + fromlist = NULL; + } + + if (fromlist == NULL) { + Py_DECREF(tail); + PyMem_FREE(buf); + return head; + } + + Py_DECREF(head); + if (!ensure_fromlist(tail, fromlist, buf, buflen, 0)) { + Py_DECREF(tail); + goto error_exit; + } + + PyMem_FREE(buf); + return tail; + +error_exit: + PyMem_FREE(buf); + return NULL; +} + +PyObject * +PyImport_ImportModuleLevel(char *name, PyObject *globals, PyObject *locals, + PyObject *fromlist, int level) +{ + PyObject *result; + _PyImport_AcquireLock(); + result = import_module_level(name, globals, locals, fromlist, level); + if (_PyImport_ReleaseLock() < 0) { + Py_XDECREF(result); + PyErr_SetString(PyExc_RuntimeError, + "not holding the import lock"); + return NULL; + } + return result; +} + +/* Return the package that an import is being performed in. If globals comes + from the module foo.bar.bat (not itself a package), this returns the + sys.modules entry for foo.bar. If globals is from a package's __init__.py, + the package's entry in sys.modules is returned, as a borrowed reference. + + The *name* of the returned package is returned in buf, with the length of + the name in *p_buflen. + + If globals doesn't come from a package or a module in a package, or a + corresponding entry is not found in sys.modules, Py_None is returned. +*/ +static PyObject * +get_parent(PyObject *globals, char *buf, Py_ssize_t *p_buflen, int level) +{ + static PyObject *namestr = NULL; + static PyObject *pathstr = NULL; + static PyObject *pkgstr = NULL; + PyObject *pkgname, *modname, *modpath, *modules, *parent; + int orig_level = level; + + if (globals == NULL || !PyDict_Check(globals) || !level) + return Py_None; + + if (namestr == NULL) { + namestr = PyString_InternFromString("__name__"); + if (namestr == NULL) + return NULL; + } + if (pathstr == NULL) { + pathstr = PyString_InternFromString("__path__"); + if (pathstr == NULL) + return NULL; + } + if (pkgstr == NULL) { + pkgstr = PyString_InternFromString("__package__"); + if (pkgstr == NULL) + return NULL; + } + + *buf = '\0'; + *p_buflen = 0; + pkgname = PyDict_GetItem(globals, pkgstr); + + if ((pkgname != NULL) && (pkgname != Py_None)) { + /* __package__ is set, so use it */ + Py_ssize_t len; + if (!PyString_Check(pkgname)) { + PyErr_SetString(PyExc_ValueError, + "__package__ set to non-string"); + return NULL; + } + len = PyString_GET_SIZE(pkgname); + if (len == 0) { + if (level > 0) { + PyErr_SetString(PyExc_ValueError, + "Attempted relative import in non-package"); + return NULL; + } + return Py_None; + } + if (len > MAXPATHLEN) { + PyErr_SetString(PyExc_ValueError, + "Package name too long"); + return NULL; + } + strcpy(buf, PyString_AS_STRING(pkgname)); + } else { + /* __package__ not set, so figure it out and set it */ + modname = PyDict_GetItem(globals, namestr); + if (modname == NULL || !PyString_Check(modname)) + return Py_None; + + modpath = PyDict_GetItem(globals, pathstr); + if (modpath != NULL) { + /* __path__ is set, so modname is already the package name */ + Py_ssize_t len = PyString_GET_SIZE(modname); + int error; + if (len > MAXPATHLEN) { + PyErr_SetString(PyExc_ValueError, + "Module name too long"); + return NULL; + } + strcpy(buf, PyString_AS_STRING(modname)); + error = PyDict_SetItem(globals, pkgstr, modname); + if (error) { + PyErr_SetString(PyExc_ValueError, + "Could not set __package__"); + return NULL; + } + } else { + /* Normal module, so work out the package name if any */ + char *start = PyString_AS_STRING(modname); + char *lastdot = strrchr(start, '.'); + size_t len; + int error; + if (lastdot == NULL && level > 0) { + PyErr_SetString(PyExc_ValueError, + "Attempted relative import in non-package"); + return NULL; + } + if (lastdot == NULL) { + error = PyDict_SetItem(globals, pkgstr, Py_None); + if (error) { + PyErr_SetString(PyExc_ValueError, + "Could not set __package__"); + return NULL; + } + return Py_None; + } + len = lastdot - start; + if (len >= MAXPATHLEN) { + PyErr_SetString(PyExc_ValueError, + "Module name too long"); + return NULL; + } + strncpy(buf, start, len); + buf[len] = '\0'; + pkgname = PyString_FromString(buf); + if (pkgname == NULL) { + return NULL; + } + error = PyDict_SetItem(globals, pkgstr, pkgname); + Py_DECREF(pkgname); + if (error) { + PyErr_SetString(PyExc_ValueError, + "Could not set __package__"); + return NULL; + } + } + } + while (--level > 0) { + char *dot = strrchr(buf, '.'); + if (dot == NULL) { + PyErr_SetString(PyExc_ValueError, + "Attempted relative import beyond " + "toplevel package"); + return NULL; + } + *dot = '\0'; + } + *p_buflen = strlen(buf); + + modules = PyImport_GetModuleDict(); + parent = PyDict_GetItemString(modules, buf); + if (parent == NULL) { + if (orig_level < 1) { + PyObject *err_msg = PyString_FromFormat( + "Parent module '%.200s' not found " + "while handling absolute import", buf); + if (err_msg == NULL) { + return NULL; + } + if (!PyErr_WarnEx(PyExc_RuntimeWarning, + PyString_AsString(err_msg), 1)) { + *buf = '\0'; + *p_buflen = 0; + parent = Py_None; + } + Py_DECREF(err_msg); + } else { + PyErr_Format(PyExc_SystemError, + "Parent module '%.200s' not loaded, " + "cannot perform relative import", buf); + } + } + return parent; + /* We expect, but can't guarantee, if parent != None, that: + - parent.__name__ == buf + - parent.__dict__ is globals + If this is violated... Who cares? */ +} + +/* altmod is either None or same as mod */ +static PyObject * +load_next(PyObject *mod, PyObject *altmod, char **p_name, char *buf, + Py_ssize_t *p_buflen) +{ + char *name = *p_name; + char *dot = strchr(name, '.'); + size_t len; + char *p; + PyObject *result; + + if (strlen(name) == 0) { + /* completely empty module name should only happen in + 'from . import' (or '__import__("")')*/ + Py_INCREF(mod); + *p_name = NULL; + return mod; + } + + if (dot == NULL) { + *p_name = NULL; + len = strlen(name); + } + else { + *p_name = dot+1; + len = dot-name; + } + if (len == 0) { + PyErr_SetString(PyExc_ValueError, + "Empty module name"); + return NULL; + } + + p = buf + *p_buflen; + if (p != buf) + *p++ = '.'; + if (p+len-buf >= MAXPATHLEN) { + PyErr_SetString(PyExc_ValueError, + "Module name too long"); + return NULL; + } + strncpy(p, name, len); + p[len] = '\0'; + *p_buflen = p+len-buf; + + result = import_submodule(mod, p, buf); + if (result == Py_None && altmod != mod) { + Py_DECREF(result); + /* Here, altmod must be None and mod must not be None */ + result = import_submodule(altmod, p, p); + if (result != NULL && result != Py_None) { + if (mark_miss(buf) != 0) { + Py_DECREF(result); + return NULL; + } + strncpy(buf, name, len); + buf[len] = '\0'; + *p_buflen = len; + } + } + if (result == NULL) + return NULL; + + if (result == Py_None) { + Py_DECREF(result); + PyErr_Format(PyExc_ImportError, + "No module named %.200s", name); + return NULL; + } + + return result; +} + +static int +mark_miss(char *name) +{ + PyObject *modules = PyImport_GetModuleDict(); + return PyDict_SetItemString(modules, name, Py_None); +} + +static int +ensure_fromlist(PyObject *mod, PyObject *fromlist, char *buf, Py_ssize_t buflen, + int recursive) +{ + int i; + + if (!PyObject_HasAttrString(mod, "__path__")) + return 1; + + for (i = 0; ; i++) { + PyObject *item = PySequence_GetItem(fromlist, i); + int hasit; + if (item == NULL) { + if (PyErr_ExceptionMatches(PyExc_IndexError)) { + PyErr_Clear(); + return 1; + } + return 0; + } + if (!PyString_Check(item)) { + PyErr_SetString(PyExc_TypeError, + "Item in ``from list'' not a string"); + Py_DECREF(item); + return 0; + } + if (PyString_AS_STRING(item)[0] == '*') { + PyObject *all; + Py_DECREF(item); + /* See if the package defines __all__ */ + if (recursive) + continue; /* Avoid endless recursion */ + all = PyObject_GetAttrString(mod, "__all__"); + if (all == NULL) + PyErr_Clear(); + else { + int ret = ensure_fromlist(mod, all, buf, buflen, 1); + Py_DECREF(all); + if (!ret) + return 0; + } + continue; + } + hasit = PyObject_HasAttr(mod, item); + if (!hasit) { + char *subname = PyString_AS_STRING(item); + PyObject *submod; + char *p; + if (buflen + strlen(subname) >= MAXPATHLEN) { + PyErr_SetString(PyExc_ValueError, + "Module name too long"); + Py_DECREF(item); + return 0; + } + p = buf + buflen; + *p++ = '.'; + strcpy(p, subname); + submod = import_submodule(mod, subname, buf); + Py_XDECREF(submod); + if (submod == NULL) { + Py_DECREF(item); + return 0; + } + } + Py_DECREF(item); + } + + /* NOTREACHED */ +} + +static int +add_submodule(PyObject *mod, PyObject *submod, char *fullname, char *subname, + PyObject *modules) +{ + if (mod == Py_None) + return 1; + /* Irrespective of the success of this load, make a + reference to it in the parent package module. A copy gets + saved in the modules dictionary under the full name, so get a + reference from there, if need be. (The exception is when the + load failed with a SyntaxError -- then there's no trace in + sys.modules. In that case, of course, do nothing extra.) */ + if (submod == NULL) { + submod = PyDict_GetItemString(modules, fullname); + if (submod == NULL) + return 1; + } + if (PyModule_Check(mod)) { + /* We can't use setattr here since it can give a + * spurious warning if the submodule name shadows a + * builtin name */ + PyObject *dict = PyModule_GetDict(mod); + if (!dict) + return 0; + if (PyDict_SetItemString(dict, subname, submod) < 0) + return 0; + } + else { + if (PyObject_SetAttrString(mod, subname, submod) < 0) + return 0; + } + return 1; +} + +static PyObject * +import_submodule(PyObject *mod, char *subname, char *fullname) +{ + PyObject *modules = PyImport_GetModuleDict(); + PyObject *m = NULL; + + /* Require: + if mod == None: subname == fullname + else: mod.__name__ + "." + subname == fullname + */ + + if ((m = PyDict_GetItemString(modules, fullname)) != NULL) { + Py_INCREF(m); + } + else { + PyObject *path, *loader = NULL; + char *buf; + struct filedescr *fdp; + FILE *fp = NULL; + + if (mod == Py_None) + path = NULL; + else { + path = PyObject_GetAttrString(mod, "__path__"); + if (path == NULL) { + PyErr_Clear(); + Py_INCREF(Py_None); + return Py_None; + } + } + + buf = PyMem_MALLOC(MAXPATHLEN+1); + if (buf == NULL) { + return PyErr_NoMemory(); + } + buf[0] = '\0'; + fdp = find_module(fullname, subname, path, buf, MAXPATHLEN+1, + &fp, &loader); + Py_XDECREF(path); + if (fdp == NULL) { + PyMem_FREE(buf); + if (!PyErr_ExceptionMatches(PyExc_ImportError)) + return NULL; + PyErr_Clear(); + Py_INCREF(Py_None); + return Py_None; + } + m = load_module(fullname, fp, buf, fdp->type, loader); + Py_XDECREF(loader); + if (fp) + fclose(fp); + if (!add_submodule(mod, m, fullname, subname, modules)) { + Py_XDECREF(m); + m = NULL; + } + PyMem_FREE(buf); + } + + return m; +} + + +/* Re-import a module of any kind and return its module object, WITH + INCREMENTED REFERENCE COUNT */ + +PyObject * +PyImport_ReloadModule(PyObject *m) +{ + PyInterpreterState *interp = PyThreadState_Get()->interp; + PyObject *modules_reloading = interp->modules_reloading; + PyObject *modules = PyImport_GetModuleDict(); + PyObject *path = NULL, *loader = NULL, *existing_m = NULL; + char *name, *subname; + char *buf; + struct filedescr *fdp; + FILE *fp = NULL; + PyObject *newm; + + if (modules_reloading == NULL) { + Py_FatalError("PyImport_ReloadModule: " + "no modules_reloading dictionary!"); + return NULL; + } + + if (m == NULL || !PyModule_Check(m)) { + PyErr_SetString(PyExc_TypeError, + "reload() argument must be module"); + return NULL; + } + name = PyModule_GetName(m); + if (name == NULL) + return NULL; + if (m != PyDict_GetItemString(modules, name)) { + PyErr_Format(PyExc_ImportError, + "reload(): module %.200s not in sys.modules", + name); + return NULL; + } + existing_m = PyDict_GetItemString(modules_reloading, name); + if (existing_m != NULL) { + /* Due to a recursive reload, this module is already + being reloaded. */ + Py_INCREF(existing_m); + return existing_m; + } + if (PyDict_SetItemString(modules_reloading, name, m) < 0) + return NULL; + + subname = strrchr(name, '.'); + if (subname == NULL) + subname = name; + else { + PyObject *parentname, *parent; + parentname = PyString_FromStringAndSize(name, (subname-name)); + if (parentname == NULL) { + imp_modules_reloading_clear(); + return NULL; + } + parent = PyDict_GetItem(modules, parentname); + if (parent == NULL) { + PyErr_Format(PyExc_ImportError, + "reload(): parent %.200s not in sys.modules", + PyString_AS_STRING(parentname)); + Py_DECREF(parentname); + imp_modules_reloading_clear(); + return NULL; + } + Py_DECREF(parentname); + subname++; + path = PyObject_GetAttrString(parent, "__path__"); + if (path == NULL) + PyErr_Clear(); + } + buf = PyMem_MALLOC(MAXPATHLEN+1); + if (buf == NULL) { + Py_XDECREF(path); + return PyErr_NoMemory(); + } + buf[0] = '\0'; + fdp = find_module(name, subname, path, buf, MAXPATHLEN+1, &fp, &loader); + Py_XDECREF(path); + + if (fdp == NULL) { + Py_XDECREF(loader); + imp_modules_reloading_clear(); + PyMem_FREE(buf); + return NULL; + } + + newm = load_module(name, fp, buf, fdp->type, loader); + Py_XDECREF(loader); + + if (fp) + fclose(fp); + if (newm == NULL) { + /* load_module probably removed name from modules because of + * the error. Put back the original module object. We're + * going to return NULL in this case regardless of whether + * replacing name succeeds, so the return value is ignored. + */ + PyDict_SetItemString(modules, name, m); + } + imp_modules_reloading_clear(); + PyMem_FREE(buf); + return newm; +} + + +/* Higher-level import emulator which emulates the "import" statement + more accurately -- it invokes the __import__() function from the + builtins of the current globals. This means that the import is + done using whatever import hooks are installed in the current + environment, e.g. by "rexec". + A dummy list ["__doc__"] is passed as the 4th argument so that + e.g. PyImport_Import(PyString_FromString("win32com.client.gencache")) + will return instead of . */ + +PyObject * +PyImport_Import(PyObject *module_name) +{ + static PyObject *silly_list = NULL; + static PyObject *builtins_str = NULL; + static PyObject *import_str = NULL; + PyObject *globals = NULL; + PyObject *import = NULL; + PyObject *builtins = NULL; + PyObject *r = NULL; + + /* Initialize constant string objects */ + if (silly_list == NULL) { + import_str = PyString_InternFromString("__import__"); + if (import_str == NULL) + return NULL; + builtins_str = PyString_InternFromString("__builtins__"); + if (builtins_str == NULL) + return NULL; + silly_list = Py_BuildValue("[s]", "__doc__"); + if (silly_list == NULL) + return NULL; + } + + /* Get the builtins from current globals */ + globals = PyEval_GetGlobals(); + if (globals != NULL) { + Py_INCREF(globals); + builtins = PyObject_GetItem(globals, builtins_str); + if (builtins == NULL) + goto err; + } + else { + /* No globals -- use standard builtins, and fake globals */ + builtins = PyImport_ImportModuleLevel("__builtin__", + NULL, NULL, NULL, 0); + if (builtins == NULL) + return NULL; + globals = Py_BuildValue("{OO}", builtins_str, builtins); + if (globals == NULL) + goto err; + } + + /* Get the __import__ function from the builtins */ + if (PyDict_Check(builtins)) { + import = PyObject_GetItem(builtins, import_str); + if (import == NULL) + PyErr_SetObject(PyExc_KeyError, import_str); + } + else + import = PyObject_GetAttr(builtins, import_str); + if (import == NULL) + goto err; + + /* Call the __import__ function with the proper argument list + * Always use absolute import here. */ + r = PyObject_CallFunction(import, "OOOOi", module_name, globals, + globals, silly_list, 0, NULL); + + err: + Py_XDECREF(globals); + Py_XDECREF(builtins); + Py_XDECREF(import); + + return r; +} + + +/* Module 'imp' provides Python access to the primitives used for + importing modules. +*/ + +static PyObject * +imp_get_magic(PyObject *self, PyObject *noargs) +{ + char buf[4]; + + buf[0] = (char) ((pyc_magic >> 0) & 0xff); + buf[1] = (char) ((pyc_magic >> 8) & 0xff); + buf[2] = (char) ((pyc_magic >> 16) & 0xff); + buf[3] = (char) ((pyc_magic >> 24) & 0xff); + + return PyString_FromStringAndSize(buf, 4); +} + +static PyObject * +imp_get_suffixes(PyObject *self, PyObject *noargs) +{ + PyObject *list; + struct filedescr *fdp; + + list = PyList_New(0); + if (list == NULL) + return NULL; + for (fdp = _PyImport_Filetab; fdp->suffix != NULL; fdp++) { + PyObject *item = Py_BuildValue("ssi", + fdp->suffix, fdp->mode, fdp->type); + if (item == NULL) { + Py_DECREF(list); + return NULL; + } + if (PyList_Append(list, item) < 0) { + Py_DECREF(list); + Py_DECREF(item); + return NULL; + } + Py_DECREF(item); + } + return list; +} + +static PyObject * +call_find_module(char *name, PyObject *path) +{ + extern int fclose(FILE *); + PyObject *fob, *ret; + struct filedescr *fdp; + char *pathname; + FILE *fp = NULL; + + pathname = PyMem_MALLOC(MAXPATHLEN+1); + if (pathname == NULL) { + return PyErr_NoMemory(); + } + pathname[0] = '\0'; + if (path == Py_None) + path = NULL; + fdp = find_module(NULL, name, path, pathname, MAXPATHLEN+1, &fp, NULL); + if (fdp == NULL) { + PyMem_FREE(pathname); + return NULL; + } + if (fp != NULL) { + fob = PyFile_FromFile(fp, pathname, fdp->mode, fclose); + if (fob == NULL) { + PyMem_FREE(pathname); + return NULL; + } + } + else { + fob = Py_None; + Py_INCREF(fob); + } + ret = Py_BuildValue("Os(ssi)", + fob, pathname, fdp->suffix, fdp->mode, fdp->type); + Py_DECREF(fob); + PyMem_FREE(pathname); + return ret; +} + +static PyObject * +imp_find_module(PyObject *self, PyObject *args) +{ + char *name; + PyObject *path = NULL; + if (!PyArg_ParseTuple(args, "s|O:find_module", &name, &path)) + return NULL; + return call_find_module(name, path); +} + +static PyObject * +imp_init_builtin(PyObject *self, PyObject *args) +{ + char *name; + int ret; + PyObject *m; + if (!PyArg_ParseTuple(args, "s:init_builtin", &name)) + return NULL; + ret = init_builtin(name); + if (ret < 0) + return NULL; + if (ret == 0) { + Py_INCREF(Py_None); + return Py_None; + } + m = PyImport_AddModule(name); + Py_XINCREF(m); + return m; +} + +static PyObject * +imp_init_frozen(PyObject *self, PyObject *args) +{ + char *name; + int ret; + PyObject *m; + if (!PyArg_ParseTuple(args, "s:init_frozen", &name)) + return NULL; + ret = PyImport_ImportFrozenModule(name); + if (ret < 0) + return NULL; + if (ret == 0) { + Py_INCREF(Py_None); + return Py_None; + } + m = PyImport_AddModule(name); + Py_XINCREF(m); + return m; +} + +static PyObject * +imp_get_frozen_object(PyObject *self, PyObject *args) +{ + char *name; + + if (!PyArg_ParseTuple(args, "s:get_frozen_object", &name)) + return NULL; + return get_frozen_object(name); +} + +static PyObject * +imp_is_builtin(PyObject *self, PyObject *args) +{ + char *name; + if (!PyArg_ParseTuple(args, "s:is_builtin", &name)) + return NULL; + return PyInt_FromLong(is_builtin(name)); +} + +static PyObject * +imp_is_frozen(PyObject *self, PyObject *args) +{ + char *name; + struct _frozen *p; + if (!PyArg_ParseTuple(args, "s:is_frozen", &name)) + return NULL; + p = find_frozen(name); + return PyBool_FromLong((long) (p == NULL ? 0 : p->size)); +} + +static FILE * +get_file(char *pathname, PyObject *fob, char *mode) +{ + FILE *fp; + if (fob == NULL) { + if (mode[0] == 'U') + mode = "r" PY_STDIOTEXTMODE; + fp = fopen(pathname, mode); + if (fp == NULL) + PyErr_SetFromErrno(PyExc_IOError); + } + else { + fp = PyFile_AsFile(fob); + if (fp == NULL) + PyErr_SetString(PyExc_ValueError, + "bad/closed file object"); + } + return fp; +} + +static PyObject * +imp_load_compiled(PyObject *self, PyObject *args) +{ + char *name; + char *pathname; + PyObject *fob = NULL; + PyObject *m; + FILE *fp; + if (!PyArg_ParseTuple(args, "ss|O!:load_compiled", &name, &pathname, + &PyFile_Type, &fob)) + return NULL; + fp = get_file(pathname, fob, "rb"); + if (fp == NULL) + return NULL; + m = load_compiled_module(name, pathname, fp); + if (fob == NULL) + fclose(fp); + return m; +} + +#ifdef HAVE_DYNAMIC_LOADING + +static PyObject * +imp_load_dynamic(PyObject *self, PyObject *args) +{ + char *name; + char *pathname; + PyObject *fob = NULL; + PyObject *m; + FILE *fp = NULL; + if (!PyArg_ParseTuple(args, "ss|O!:load_dynamic", &name, &pathname, + &PyFile_Type, &fob)) + return NULL; + if (fob) { + fp = get_file(pathname, fob, "r"); + if (fp == NULL) + return NULL; + } + m = _PyImport_LoadDynamicModule(name, pathname, fp); + return m; +} + +#endif /* HAVE_DYNAMIC_LOADING */ + +static PyObject * +imp_load_source(PyObject *self, PyObject *args) +{ + char *name; + char *pathname; + PyObject *fob = NULL; + PyObject *m; + FILE *fp; + if (!PyArg_ParseTuple(args, "ss|O!:load_source", &name, &pathname, + &PyFile_Type, &fob)) + return NULL; + fp = get_file(pathname, fob, "r"); + if (fp == NULL) + return NULL; + m = load_source_module(name, pathname, fp); + if (fob == NULL) + fclose(fp); + return m; +} + +static PyObject * +imp_load_module(PyObject *self, PyObject *args) +{ + char *name; + PyObject *fob; + char *pathname; + char *suffix; /* Unused */ + char *mode; + int type; + FILE *fp; + + if (!PyArg_ParseTuple(args, "sOs(ssi):load_module", + &name, &fob, &pathname, + &suffix, &mode, &type)) + return NULL; + if (*mode) { + /* Mode must start with 'r' or 'U' and must not contain '+'. + Implicit in this test is the assumption that the mode + may contain other modifiers like 'b' or 't'. */ + + if (!(*mode == 'r' || *mode == 'U') || strchr(mode, '+')) { + PyErr_Format(PyExc_ValueError, + "invalid file open mode %.200s", mode); + return NULL; + } + } + if (fob == Py_None) + fp = NULL; + else { + if (!PyFile_Check(fob)) { + PyErr_SetString(PyExc_ValueError, + "load_module arg#2 should be a file or None"); + return NULL; + } + fp = get_file(pathname, fob, mode); + if (fp == NULL) + return NULL; + } + return load_module(name, fp, pathname, type, NULL); +} + +static PyObject * +imp_load_package(PyObject *self, PyObject *args) +{ + char *name; + char *pathname; + if (!PyArg_ParseTuple(args, "ss:load_package", &name, &pathname)) + return NULL; + return load_package(name, pathname); +} + +static PyObject * +imp_new_module(PyObject *self, PyObject *args) +{ + char *name; + if (!PyArg_ParseTuple(args, "s:new_module", &name)) + return NULL; + return PyModule_New(name); +} + +static PyObject * +imp_reload(PyObject *self, PyObject *v) +{ + return PyImport_ReloadModule(v); +} + + +/* Doc strings */ + +PyDoc_STRVAR(doc_imp, +"This module provides the components needed to build your own\n\ +__import__ function. Undocumented functions are obsolete."); + +PyDoc_STRVAR(doc_reload, +"reload(module) -> module\n\ +\n\ +Reload the module. The module must have been successfully imported before."); + +PyDoc_STRVAR(doc_find_module, +"find_module(name, [path]) -> (file, filename, (suffix, mode, type))\n\ +Search for a module. If path is omitted or None, search for a\n\ +built-in, frozen or special module and continue search in sys.path.\n\ +The module name cannot contain '.'; to search for a submodule of a\n\ +package, pass the submodule name and the package's __path__."); + +PyDoc_STRVAR(doc_load_module, +"load_module(name, file, filename, (suffix, mode, type)) -> module\n\ +Load a module, given information returned by find_module().\n\ +The module name must include the full package name, if any."); + +PyDoc_STRVAR(doc_get_magic, +"get_magic() -> string\n\ +Return the magic number for .pyc or .pyo files."); + +PyDoc_STRVAR(doc_get_suffixes, +"get_suffixes() -> [(suffix, mode, type), ...]\n\ +Return a list of (suffix, mode, type) tuples describing the files\n\ +that find_module() looks for."); + +PyDoc_STRVAR(doc_new_module, +"new_module(name) -> module\n\ +Create a new module. Do not enter it in sys.modules.\n\ +The module name must include the full package name, if any."); + +PyDoc_STRVAR(doc_lock_held, +"lock_held() -> boolean\n\ +Return True if the import lock is currently held, else False.\n\ +On platforms without threads, return False."); + +PyDoc_STRVAR(doc_acquire_lock, +"acquire_lock() -> None\n\ +Acquires the interpreter's import lock for the current thread.\n\ +This lock should be used by import hooks to ensure thread-safety\n\ +when importing modules.\n\ +On platforms without threads, this function does nothing."); + +PyDoc_STRVAR(doc_release_lock, +"release_lock() -> None\n\ +Release the interpreter's import lock.\n\ +On platforms without threads, this function does nothing."); + +static PyMethodDef imp_methods[] = { + {"reload", imp_reload, METH_O, doc_reload}, + {"find_module", imp_find_module, METH_VARARGS, doc_find_module}, + {"get_magic", imp_get_magic, METH_NOARGS, doc_get_magic}, + {"get_suffixes", imp_get_suffixes, METH_NOARGS, doc_get_suffixes}, + {"load_module", imp_load_module, METH_VARARGS, doc_load_module}, + {"new_module", imp_new_module, METH_VARARGS, doc_new_module}, + {"lock_held", imp_lock_held, METH_NOARGS, doc_lock_held}, + {"acquire_lock", imp_acquire_lock, METH_NOARGS, doc_acquire_lock}, + {"release_lock", imp_release_lock, METH_NOARGS, doc_release_lock}, + /* The rest are obsolete */ + {"get_frozen_object", imp_get_frozen_object, METH_VARARGS}, + {"init_builtin", imp_init_builtin, METH_VARARGS}, + {"init_frozen", imp_init_frozen, METH_VARARGS}, + {"is_builtin", imp_is_builtin, METH_VARARGS}, + {"is_frozen", imp_is_frozen, METH_VARARGS}, + {"load_compiled", imp_load_compiled, METH_VARARGS}, +#ifdef HAVE_DYNAMIC_LOADING + {"load_dynamic", imp_load_dynamic, METH_VARARGS}, +#endif + {"load_package", imp_load_package, METH_VARARGS}, + {"load_source", imp_load_source, METH_VARARGS}, + {NULL, NULL} /* sentinel */ +}; + +static int +setint(PyObject *d, char *name, int value) +{ + PyObject *v; + int err; + + v = PyInt_FromLong((long)value); + err = PyDict_SetItemString(d, name, v); + Py_XDECREF(v); + return err; +} + +typedef struct { + PyObject_HEAD +} NullImporter; + +static int +NullImporter_init(NullImporter *self, PyObject *args, PyObject *kwds) +{ + char *path; + Py_ssize_t pathlen; + + if (!_PyArg_NoKeywords("NullImporter()", kwds)) + return -1; + + if (!PyArg_ParseTuple(args, "s:NullImporter", + &path)) + return -1; + + pathlen = strlen(path); + if (pathlen == 0) { + PyErr_SetString(PyExc_ImportError, "empty pathname"); + return -1; + } else { + if(isdir(path)) { + PyErr_SetString(PyExc_ImportError, + "existing directory"); + return -1; + } + } + return 0; +} + +static PyObject * +NullImporter_find_module(NullImporter *self, PyObject *args) +{ + Py_RETURN_NONE; +} + +static PyMethodDef NullImporter_methods[] = { + {"find_module", (PyCFunction)NullImporter_find_module, METH_VARARGS, + "Always return None" + }, + {NULL} /* Sentinel */ +}; + + +PyTypeObject PyNullImporter_Type = { + PyVarObject_HEAD_INIT(NULL, 0) + "imp.NullImporter", /*tp_name*/ + sizeof(NullImporter), /*tp_basicsize*/ + 0, /*tp_itemsize*/ + 0, /*tp_dealloc*/ + 0, /*tp_print*/ + 0, /*tp_getattr*/ + 0, /*tp_setattr*/ + 0, /*tp_compare*/ + 0, /*tp_repr*/ + 0, /*tp_as_number*/ + 0, /*tp_as_sequence*/ + 0, /*tp_as_mapping*/ + 0, /*tp_hash */ + 0, /*tp_call*/ + 0, /*tp_str*/ + 0, /*tp_getattro*/ + 0, /*tp_setattro*/ + 0, /*tp_as_buffer*/ + Py_TPFLAGS_DEFAULT, /*tp_flags*/ + "Null importer object", /* tp_doc */ + 0, /* tp_traverse */ + 0, /* tp_clear */ + 0, /* tp_richcompare */ + 0, /* tp_weaklistoffset */ + 0, /* tp_iter */ + 0, /* tp_iternext */ + NullImporter_methods, /* tp_methods */ + 0, /* tp_members */ + 0, /* tp_getset */ + 0, /* tp_base */ + 0, /* tp_dict */ + 0, /* tp_descr_get */ + 0, /* tp_descr_set */ + 0, /* tp_dictoffset */ + (initproc)NullImporter_init, /* tp_init */ + 0, /* tp_alloc */ + PyType_GenericNew /* tp_new */ +}; + + +PyMODINIT_FUNC +initimp(void) +{ + PyObject *m, *d; + + if (PyType_Ready(&PyNullImporter_Type) < 0) + goto failure; + + m = Py_InitModule4("imp", imp_methods, doc_imp, + NULL, PYTHON_API_VERSION); + if (m == NULL) + goto failure; + d = PyModule_GetDict(m); + if (d == NULL) + goto failure; + + if (setint(d, "SEARCH_ERROR", SEARCH_ERROR) < 0) goto failure; + if (setint(d, "PY_SOURCE", PY_SOURCE) < 0) goto failure; + if (setint(d, "PY_COMPILED", PY_COMPILED) < 0) goto failure; + if (setint(d, "C_EXTENSION", C_EXTENSION) < 0) goto failure; + if (setint(d, "PY_RESOURCE", PY_RESOURCE) < 0) goto failure; + if (setint(d, "PKG_DIRECTORY", PKG_DIRECTORY) < 0) goto failure; + if (setint(d, "C_BUILTIN", C_BUILTIN) < 0) goto failure; + if (setint(d, "PY_FROZEN", PY_FROZEN) < 0) goto failure; + if (setint(d, "PY_CODERESOURCE", PY_CODERESOURCE) < 0) goto failure; + if (setint(d, "IMP_HOOK", IMP_HOOK) < 0) goto failure; + + Py_INCREF(&PyNullImporter_Type); + PyModule_AddObject(m, "NullImporter", (PyObject *)&PyNullImporter_Type); + failure: + ; +} + + +/* API for embedding applications that want to add their own entries + to the table of built-in modules. This should normally be called + *before* Py_Initialize(). When the table resize fails, -1 is + returned and the existing table is unchanged. + + After a similar function by Just van Rossum. */ + +int +PyImport_ExtendInittab(struct _inittab *newtab) +{ + static struct _inittab *our_copy = NULL; + struct _inittab *p; + int i, n; + + /* Count the number of entries in both tables */ + for (n = 0; newtab[n].name != NULL; n++) + ; + if (n == 0) + return 0; /* Nothing to do */ + for (i = 0; PyImport_Inittab[i].name != NULL; i++) + ; + + /* Allocate new memory for the combined table */ + p = our_copy; + PyMem_RESIZE(p, struct _inittab, i+n+1); + if (p == NULL) + return -1; + + /* Copy the tables into the new memory */ + if (our_copy != PyImport_Inittab) + memcpy(p, PyImport_Inittab, (i+1) * sizeof(struct _inittab)); + PyImport_Inittab = our_copy = p; + memcpy(p+i, newtab, (n+1) * sizeof(struct _inittab)); + + return 0; +} + +/* Shorthand to add a single entry given a name and a function */ + +int +PyImport_AppendInittab(const char *name, void (*initfunc)(void)) +{ + struct _inittab newtab[2]; + + memset(newtab, '\0', sizeof newtab); + + newtab[0].name = (char *)name; + newtab[0].initfunc = initfunc; + + return PyImport_ExtendInittab(newtab); +} + +#ifdef __cplusplus +} +#endif diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/importdl.c b/AppPkg/Applications/Python/Python-2.7.10/Python/importdl.c new file mode 100644 index 0000000000..0280e81bc5 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/importdl.c @@ -0,0 +1,78 @@ + +/* Support for dynamic loading of extension modules */ + +#include "Python.h" + +/* ./configure sets HAVE_DYNAMIC_LOADING if dynamic loading of modules is + supported on this platform. configure will then compile and link in one + of the dynload_*.c files, as appropriate. We will call a function in + those modules to get a function pointer to the module's init function. +*/ +#ifdef HAVE_DYNAMIC_LOADING + +#include "importdl.h" + +extern dl_funcptr _PyImport_GetDynLoadFunc(const char *name, + const char *shortname, + const char *pathname, FILE *fp); + + + +PyObject * +_PyImport_LoadDynamicModule(char *name, char *pathname, FILE *fp) +{ + PyObject *m; + char *lastdot, *shortname, *packagecontext, *oldcontext; + dl_funcptr p; + + if ((m = _PyImport_FindExtension(name, pathname)) != NULL) { + Py_INCREF(m); + return m; + } + lastdot = strrchr(name, '.'); + if (lastdot == NULL) { + packagecontext = NULL; + shortname = name; + } + else { + packagecontext = name; + shortname = lastdot+1; + } + + p = _PyImport_GetDynLoadFunc(name, shortname, pathname, fp); + if (PyErr_Occurred()) + return NULL; + if (p == NULL) { + PyErr_Format(PyExc_ImportError, + "dynamic module does not define init function (init%.200s)", + shortname); + return NULL; + } + oldcontext = _Py_PackageContext; + _Py_PackageContext = packagecontext; + (*p)(); + _Py_PackageContext = oldcontext; + if (PyErr_Occurred()) + return NULL; + + m = PyDict_GetItemString(PyImport_GetModuleDict(), name); + if (m == NULL) { + PyErr_SetString(PyExc_SystemError, + "dynamic module not initialized properly"); + return NULL; + } + /* Remember the filename as the __file__ attribute */ + if (PyModule_AddStringConstant(m, "__file__", pathname) < 0) + PyErr_Clear(); /* Not important enough to report */ + + if (_PyImport_FixupExtension(name, pathname) == NULL) + return NULL; + if (Py_VerboseFlag) + PySys_WriteStderr( + "import %s # dynamically loaded from %s\n", + name, pathname); + Py_INCREF(m); + return m; +} + +#endif /* HAVE_DYNAMIC_LOADING */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/importdl.h b/AppPkg/Applications/Python/Python-2.7.10/Python/importdl.h new file mode 100644 index 0000000000..7e17246678 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/importdl.h @@ -0,0 +1,53 @@ +#ifndef Py_IMPORTDL_H +#define Py_IMPORTDL_H + +#ifdef __cplusplus +extern "C" { +#endif + + +/* Definitions for dynamic loading of extension modules */ +enum filetype { + SEARCH_ERROR, + PY_SOURCE, + PY_COMPILED, + C_EXTENSION, + PY_RESOURCE, /* Mac only */ + PKG_DIRECTORY, + C_BUILTIN, + PY_FROZEN, + PY_CODERESOURCE, /* Mac only */ + IMP_HOOK +}; + +struct filedescr { + char *suffix; + char *mode; + enum filetype type; +}; +extern struct filedescr * _PyImport_Filetab; +extern const struct filedescr _PyImport_DynLoadFiletab[]; + +extern PyObject *_PyImport_LoadDynamicModule(char *name, char *pathname, + FILE *); + +/* Max length of module suffix searched for -- accommodates "module.slb" */ +#define MAXSUFFIXSIZE 12 + +#ifdef MS_WINDOWS +#include +typedef FARPROC dl_funcptr; +#else +#if defined(PYOS_OS2) && !defined(PYCC_GCC) +#include +typedef int (* APIENTRY dl_funcptr)(); +#else +typedef void (*dl_funcptr)(void); +#endif +#endif + + +#ifdef __cplusplus +} +#endif +#endif /* !Py_IMPORTDL_H */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/modsupport.c b/AppPkg/Applications/Python/Python-2.7.10/Python/modsupport.c new file mode 100644 index 0000000000..e383bdf0da --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/modsupport.c @@ -0,0 +1,644 @@ + +/* Module support implementation */ + +#include "Python.h" + +#define FLAG_SIZE_T 1 +typedef double va_double; + +static PyObject *va_build_value(const char *, va_list, int); + +/* Package context -- the full module name for package imports */ +char *_Py_PackageContext = NULL; + +/* Py_InitModule4() parameters: + - name is the module name + - methods is the list of top-level functions + - doc is the documentation string + - passthrough is passed as self to functions defined in the module + - api_version is the value of PYTHON_API_VERSION at the time the + module was compiled + + Return value is a borrowed reference to the module object; or NULL + if an error occurred (in Python 1.4 and before, errors were fatal). + Errors may still leak memory. +*/ + +static char api_version_warning[] = +"Python C API version mismatch for module %.100s:\ + This Python has API version %d, module %.100s has version %d."; + +PyObject * +Py_InitModule4(const char *name, PyMethodDef *methods, const char *doc, + PyObject *passthrough, int module_api_version) +{ + PyObject *m, *d, *v, *n; + PyMethodDef *ml; + PyInterpreterState *interp = PyThreadState_Get()->interp; + if (interp->modules == NULL) + Py_FatalError("Python import machinery not initialized"); + if (module_api_version != PYTHON_API_VERSION) { + char message[512]; + PyOS_snprintf(message, sizeof(message), + api_version_warning, name, + PYTHON_API_VERSION, name, + module_api_version); + if (PyErr_Warn(PyExc_RuntimeWarning, message)) + return NULL; + } + /* Make sure name is fully qualified. + + This is a bit of a hack: when the shared library is loaded, + the module name is "package.module", but the module calls + Py_InitModule*() with just "module" for the name. The shared + library loader squirrels away the true name of the module in + _Py_PackageContext, and Py_InitModule*() will substitute this + (if the name actually matches). + */ + if (_Py_PackageContext != NULL) { + char *p = strrchr(_Py_PackageContext, '.'); + if (p != NULL && strcmp(name, p+1) == 0) { + name = _Py_PackageContext; + _Py_PackageContext = NULL; + } + } + if ((m = PyImport_AddModule(name)) == NULL) + return NULL; + d = PyModule_GetDict(m); + if (methods != NULL) { + n = PyString_FromString(name); + if (n == NULL) + return NULL; + for (ml = methods; ml->ml_name != NULL; ml++) { + if ((ml->ml_flags & METH_CLASS) || + (ml->ml_flags & METH_STATIC)) { + PyErr_SetString(PyExc_ValueError, + "module functions cannot set" + " METH_CLASS or METH_STATIC"); + Py_DECREF(n); + return NULL; + } + v = PyCFunction_NewEx(ml, passthrough, n); + if (v == NULL) { + Py_DECREF(n); + return NULL; + } + if (PyDict_SetItemString(d, ml->ml_name, v) != 0) { + Py_DECREF(v); + Py_DECREF(n); + return NULL; + } + Py_DECREF(v); + } + Py_DECREF(n); + } + if (doc != NULL) { + v = PyString_FromString(doc); + if (v == NULL || PyDict_SetItemString(d, "__doc__", v) != 0) { + Py_XDECREF(v); + return NULL; + } + Py_DECREF(v); + } + return m; +} + + +/* Helper for mkvalue() to scan the length of a format */ + +static int +countformat(const char *format, int endchar) +{ + int count = 0; + int level = 0; + while (level > 0 || *format != endchar) { + switch (*format) { + case '\0': + /* Premature end */ + PyErr_SetString(PyExc_SystemError, + "unmatched paren in format"); + return -1; + case '(': + case '[': + case '{': + if (level == 0) + count++; + level++; + break; + case ')': + case ']': + case '}': + level--; + break; + case '#': + case '&': + case ',': + case ':': + case ' ': + case '\t': + break; + default: + if (level == 0) + count++; + } + format++; + } + return count; +} + + +/* Generic function to create a value -- the inverse of getargs() */ +/* After an original idea and first implementation by Steven Miale */ + +static PyObject *do_mktuple(const char**, va_list *, int, int, int); +static PyObject *do_mklist(const char**, va_list *, int, int, int); +static PyObject *do_mkdict(const char**, va_list *, int, int, int); +static PyObject *do_mkvalue(const char**, va_list *, int); + + +static PyObject * +do_mkdict(const char **p_format, va_list *p_va, int endchar, int n, int flags) +{ + PyObject *d; + int i; + int itemfailed = 0; + if (n < 0) + return NULL; + if ((d = PyDict_New()) == NULL) + return NULL; + /* Note that we can't bail immediately on error as this will leak + refcounts on any 'N' arguments. */ + for (i = 0; i < n; i+= 2) { + PyObject *k, *v; + int err; + k = do_mkvalue(p_format, p_va, flags); + if (k == NULL) { + itemfailed = 1; + Py_INCREF(Py_None); + k = Py_None; + } + v = do_mkvalue(p_format, p_va, flags); + if (v == NULL) { + itemfailed = 1; + Py_INCREF(Py_None); + v = Py_None; + } + err = PyDict_SetItem(d, k, v); + Py_DECREF(k); + Py_DECREF(v); + if (err < 0 || itemfailed) { + Py_DECREF(d); + return NULL; + } + } + if (d != NULL && **p_format != endchar) { + Py_DECREF(d); + d = NULL; + PyErr_SetString(PyExc_SystemError, + "Unmatched paren in format"); + } + else if (endchar) + ++*p_format; + return d; +} + +static PyObject * +do_mklist(const char **p_format, va_list *p_va, int endchar, int n, int flags) +{ + PyObject *v; + int i; + int itemfailed = 0; + if (n < 0) + return NULL; + v = PyList_New(n); + if (v == NULL) + return NULL; + /* Note that we can't bail immediately on error as this will leak + refcounts on any 'N' arguments. */ + for (i = 0; i < n; i++) { + PyObject *w = do_mkvalue(p_format, p_va, flags); + if (w == NULL) { + itemfailed = 1; + Py_INCREF(Py_None); + w = Py_None; + } + PyList_SET_ITEM(v, i, w); + } + + if (itemfailed) { + /* do_mkvalue() should have already set an error */ + Py_DECREF(v); + return NULL; + } + if (**p_format != endchar) { + Py_DECREF(v); + PyErr_SetString(PyExc_SystemError, + "Unmatched paren in format"); + return NULL; + } + if (endchar) + ++*p_format; + return v; +} + +#ifdef Py_USING_UNICODE +static int +_ustrlen(Py_UNICODE *u) +{ + int i = 0; + Py_UNICODE *v = u; + while (*v != 0) { i++; v++; } + return i; +} +#endif + +static PyObject * +do_mktuple(const char **p_format, va_list *p_va, int endchar, int n, int flags) +{ + PyObject *v; + int i; + int itemfailed = 0; + if (n < 0) + return NULL; + if ((v = PyTuple_New(n)) == NULL) + return NULL; + /* Note that we can't bail immediately on error as this will leak + refcounts on any 'N' arguments. */ + for (i = 0; i < n; i++) { + PyObject *w = do_mkvalue(p_format, p_va, flags); + if (w == NULL) { + itemfailed = 1; + Py_INCREF(Py_None); + w = Py_None; + } + PyTuple_SET_ITEM(v, i, w); + } + if (itemfailed) { + /* do_mkvalue() should have already set an error */ + Py_DECREF(v); + return NULL; + } + if (**p_format != endchar) { + Py_DECREF(v); + PyErr_SetString(PyExc_SystemError, + "Unmatched paren in format"); + return NULL; + } + if (endchar) + ++*p_format; + return v; +} + +static PyObject * +do_mkvalue(const char **p_format, va_list *p_va, int flags) +{ + for (;;) { + switch (*(*p_format)++) { + case '(': + return do_mktuple(p_format, p_va, ')', + countformat(*p_format, ')'), flags); + + case '[': + return do_mklist(p_format, p_va, ']', + countformat(*p_format, ']'), flags); + + case '{': + return do_mkdict(p_format, p_va, '}', + countformat(*p_format, '}'), flags); + + case 'b': + case 'B': + case 'h': + case 'i': + return PyInt_FromLong((long)va_arg(*p_va, int)); + + case 'H': + return PyInt_FromLong((long)va_arg(*p_va, unsigned int)); + + case 'I': + { + unsigned int n; + n = va_arg(*p_va, unsigned int); + if (n > (unsigned long)PyInt_GetMax()) + return PyLong_FromUnsignedLong((unsigned long)n); + else + return PyInt_FromLong(n); + } + + case 'n': +#if SIZEOF_SIZE_T!=SIZEOF_LONG + return PyInt_FromSsize_t(va_arg(*p_va, Py_ssize_t)); +#endif + /* Fall through from 'n' to 'l' if Py_ssize_t is long */ + case 'l': + return PyInt_FromLong(va_arg(*p_va, long)); + + case 'k': + { + unsigned long n; + n = va_arg(*p_va, unsigned long); + if (n > (unsigned long)PyInt_GetMax()) + return PyLong_FromUnsignedLong(n); + else + return PyInt_FromLong(n); + } + +#ifdef HAVE_LONG_LONG + case 'L': + return PyLong_FromLongLong((PY_LONG_LONG)va_arg(*p_va, PY_LONG_LONG)); + + case 'K': + return PyLong_FromUnsignedLongLong((PY_LONG_LONG)va_arg(*p_va, unsigned PY_LONG_LONG)); +#endif +#ifdef Py_USING_UNICODE + case 'u': + { + PyObject *v; + Py_UNICODE *u = va_arg(*p_va, Py_UNICODE *); + Py_ssize_t n; + if (**p_format == '#') { + ++*p_format; + if (flags & FLAG_SIZE_T) + n = va_arg(*p_va, Py_ssize_t); + else + n = va_arg(*p_va, int); + } + else + n = -1; + if (u == NULL) { + v = Py_None; + Py_INCREF(v); + } + else { + if (n < 0) + n = _ustrlen(u); + v = PyUnicode_FromUnicode(u, n); + } + return v; + } +#endif + case 'f': + case 'd': + return PyFloat_FromDouble( + (double)va_arg(*p_va, va_double)); + +#ifndef WITHOUT_COMPLEX + case 'D': + return PyComplex_FromCComplex( + *((Py_complex *)va_arg(*p_va, Py_complex *))); +#endif /* WITHOUT_COMPLEX */ + + case 'c': + { + char p[1]; + p[0] = (char)va_arg(*p_va, int); + return PyString_FromStringAndSize(p, 1); + } + + case 's': + case 'z': + { + PyObject *v; + char *str = va_arg(*p_va, char *); + Py_ssize_t n; + if (**p_format == '#') { + ++*p_format; + if (flags & FLAG_SIZE_T) + n = va_arg(*p_va, Py_ssize_t); + else + n = va_arg(*p_va, int); + } + else + n = -1; + if (str == NULL) { + v = Py_None; + Py_INCREF(v); + } + else { + if (n < 0) { + size_t m = strlen(str); + if (m > PY_SSIZE_T_MAX) { + PyErr_SetString(PyExc_OverflowError, + "string too long for Python string"); + return NULL; + } + n = (Py_ssize_t)m; + } + v = PyString_FromStringAndSize(str, n); + } + return v; + } + + case 'N': + case 'S': + case 'O': + if (**p_format == '&') { + typedef PyObject *(*converter)(void *); + converter func = va_arg(*p_va, converter); + void *arg = va_arg(*p_va, void *); + ++*p_format; + return (*func)(arg); + } + else { + PyObject *v; + v = va_arg(*p_va, PyObject *); + if (v != NULL) { + if (*(*p_format - 1) != 'N') + Py_INCREF(v); + } + else if (!PyErr_Occurred()) + /* If a NULL was passed + * because a call that should + * have constructed a value + * failed, that's OK, and we + * pass the error on; but if + * no error occurred it's not + * clear that the caller knew + * what she was doing. */ + PyErr_SetString(PyExc_SystemError, + "NULL object passed to Py_BuildValue"); + return v; + } + + case ':': + case ',': + case ' ': + case '\t': + break; + + default: + PyErr_SetString(PyExc_SystemError, + "bad format char passed to Py_BuildValue"); + return NULL; + + } + } +} + + +PyObject * +Py_BuildValue(const char *format, ...) +{ + va_list va; + PyObject* retval; + va_start(va, format); + retval = va_build_value(format, va, 0); + va_end(va); + return retval; +} + +PyObject * +_Py_BuildValue_SizeT(const char *format, ...) +{ + va_list va; + PyObject* retval; + va_start(va, format); + retval = va_build_value(format, va, FLAG_SIZE_T); + va_end(va); + return retval; +} + +PyObject * +Py_VaBuildValue(const char *format, va_list va) +{ + return va_build_value(format, va, 0); +} + +PyObject * +_Py_VaBuildValue_SizeT(const char *format, va_list va) +{ + return va_build_value(format, va, FLAG_SIZE_T); +} + +static PyObject * +va_build_value(const char *format, va_list va, int flags) +{ + const char *f = format; + int n = countformat(f, '\0'); + va_list lva; + +#ifdef VA_LIST_IS_ARRAY + memcpy(lva, va, sizeof(va_list)); +#else +#ifdef __va_copy + __va_copy(lva, va); +#else + lva = va; +#endif +#endif + + if (n < 0) + return NULL; + if (n == 0) { + Py_INCREF(Py_None); + return Py_None; + } + if (n == 1) + return do_mkvalue(&f, &lva, flags); + return do_mktuple(&f, &lva, '\0', n, flags); +} + + +PyObject * +PyEval_CallFunction(PyObject *obj, const char *format, ...) +{ + va_list vargs; + PyObject *args; + PyObject *res; + + va_start(vargs, format); + + args = Py_VaBuildValue(format, vargs); + va_end(vargs); + + if (args == NULL) + return NULL; + + res = PyEval_CallObject(obj, args); + Py_DECREF(args); + + return res; +} + + +PyObject * +PyEval_CallMethod(PyObject *obj, const char *methodname, const char *format, ...) +{ + va_list vargs; + PyObject *meth; + PyObject *args; + PyObject *res; + + meth = PyObject_GetAttrString(obj, methodname); + if (meth == NULL) + return NULL; + + va_start(vargs, format); + + args = Py_VaBuildValue(format, vargs); + va_end(vargs); + + if (args == NULL) { + Py_DECREF(meth); + return NULL; + } + + res = PyEval_CallObject(meth, args); + Py_DECREF(meth); + Py_DECREF(args); + + return res; +} + +int +PyModule_AddObject(PyObject *m, const char *name, PyObject *o) +{ + PyObject *dict; + if (!PyModule_Check(m)) { + PyErr_SetString(PyExc_TypeError, + "PyModule_AddObject() needs module as first arg"); + return -1; + } + if (!o) { + if (!PyErr_Occurred()) + PyErr_SetString(PyExc_TypeError, + "PyModule_AddObject() needs non-NULL value"); + return -1; + } + + dict = PyModule_GetDict(m); + if (dict == NULL) { + /* Internal error -- modules must have a dict! */ + PyErr_Format(PyExc_SystemError, "module '%s' has no __dict__", + PyModule_GetName(m)); + return -1; + } + if (PyDict_SetItemString(dict, name, o)) + return -1; + Py_DECREF(o); + return 0; +} + +int +PyModule_AddIntConstant(PyObject *m, const char *name, long value) +{ + PyObject *o = PyInt_FromLong(value); + if (!o) + return -1; + if (PyModule_AddObject(m, name, o) == 0) + return 0; + Py_DECREF(o); + return -1; +} + +int +PyModule_AddStringConstant(PyObject *m, const char *name, const char *value) +{ + PyObject *o = PyString_FromString(value); + if (!o) + return -1; + if (PyModule_AddObject(m, name, o) == 0) + return 0; + Py_DECREF(o); + return -1; +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/mysnprintf.c b/AppPkg/Applications/Python/Python-2.7.10/Python/mysnprintf.c new file mode 100644 index 0000000000..f9481a8dec --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/mysnprintf.c @@ -0,0 +1,105 @@ +#include "Python.h" +#include + +/* snprintf() wrappers. If the platform has vsnprintf, we use it, else we + emulate it in a half-hearted way. Even if the platform has it, we wrap + it because platforms differ in what vsnprintf does in case the buffer + is too small: C99 behavior is to return the number of characters that + would have been written had the buffer not been too small, and to set + the last byte of the buffer to \0. At least MS _vsnprintf returns a + negative value instead, and fills the entire buffer with non-\0 data. + + The wrappers ensure that str[size-1] is always \0 upon return. + + PyOS_snprintf and PyOS_vsnprintf never write more than size bytes + (including the trailing '\0') into str. + + If the platform doesn't have vsnprintf, and the buffer size needed to + avoid truncation exceeds size by more than 512, Python aborts with a + Py_FatalError. + + Return value (rv): + + When 0 <= rv < size, the output conversion was unexceptional, and + rv characters were written to str (excluding a trailing \0 byte at + str[rv]). + + When rv >= size, output conversion was truncated, and a buffer of + size rv+1 would have been needed to avoid truncation. str[size-1] + is \0 in this case. + + When rv < 0, "something bad happened". str[size-1] is \0 in this + case too, but the rest of str is unreliable. It could be that + an error in format codes was detected by libc, or on platforms + with a non-C99 vsnprintf simply that the buffer wasn't big enough + to avoid truncation, or on platforms without any vsnprintf that + PyMem_Malloc couldn't obtain space for a temp buffer. + + CAUTION: Unlike C99, str != NULL and size > 0 are required. +*/ + +int +PyOS_snprintf(char *str, size_t size, const char *format, ...) +{ + int rc; + va_list va; + + va_start(va, format); + rc = PyOS_vsnprintf(str, size, format, va); + va_end(va); + return rc; +} + +int +PyOS_vsnprintf(char *str, size_t size, const char *format, va_list va) +{ + int len; /* # bytes written, excluding \0 */ +#ifdef HAVE_SNPRINTF +#define _PyOS_vsnprintf_EXTRA_SPACE 1 +#else +#define _PyOS_vsnprintf_EXTRA_SPACE 512 + char *buffer; +#endif + assert(str != NULL); + assert(size > 0); + assert(format != NULL); + /* We take a size_t as input but return an int. Sanity check + * our input so that it won't cause an overflow in the + * vsnprintf return value or the buffer malloc size. */ + if (size > INT_MAX - _PyOS_vsnprintf_EXTRA_SPACE) { + len = -666; + goto Done; + } + +#ifdef HAVE_SNPRINTF + len = vsnprintf(str, size, format, va); +#else + /* Emulate it. */ + buffer = PyMem_MALLOC(size + _PyOS_vsnprintf_EXTRA_SPACE); + if (buffer == NULL) { + len = -666; + goto Done; + } + + len = vsprintf(buffer, format, va); + if (len < 0) + /* ignore the error */; + + else if ((size_t)len >= size + _PyOS_vsnprintf_EXTRA_SPACE) + Py_FatalError("Buffer overflow in PyOS_snprintf/PyOS_vsnprintf"); + + else { + const size_t to_copy = (size_t)len < size ? + (size_t)len : size - 1; + assert(to_copy < size); + memcpy(str, buffer, to_copy); + str[to_copy] = '\0'; + } + PyMem_FREE(buffer); +#endif +Done: + if (size > 0) + str[size-1] = '\0'; + return len; +#undef _PyOS_vsnprintf_EXTRA_SPACE +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/mystrtoul.c b/AppPkg/Applications/Python/Python-2.7.10/Python/mystrtoul.c new file mode 100644 index 0000000000..096eb1620d --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/mystrtoul.c @@ -0,0 +1,285 @@ + +#include "Python.h" + +#if defined(__sgi) && defined(WITH_THREAD) && !defined(_SGI_MP_SOURCE) +#define _SGI_MP_SOURCE +#endif + +/* strtol and strtoul, renamed to avoid conflicts */ + + +#include +#ifdef HAVE_ERRNO_H +#include +#endif + +/* Static overflow check values for bases 2 through 36. + * smallmax[base] is the largest unsigned long i such that + * i * base doesn't overflow unsigned long. + */ +static unsigned long smallmax[] = { + 0, /* bases 0 and 1 are invalid */ + 0, + ULONG_MAX / 2, + ULONG_MAX / 3, + ULONG_MAX / 4, + ULONG_MAX / 5, + ULONG_MAX / 6, + ULONG_MAX / 7, + ULONG_MAX / 8, + ULONG_MAX / 9, + ULONG_MAX / 10, + ULONG_MAX / 11, + ULONG_MAX / 12, + ULONG_MAX / 13, + ULONG_MAX / 14, + ULONG_MAX / 15, + ULONG_MAX / 16, + ULONG_MAX / 17, + ULONG_MAX / 18, + ULONG_MAX / 19, + ULONG_MAX / 20, + ULONG_MAX / 21, + ULONG_MAX / 22, + ULONG_MAX / 23, + ULONG_MAX / 24, + ULONG_MAX / 25, + ULONG_MAX / 26, + ULONG_MAX / 27, + ULONG_MAX / 28, + ULONG_MAX / 29, + ULONG_MAX / 30, + ULONG_MAX / 31, + ULONG_MAX / 32, + ULONG_MAX / 33, + ULONG_MAX / 34, + ULONG_MAX / 35, + ULONG_MAX / 36, +}; + +/* maximum digits that can't ever overflow for bases 2 through 36, + * calculated by [int(math.floor(math.log(2**32, i))) for i in range(2, 37)]. + * Note that this is pessimistic if sizeof(long) > 4. + */ +#if SIZEOF_LONG == 4 +static int digitlimit[] = { + 0, 0, 32, 20, 16, 13, 12, 11, 10, 10, /* 0 - 9 */ + 9, 9, 8, 8, 8, 8, 8, 7, 7, 7, /* 10 - 19 */ + 7, 7, 7, 7, 6, 6, 6, 6, 6, 6, /* 20 - 29 */ + 6, 6, 6, 6, 6, 6, 6}; /* 30 - 36 */ +#elif SIZEOF_LONG == 8 +/* [int(math.floor(math.log(2**64, i))) for i in range(2, 37)] */ +static int digitlimit[] = { + 0, 0, 64, 40, 32, 27, 24, 22, 21, 20, /* 0 - 9 */ + 19, 18, 17, 17, 16, 16, 16, 15, 15, 15, /* 10 - 19 */ + 14, 14, 14, 14, 13, 13, 13, 13, 13, 13, /* 20 - 29 */ + 13, 12, 12, 12, 12, 12, 12}; /* 30 - 36 */ +#else +#error "Need table for SIZEOF_LONG" +#endif + +/* +** strtoul +** This is a general purpose routine for converting +** an ascii string to an integer in an arbitrary base. +** Leading white space is ignored. If 'base' is zero +** it looks for a leading 0, 0b, 0B, 0o, 0O, 0x or 0X +** to tell which base. If these are absent it defaults +** to 10. Base must be 0 or between 2 and 36 (inclusive). +** If 'ptr' is non-NULL it will contain a pointer to +** the end of the scan. +** Errors due to bad pointers will probably result in +** exceptions - we don't check for them. +*/ +unsigned long +PyOS_strtoul(register char *str, char **ptr, int base) +{ + register unsigned long result = 0; /* return value of the function */ + register int c; /* current input character */ + register int ovlimit; /* required digits to overflow */ + + /* skip leading white space */ + while (*str && isspace(Py_CHARMASK(*str))) + ++str; + + /* check for leading 0 or 0x for auto-base or base 16 */ + switch (base) { + case 0: /* look for leading 0, 0b, 0o or 0x */ + if (*str == '0') { + ++str; + if (*str == 'x' || *str == 'X') { + /* there must be at least one digit after 0x */ + if (_PyLong_DigitValue[Py_CHARMASK(str[1])] >= 16) { + if (ptr) + *ptr = str; + return 0; + } + ++str; + base = 16; + } else if (*str == 'o' || *str == 'O') { + /* there must be at least one digit after 0o */ + if (_PyLong_DigitValue[Py_CHARMASK(str[1])] >= 8) { + if (ptr) + *ptr = str; + return 0; + } + ++str; + base = 8; + } else if (*str == 'b' || *str == 'B') { + /* there must be at least one digit after 0b */ + if (_PyLong_DigitValue[Py_CHARMASK(str[1])] >= 2) { + if (ptr) + *ptr = str; + return 0; + } + ++str; + base = 2; + } else { + base = 8; + } + } + else + base = 10; + break; + + case 2: /* skip leading 0b or 0B */ + if (*str == '0') { + ++str; + if (*str == 'b' || *str == 'B') { + /* there must be at least one digit after 0b */ + if (_PyLong_DigitValue[Py_CHARMASK(str[1])] >= 2) { + if (ptr) + *ptr = str; + return 0; + } + ++str; + } + } + break; + + case 8: /* skip leading 0o or 0O */ + if (*str == '0') { + ++str; + if (*str == 'o' || *str == 'O') { + /* there must be at least one digit after 0o */ + if (_PyLong_DigitValue[Py_CHARMASK(str[1])] >= 8) { + if (ptr) + *ptr = str; + return 0; + } + ++str; + } + } + break; + + case 16: /* skip leading 0x or 0X */ + if (*str == '0') { + ++str; + if (*str == 'x' || *str == 'X') { + /* there must be at least one digit after 0x */ + if (_PyLong_DigitValue[Py_CHARMASK(str[1])] >= 16) { + if (ptr) + *ptr = str; + return 0; + } + ++str; + } + } + break; + } + + /* catch silly bases */ + if (base < 2 || base > 36) { + if (ptr) + *ptr = str; + return 0; + } + + /* skip leading zeroes */ + while (*str == '0') + ++str; + + /* base is guaranteed to be in [2, 36] at this point */ + ovlimit = digitlimit[base]; + + /* do the conversion until non-digit character encountered */ + while ((c = _PyLong_DigitValue[Py_CHARMASK(*str)]) < base) { + if (ovlimit > 0) /* no overflow check required */ + result = result * base + c; + else { /* requires overflow check */ + register unsigned long temp_result; + + if (ovlimit < 0) /* guaranteed overflow */ + goto overflowed; + + /* there could be an overflow */ + /* check overflow just from shifting */ + if (result > smallmax[base]) + goto overflowed; + + result *= base; + + /* check overflow from the digit's value */ + temp_result = result + c; + if (temp_result < result) + goto overflowed; + + result = temp_result; + } + + ++str; + --ovlimit; + } + + /* set pointer to point to the last character scanned */ + if (ptr) + *ptr = str; + + return result; + +overflowed: + if (ptr) { + /* spool through remaining digit characters */ + while (_PyLong_DigitValue[Py_CHARMASK(*str)] < base) + ++str; + *ptr = str; + } + errno = ERANGE; + return (unsigned long)-1; +} + +/* Checking for overflow in PyOS_strtol is a PITA; see comments + * about PY_ABS_LONG_MIN in longobject.c. + */ +#define PY_ABS_LONG_MIN (0-(unsigned long)LONG_MIN) + +long +PyOS_strtol(char *str, char **ptr, int base) +{ + long result; + unsigned long uresult; + char sign; + + while (*str && isspace(Py_CHARMASK(*str))) + str++; + + sign = *str; + if (sign == '+' || sign == '-') + str++; + + uresult = PyOS_strtoul(str, ptr, base); + + if (uresult <= (unsigned long)LONG_MAX) { + result = (long)uresult; + if (sign == '-') + result = -result; + } + else if (sign == '-' && uresult == PY_ABS_LONG_MIN) { + result = LONG_MIN; + } + else { + errno = ERANGE; + result = LONG_MAX; + } + return result; +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/peephole.c b/AppPkg/Applications/Python/Python-2.7.10/Python/peephole.c new file mode 100644 index 0000000000..54404a3525 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/peephole.c @@ -0,0 +1,667 @@ +/* Peephole optimizations for bytecode compiler. */ + +#include "Python.h" + +#include "Python-ast.h" +#include "node.h" +#include "pyarena.h" +#include "ast.h" +#include "code.h" +#include "compile.h" +#include "symtable.h" +#include "opcode.h" + +#define GETARG(arr, i) ((int)((arr[i+2]<<8) + arr[i+1])) +#define UNCONDITIONAL_JUMP(op) (op==JUMP_ABSOLUTE || op==JUMP_FORWARD) +#define CONDITIONAL_JUMP(op) (op==POP_JUMP_IF_FALSE || op==POP_JUMP_IF_TRUE \ + || op==JUMP_IF_FALSE_OR_POP || op==JUMP_IF_TRUE_OR_POP) +#define ABSOLUTE_JUMP(op) (op==JUMP_ABSOLUTE || op==CONTINUE_LOOP \ + || op==POP_JUMP_IF_FALSE || op==POP_JUMP_IF_TRUE \ + || op==JUMP_IF_FALSE_OR_POP || op==JUMP_IF_TRUE_OR_POP) +#define JUMPS_ON_TRUE(op) (op==POP_JUMP_IF_TRUE || op==JUMP_IF_TRUE_OR_POP) +#define GETJUMPTGT(arr, i) (GETARG(arr,i) + (ABSOLUTE_JUMP(arr[i]) ? 0 : i+3)) +#define SETARG(arr, i, val) arr[i+2] = val>>8; arr[i+1] = val & 255 +#define CODESIZE(op) (HAS_ARG(op) ? 3 : 1) +#define ISBASICBLOCK(blocks, start, bytes) \ + (blocks[start]==blocks[start+bytes-1]) + +/* Replace LOAD_CONST c1. LOAD_CONST c2 ... LOAD_CONST cn BUILD_TUPLE n + with LOAD_CONST (c1, c2, ... cn). + The consts table must still be in list form so that the + new constant (c1, c2, ... cn) can be appended. + Called with codestr pointing to the first LOAD_CONST. + Bails out with no change if one or more of the LOAD_CONSTs is missing. + Also works for BUILD_LIST when followed by an "in" or "not in" test. +*/ +static int +tuple_of_constants(unsigned char *codestr, Py_ssize_t n, PyObject *consts) +{ + PyObject *newconst, *constant; + Py_ssize_t i, arg, len_consts; + + /* Pre-conditions */ + assert(PyList_CheckExact(consts)); + assert(codestr[n*3] == BUILD_TUPLE || codestr[n*3] == BUILD_LIST); + assert(GETARG(codestr, (n*3)) == n); + for (i=0 ; i 20) { + Py_DECREF(newconst); + return 0; + } + + /* Append folded constant into consts table */ + len_consts = PyList_GET_SIZE(consts); + if (PyList_Append(consts, newconst)) { + Py_DECREF(newconst); + return 0; + } + Py_DECREF(newconst); + + /* Write NOP NOP NOP NOP LOAD_CONST newconst */ + memset(codestr, NOP, 4); + codestr[4] = LOAD_CONST; + SETARG(codestr, 4, len_consts); + return 1; +} + +static int +fold_unaryops_on_constants(unsigned char *codestr, PyObject *consts) +{ + PyObject *newconst=NULL, *v; + Py_ssize_t len_consts; + int opcode; + + /* Pre-conditions */ + assert(PyList_CheckExact(consts)); + assert(codestr[0] == LOAD_CONST); + + /* Create new constant */ + v = PyList_GET_ITEM(consts, GETARG(codestr, 0)); + opcode = codestr[3]; + switch (opcode) { + case UNARY_NEGATIVE: + /* Preserve the sign of -0.0 */ + if (PyObject_IsTrue(v) == 1) + newconst = PyNumber_Negative(v); + break; + case UNARY_CONVERT: + newconst = PyObject_Repr(v); + break; + case UNARY_INVERT: + newconst = PyNumber_Invert(v); + break; + default: + /* Called with an unknown opcode */ + PyErr_Format(PyExc_SystemError, + "unexpected unary operation %d on a constant", + opcode); + return 0; + } + if (newconst == NULL) { + PyErr_Clear(); + return 0; + } + + /* Append folded constant into consts table */ + len_consts = PyList_GET_SIZE(consts); + if (PyList_Append(consts, newconst)) { + Py_DECREF(newconst); + return 0; + } + Py_DECREF(newconst); + + /* Write NOP LOAD_CONST newconst */ + codestr[0] = NOP; + codestr[1] = LOAD_CONST; + SETARG(codestr, 1, len_consts); + return 1; +} + +static unsigned int * +markblocks(unsigned char *code, Py_ssize_t len) +{ + unsigned int *blocks = PyMem_New(unsigned int, len); + int i,j, opcode, blockcnt = 0; + + if (blocks == NULL) { + PyErr_NoMemory(); + return NULL; + } + memset(blocks, 0, len*sizeof(int)); + + /* Mark labels in the first pass */ + for (i=0 ; i= 255. + + Optimizations are restricted to simple transformations occuring within a + single basic block. All transformations keep the code size the same or + smaller. For those that reduce size, the gaps are initially filled with + NOPs. Later those NOPs are removed and the jump addresses retargeted in + a single pass. Line numbering is adjusted accordingly. */ + +PyObject * +PyCode_Optimize(PyObject *code, PyObject* consts, PyObject *names, + PyObject *lineno_obj) +{ + Py_ssize_t i, j, codelen; + int nops, h, adj; + int tgt, tgttgt, opcode; + unsigned char *codestr = NULL; + unsigned char *lineno; + int *addrmap = NULL; + int new_line, cum_orig_line, last_line, tabsiz; + int cumlc=0, lastlc=0; /* Count runs of consecutive LOAD_CONSTs */ + unsigned int *blocks = NULL; + char *name; + + /* Bail out if an exception is set */ + if (PyErr_Occurred()) + goto exitError; + + /* Bypass optimization when the lineno table is too complex */ + assert(PyString_Check(lineno_obj)); + lineno = (unsigned char*)PyString_AS_STRING(lineno_obj); + tabsiz = PyString_GET_SIZE(lineno_obj); + if (memchr(lineno, 255, tabsiz) != NULL) + goto exitUnchanged; + + /* Avoid situations where jump retargeting could overflow */ + assert(PyString_Check(code)); + codelen = PyString_GET_SIZE(code); + if (codelen > 32700) + goto exitUnchanged; + + /* Make a modifiable copy of the code string */ + codestr = (unsigned char *)PyMem_Malloc(codelen); + if (codestr == NULL) + goto exitError; + codestr = (unsigned char *)memcpy(codestr, + PyString_AS_STRING(code), codelen); + + /* Verify that RETURN_VALUE terminates the codestring. This allows + the various transformation patterns to look ahead several + instructions without additional checks to make sure they are not + looking beyond the end of the code string. + */ + if (codestr[codelen-1] != RETURN_VALUE) + goto exitUnchanged; + + /* Mapping to new jump targets after NOPs are removed */ + addrmap = PyMem_New(int, codelen); + if (addrmap == NULL) { + PyErr_NoMemory(); + goto exitError; + } + + blocks = markblocks(codestr, codelen); + if (blocks == NULL) + goto exitError; + assert(PyList_Check(consts)); + + for (i=0 ; i a is not b + not a in b --> a not in b + not a is not b --> a is b + not a not in b --> a in b + */ + case COMPARE_OP: + j = GETARG(codestr, i); + if (j < 6 || j > 9 || + codestr[i+3] != UNARY_NOT || + !ISBASICBLOCK(blocks,i,4)) + continue; + SETARG(codestr, i, (j^1)); + codestr[i+3] = NOP; + break; + + /* Replace LOAD_GLOBAL/LOAD_NAME None + with LOAD_CONST None */ + case LOAD_NAME: + case LOAD_GLOBAL: + j = GETARG(codestr, i); + name = PyString_AsString(PyTuple_GET_ITEM(names, j)); + if (name == NULL || strcmp(name, "None") != 0) + continue; + for (j=0 ; j < PyList_GET_SIZE(consts) ; j++) { + if (PyList_GET_ITEM(consts, j) == Py_None) + break; + } + if (j == PyList_GET_SIZE(consts)) { + if (PyList_Append(consts, Py_None) == -1) + goto exitError; + } + assert(PyList_GET_ITEM(consts, j) == Py_None); + codestr[i] = LOAD_CONST; + SETARG(codestr, i, j); + cumlc = lastlc + 1; + break; + + /* Skip over LOAD_CONST trueconst + POP_JUMP_IF_FALSE xx. This improves + "while 1" performance. */ + case LOAD_CONST: + cumlc = lastlc + 1; + j = GETARG(codestr, i); + if (codestr[i+3] != POP_JUMP_IF_FALSE || + !ISBASICBLOCK(blocks,i,6) || + !PyObject_IsTrue(PyList_GET_ITEM(consts, j))) + continue; + memset(codestr+i, NOP, 6); + cumlc = 0; + break; + + /* Try to fold tuples of constants (includes a case for lists + which are only used for "in" and "not in" tests). + Skip over BUILD_SEQN 1 UNPACK_SEQN 1. + Replace BUILD_SEQN 2 UNPACK_SEQN 2 with ROT2. + Replace BUILD_SEQN 3 UNPACK_SEQN 3 with ROT3 ROT2. */ + case BUILD_TUPLE: + case BUILD_LIST: + j = GETARG(codestr, i); + h = i - 3 * j; + if (h >= 0 && + j <= lastlc && + ((opcode == BUILD_TUPLE && + ISBASICBLOCK(blocks, h, 3*(j+1))) || + (opcode == BUILD_LIST && + codestr[i+3]==COMPARE_OP && + ISBASICBLOCK(blocks, h, 3*(j+2)) && + (GETARG(codestr,i+3)==6 || + GETARG(codestr,i+3)==7))) && + tuple_of_constants(&codestr[h], j, consts)) { + assert(codestr[i] == LOAD_CONST); + cumlc = 1; + break; + } + if (codestr[i+3] != UNPACK_SEQUENCE || + !ISBASICBLOCK(blocks,i,6) || + j != GETARG(codestr, i+3)) + continue; + if (j == 1) { + memset(codestr+i, NOP, 6); + } else if (j == 2) { + codestr[i] = ROT_TWO; + memset(codestr+i+1, NOP, 5); + } else if (j == 3) { + codestr[i] = ROT_THREE; + codestr[i+1] = ROT_TWO; + memset(codestr+i+2, NOP, 4); + } + break; + + /* Fold binary ops on constants. + LOAD_CONST c1 LOAD_CONST c2 BINOP --> LOAD_CONST binop(c1,c2) */ + case BINARY_POWER: + case BINARY_MULTIPLY: + case BINARY_TRUE_DIVIDE: + case BINARY_FLOOR_DIVIDE: + case BINARY_MODULO: + case BINARY_ADD: + case BINARY_SUBTRACT: + case BINARY_SUBSCR: + case BINARY_LSHIFT: + case BINARY_RSHIFT: + case BINARY_AND: + case BINARY_XOR: + case BINARY_OR: + if (lastlc >= 2 && + ISBASICBLOCK(blocks, i-6, 7) && + fold_binops_on_constants(&codestr[i-6], consts)) { + i -= 2; + assert(codestr[i] == LOAD_CONST); + cumlc = 1; + } + break; + + /* Fold unary ops on constants. + LOAD_CONST c1 UNARY_OP --> LOAD_CONST unary_op(c) */ + case UNARY_NEGATIVE: + case UNARY_CONVERT: + case UNARY_INVERT: + if (lastlc >= 1 && + ISBASICBLOCK(blocks, i-3, 4) && + fold_unaryops_on_constants(&codestr[i-3], consts)) { + i -= 2; + assert(codestr[i] == LOAD_CONST); + cumlc = 1; + } + break; + + /* Simplify conditional jump to conditional jump where the + result of the first test implies the success of a similar + test or the failure of the opposite test. + Arises in code like: + "if a and b:" + "if a or b:" + "a and b or c" + "(a and b) and c" + x:JUMP_IF_FALSE_OR_POP y y:JUMP_IF_FALSE_OR_POP z + --> x:JUMP_IF_FALSE_OR_POP z + x:JUMP_IF_FALSE_OR_POP y y:JUMP_IF_TRUE_OR_POP z + --> x:POP_JUMP_IF_FALSE y+3 + where y+3 is the instruction following the second test. + */ + case JUMP_IF_FALSE_OR_POP: + case JUMP_IF_TRUE_OR_POP: + tgt = GETJUMPTGT(codestr, i); + j = codestr[tgt]; + if (CONDITIONAL_JUMP(j)) { + /* NOTE: all possible jumps here are absolute! */ + if (JUMPS_ON_TRUE(j) == JUMPS_ON_TRUE(opcode)) { + /* The second jump will be + taken iff the first is. */ + tgttgt = GETJUMPTGT(codestr, tgt); + /* The current opcode inherits + its target's stack behaviour */ + codestr[i] = j; + SETARG(codestr, i, tgttgt); + goto reoptimize_current; + } else { + /* The second jump is not taken if the first is (so + jump past it), and all conditional jumps pop their + argument when they're not taken (so change the + first jump to pop its argument when it's taken). */ + if (JUMPS_ON_TRUE(opcode)) + codestr[i] = POP_JUMP_IF_TRUE; + else + codestr[i] = POP_JUMP_IF_FALSE; + SETARG(codestr, i, (tgt + 3)); + goto reoptimize_current; + } + } + /* Intentional fallthrough */ + + /* Replace jumps to unconditional jumps */ + case POP_JUMP_IF_FALSE: + case POP_JUMP_IF_TRUE: + case FOR_ITER: + case JUMP_FORWARD: + case JUMP_ABSOLUTE: + case CONTINUE_LOOP: + case SETUP_LOOP: + case SETUP_EXCEPT: + case SETUP_FINALLY: + case SETUP_WITH: + tgt = GETJUMPTGT(codestr, i); + /* Replace JUMP_* to a RETURN into just a RETURN */ + if (UNCONDITIONAL_JUMP(opcode) && + codestr[tgt] == RETURN_VALUE) { + codestr[i] = RETURN_VALUE; + memset(codestr+i+1, NOP, 2); + continue; + } + if (!UNCONDITIONAL_JUMP(codestr[tgt])) + continue; + tgttgt = GETJUMPTGT(codestr, tgt); + if (opcode == JUMP_FORWARD) /* JMP_ABS can go backwards */ + opcode = JUMP_ABSOLUTE; + if (!ABSOLUTE_JUMP(opcode)) + tgttgt -= i + 3; /* Calc relative jump addr */ + if (tgttgt < 0) /* No backward relative jumps */ + continue; + codestr[i] = opcode; + SETARG(codestr, i, tgttgt); + break; + + case EXTENDED_ARG: + goto exitUnchanged; + + /* Replace RETURN LOAD_CONST None RETURN with just RETURN */ + /* Remove unreachable JUMPs after RETURN */ + case RETURN_VALUE: + if (i+4 >= codelen) + continue; + if (codestr[i+4] == RETURN_VALUE && + ISBASICBLOCK(blocks,i,5)) + memset(codestr+i+1, NOP, 4); + else if (UNCONDITIONAL_JUMP(codestr[i+1]) && + ISBASICBLOCK(blocks,i,4)) + memset(codestr+i+1, NOP, 3); + break; + } + } + + /* Fixup linenotab */ + for (i=0, nops=0 ; iab_size = size; + b->ab_mem = (void *)(b + 1); + b->ab_next = NULL; + b->ab_offset = ROUNDUP((Py_uintptr_t)(b->ab_mem)) - + (Py_uintptr_t)(b->ab_mem); + return b; +} + +static void +block_free(block *b) { + while (b) { + block *next = b->ab_next; + free(b); + b = next; + } +} + +static void * +block_alloc(block *b, size_t size) +{ + void *p; + assert(b); + size = ROUNDUP(size); + if (b->ab_offset + size > b->ab_size) { + /* If we need to allocate more memory than will fit in + the default block, allocate a one-off block that is + exactly the right size. */ + /* TODO(jhylton): Think about space waste at end of block */ + block *newbl = block_new( + size < DEFAULT_BLOCK_SIZE ? + DEFAULT_BLOCK_SIZE : size); + if (!newbl) + return NULL; + assert(!b->ab_next); + b->ab_next = newbl; + b = newbl; + } + + assert(b->ab_offset + size <= b->ab_size); + p = (void *)(((char *)b->ab_mem) + b->ab_offset); + b->ab_offset += size; + return p; +} + +PyArena * +PyArena_New() +{ + PyArena* arena = (PyArena *)malloc(sizeof(PyArena)); + if (!arena) + return (PyArena*)PyErr_NoMemory(); + + arena->a_head = block_new(DEFAULT_BLOCK_SIZE); + arena->a_cur = arena->a_head; + if (!arena->a_head) { + free((void *)arena); + return (PyArena*)PyErr_NoMemory(); + } + arena->a_objects = PyList_New(0); + if (!arena->a_objects) { + block_free(arena->a_head); + free((void *)arena); + return (PyArena*)PyErr_NoMemory(); + } +#if defined(Py_DEBUG) + arena->total_allocs = 0; + arena->total_size = 0; + arena->total_blocks = 1; + arena->total_block_size = DEFAULT_BLOCK_SIZE; + arena->total_big_blocks = 0; +#endif + return arena; +} + +void +PyArena_Free(PyArena *arena) +{ + assert(arena); +#if defined(Py_DEBUG) + /* + fprintf(stderr, + "alloc=%d size=%d blocks=%d block_size=%d big=%d objects=%d\n", + arena->total_allocs, arena->total_size, arena->total_blocks, + arena->total_block_size, arena->total_big_blocks, + PyList_Size(arena->a_objects)); + */ +#endif + block_free(arena->a_head); + /* This property normally holds, except when the code being compiled + is sys.getobjects(0), in which case there will be two references. + assert(arena->a_objects->ob_refcnt == 1); + */ + + Py_DECREF(arena->a_objects); + free(arena); +} + +void * +PyArena_Malloc(PyArena *arena, size_t size) +{ + void *p = block_alloc(arena->a_cur, size); + if (!p) + return PyErr_NoMemory(); +#if defined(Py_DEBUG) + arena->total_allocs++; + arena->total_size += size; +#endif + /* Reset cur if we allocated a new block. */ + if (arena->a_cur->ab_next) { + arena->a_cur = arena->a_cur->ab_next; +#if defined(Py_DEBUG) + arena->total_blocks++; + arena->total_block_size += arena->a_cur->ab_size; + if (arena->a_cur->ab_size > DEFAULT_BLOCK_SIZE) + ++arena->total_big_blocks; +#endif + } + return p; +} + +int +PyArena_AddPyObject(PyArena *arena, PyObject *obj) +{ + int r = PyList_Append(arena->a_objects, obj); + if (r >= 0) { + Py_DECREF(obj); + } + return r; +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/pyctype.c b/AppPkg/Applications/Python/Python-2.7.10/Python/pyctype.c new file mode 100644 index 0000000000..ea977b3d12 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/pyctype.c @@ -0,0 +1,214 @@ +#include "Python.h" + +/* Our own locale-independent ctype.h-like macros */ + +const unsigned int _Py_ctype_table[256] = { + 0, /* 0x0 '\x00' */ + 0, /* 0x1 '\x01' */ + 0, /* 0x2 '\x02' */ + 0, /* 0x3 '\x03' */ + 0, /* 0x4 '\x04' */ + 0, /* 0x5 '\x05' */ + 0, /* 0x6 '\x06' */ + 0, /* 0x7 '\x07' */ + 0, /* 0x8 '\x08' */ + PY_CTF_SPACE, /* 0x9 '\t' */ + PY_CTF_SPACE, /* 0xa '\n' */ + PY_CTF_SPACE, /* 0xb '\v' */ + PY_CTF_SPACE, /* 0xc '\f' */ + PY_CTF_SPACE, /* 0xd '\r' */ + 0, /* 0xe '\x0e' */ + 0, /* 0xf '\x0f' */ + 0, /* 0x10 '\x10' */ + 0, /* 0x11 '\x11' */ + 0, /* 0x12 '\x12' */ + 0, /* 0x13 '\x13' */ + 0, /* 0x14 '\x14' */ + 0, /* 0x15 '\x15' */ + 0, /* 0x16 '\x16' */ + 0, /* 0x17 '\x17' */ + 0, /* 0x18 '\x18' */ + 0, /* 0x19 '\x19' */ + 0, /* 0x1a '\x1a' */ + 0, /* 0x1b '\x1b' */ + 0, /* 0x1c '\x1c' */ + 0, /* 0x1d '\x1d' */ + 0, /* 0x1e '\x1e' */ + 0, /* 0x1f '\x1f' */ + PY_CTF_SPACE, /* 0x20 ' ' */ + 0, /* 0x21 '!' */ + 0, /* 0x22 '"' */ + 0, /* 0x23 '#' */ + 0, /* 0x24 '$' */ + 0, /* 0x25 '%' */ + 0, /* 0x26 '&' */ + 0, /* 0x27 "'" */ + 0, /* 0x28 '(' */ + 0, /* 0x29 ')' */ + 0, /* 0x2a '*' */ + 0, /* 0x2b '+' */ + 0, /* 0x2c ',' */ + 0, /* 0x2d '-' */ + 0, /* 0x2e '.' */ + 0, /* 0x2f '/' */ + PY_CTF_DIGIT|PY_CTF_XDIGIT, /* 0x30 '0' */ + PY_CTF_DIGIT|PY_CTF_XDIGIT, /* 0x31 '1' */ + PY_CTF_DIGIT|PY_CTF_XDIGIT, /* 0x32 '2' */ + PY_CTF_DIGIT|PY_CTF_XDIGIT, /* 0x33 '3' */ + PY_CTF_DIGIT|PY_CTF_XDIGIT, /* 0x34 '4' */ + PY_CTF_DIGIT|PY_CTF_XDIGIT, /* 0x35 '5' */ + PY_CTF_DIGIT|PY_CTF_XDIGIT, /* 0x36 '6' */ + PY_CTF_DIGIT|PY_CTF_XDIGIT, /* 0x37 '7' */ + PY_CTF_DIGIT|PY_CTF_XDIGIT, /* 0x38 '8' */ + PY_CTF_DIGIT|PY_CTF_XDIGIT, /* 0x39 '9' */ + 0, /* 0x3a ':' */ + 0, /* 0x3b ';' */ + 0, /* 0x3c '<' */ + 0, /* 0x3d '=' */ + 0, /* 0x3e '>' */ + 0, /* 0x3f '?' */ + 0, /* 0x40 '@' */ + PY_CTF_UPPER|PY_CTF_XDIGIT, /* 0x41 'A' */ + PY_CTF_UPPER|PY_CTF_XDIGIT, /* 0x42 'B' */ + PY_CTF_UPPER|PY_CTF_XDIGIT, /* 0x43 'C' */ + PY_CTF_UPPER|PY_CTF_XDIGIT, /* 0x44 'D' */ + PY_CTF_UPPER|PY_CTF_XDIGIT, /* 0x45 'E' */ + PY_CTF_UPPER|PY_CTF_XDIGIT, /* 0x46 'F' */ + PY_CTF_UPPER, /* 0x47 'G' */ + PY_CTF_UPPER, /* 0x48 'H' */ + PY_CTF_UPPER, /* 0x49 'I' */ + PY_CTF_UPPER, /* 0x4a 'J' */ + PY_CTF_UPPER, /* 0x4b 'K' */ + PY_CTF_UPPER, /* 0x4c 'L' */ + PY_CTF_UPPER, /* 0x4d 'M' */ + PY_CTF_UPPER, /* 0x4e 'N' */ + PY_CTF_UPPER, /* 0x4f 'O' */ + PY_CTF_UPPER, /* 0x50 'P' */ + PY_CTF_UPPER, /* 0x51 'Q' */ + PY_CTF_UPPER, /* 0x52 'R' */ + PY_CTF_UPPER, /* 0x53 'S' */ + PY_CTF_UPPER, /* 0x54 'T' */ + PY_CTF_UPPER, /* 0x55 'U' */ + PY_CTF_UPPER, /* 0x56 'V' */ + PY_CTF_UPPER, /* 0x57 'W' */ + PY_CTF_UPPER, /* 0x58 'X' */ + PY_CTF_UPPER, /* 0x59 'Y' */ + PY_CTF_UPPER, /* 0x5a 'Z' */ + 0, /* 0x5b '[' */ + 0, /* 0x5c '\\' */ + 0, /* 0x5d ']' */ + 0, /* 0x5e '^' */ + 0, /* 0x5f '_' */ + 0, /* 0x60 '`' */ + PY_CTF_LOWER|PY_CTF_XDIGIT, /* 0x61 'a' */ + PY_CTF_LOWER|PY_CTF_XDIGIT, /* 0x62 'b' */ + PY_CTF_LOWER|PY_CTF_XDIGIT, /* 0x63 'c' */ + PY_CTF_LOWER|PY_CTF_XDIGIT, /* 0x64 'd' */ + PY_CTF_LOWER|PY_CTF_XDIGIT, /* 0x65 'e' */ + PY_CTF_LOWER|PY_CTF_XDIGIT, /* 0x66 'f' */ + PY_CTF_LOWER, /* 0x67 'g' */ + PY_CTF_LOWER, /* 0x68 'h' */ + PY_CTF_LOWER, /* 0x69 'i' */ + PY_CTF_LOWER, /* 0x6a 'j' */ + PY_CTF_LOWER, /* 0x6b 'k' */ + PY_CTF_LOWER, /* 0x6c 'l' */ + PY_CTF_LOWER, /* 0x6d 'm' */ + PY_CTF_LOWER, /* 0x6e 'n' */ + PY_CTF_LOWER, /* 0x6f 'o' */ + PY_CTF_LOWER, /* 0x70 'p' */ + PY_CTF_LOWER, /* 0x71 'q' */ + PY_CTF_LOWER, /* 0x72 'r' */ + PY_CTF_LOWER, /* 0x73 's' */ + PY_CTF_LOWER, /* 0x74 't' */ + PY_CTF_LOWER, /* 0x75 'u' */ + PY_CTF_LOWER, /* 0x76 'v' */ + PY_CTF_LOWER, /* 0x77 'w' */ + PY_CTF_LOWER, /* 0x78 'x' */ + PY_CTF_LOWER, /* 0x79 'y' */ + PY_CTF_LOWER, /* 0x7a 'z' */ + 0, /* 0x7b '{' */ + 0, /* 0x7c '|' */ + 0, /* 0x7d '}' */ + 0, /* 0x7e '~' */ + 0, /* 0x7f '\x7f' */ + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, +}; + + +const unsigned char _Py_ctype_tolower[256] = { + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, + 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, + 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, + 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, + 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, + 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f, + 0x40, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67, + 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f, + 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77, + 0x78, 0x79, 0x7a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f, + 0x60, 0x61, 0x62, 0x63, 0x64, 0x65, 0x66, 0x67, + 0x68, 0x69, 0x6a, 0x6b, 0x6c, 0x6d, 0x6e, 0x6f, + 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77, + 0x78, 0x79, 0x7a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f, + 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, + 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f, + 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, + 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f, + 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7, + 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf, + 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7, + 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf, + 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7, + 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf, + 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7, + 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf, + 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7, + 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef, + 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7, + 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff, +}; + +const unsigned char _Py_ctype_toupper[256] = { + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, + 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, + 0x10, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x17, + 0x18, 0x19, 0x1a, 0x1b, 0x1c, 0x1d, 0x1e, 0x1f, + 0x20, 0x21, 0x22, 0x23, 0x24, 0x25, 0x26, 0x27, + 0x28, 0x29, 0x2a, 0x2b, 0x2c, 0x2d, 0x2e, 0x2f, + 0x30, 0x31, 0x32, 0x33, 0x34, 0x35, 0x36, 0x37, + 0x38, 0x39, 0x3a, 0x3b, 0x3c, 0x3d, 0x3e, 0x3f, + 0x40, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, + 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f, + 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57, + 0x58, 0x59, 0x5a, 0x5b, 0x5c, 0x5d, 0x5e, 0x5f, + 0x60, 0x41, 0x42, 0x43, 0x44, 0x45, 0x46, 0x47, + 0x48, 0x49, 0x4a, 0x4b, 0x4c, 0x4d, 0x4e, 0x4f, + 0x50, 0x51, 0x52, 0x53, 0x54, 0x55, 0x56, 0x57, + 0x58, 0x59, 0x5a, 0x7b, 0x7c, 0x7d, 0x7e, 0x7f, + 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87, + 0x88, 0x89, 0x8a, 0x8b, 0x8c, 0x8d, 0x8e, 0x8f, + 0x90, 0x91, 0x92, 0x93, 0x94, 0x95, 0x96, 0x97, + 0x98, 0x99, 0x9a, 0x9b, 0x9c, 0x9d, 0x9e, 0x9f, + 0xa0, 0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6, 0xa7, + 0xa8, 0xa9, 0xaa, 0xab, 0xac, 0xad, 0xae, 0xaf, + 0xb0, 0xb1, 0xb2, 0xb3, 0xb4, 0xb5, 0xb6, 0xb7, + 0xb8, 0xb9, 0xba, 0xbb, 0xbc, 0xbd, 0xbe, 0xbf, + 0xc0, 0xc1, 0xc2, 0xc3, 0xc4, 0xc5, 0xc6, 0xc7, + 0xc8, 0xc9, 0xca, 0xcb, 0xcc, 0xcd, 0xce, 0xcf, + 0xd0, 0xd1, 0xd2, 0xd3, 0xd4, 0xd5, 0xd6, 0xd7, + 0xd8, 0xd9, 0xda, 0xdb, 0xdc, 0xdd, 0xde, 0xdf, + 0xe0, 0xe1, 0xe2, 0xe3, 0xe4, 0xe5, 0xe6, 0xe7, + 0xe8, 0xe9, 0xea, 0xeb, 0xec, 0xed, 0xee, 0xef, + 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7, + 0xf8, 0xf9, 0xfa, 0xfb, 0xfc, 0xfd, 0xfe, 0xff, +}; + diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/pyfpe.c b/AppPkg/Applications/Python/Python-2.7.10/Python/pyfpe.c new file mode 100644 index 0000000000..46a61974f7 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/pyfpe.c @@ -0,0 +1,23 @@ +#include "pyconfig.h" +#include "pyfpe.h" +/* + * The signal handler for SIGFPE is actually declared in an external + * module fpectl, or as preferred by the user. These variable + * definitions are required in order to compile Python without + * getting missing externals, but to actually handle SIGFPE requires + * defining a handler and enabling generation of SIGFPE. + */ + +#ifdef WANT_SIGFPE_HANDLER +jmp_buf PyFPE_jbuf; +int PyFPE_counter = 0; +#endif + +/* Have this outside the above #ifdef, since some picky ANSI compilers issue a + warning when compiling an empty file. */ + +double +PyFPE_dummy(void *dummy) +{ + return 1.0; +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/pymath.c b/AppPkg/Applications/Python/Python-2.7.10/Python/pymath.c new file mode 100644 index 0000000000..8085bdee20 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/pymath.c @@ -0,0 +1,79 @@ +#include "Python.h" + +#ifdef X87_DOUBLE_ROUNDING +/* On x86 platforms using an x87 FPU, this function is called from the + Py_FORCE_DOUBLE macro (defined in pymath.h) to force a floating-point + number out of an 80-bit x87 FPU register and into a 64-bit memory location, + thus rounding from extended precision to double precision. */ +double _Py_force_double(double x) +{ + volatile double y; + y = x; + return y; +} +#endif + +#ifdef HAVE_GCC_ASM_FOR_X87 + +/* inline assembly for getting and setting the 387 FPU control word on + gcc/x86 */ + +unsigned short _Py_get_387controlword(void) { + unsigned short cw; + __asm__ __volatile__ ("fnstcw %0" : "=m" (cw)); + return cw; +} + +void _Py_set_387controlword(unsigned short cw) { + __asm__ __volatile__ ("fldcw %0" : : "m" (cw)); +} + +#endif + + +#ifndef HAVE_HYPOT +double hypot(double x, double y) +{ + double yx; + + x = fabs(x); + y = fabs(y); + if (x < y) { + double temp = x; + x = y; + y = temp; + } + if (x == 0.) + return 0.; + else { + yx = y/x; + return x*sqrt(1.+yx*yx); + } +} +#endif /* HAVE_HYPOT */ + +#ifndef HAVE_COPYSIGN +double +copysign(double x, double y) +{ + /* use atan2 to distinguish -0. from 0. */ + if (y > 0. || (y == 0. && atan2(y, -1.) > 0.)) { + return fabs(x); + } else { + return -fabs(x); + } +} +#endif /* HAVE_COPYSIGN */ + +#ifndef HAVE_ROUND +double +round(double x) +{ + double absx, y; + absx = fabs(x); + y = floor(absx); + if (absx - y >= 0.5) + y += 1.0; + return copysign(y, x); +} +#endif /* HAVE_ROUND */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/pystate.c b/AppPkg/Applications/Python/Python-2.7.10/Python/pystate.c new file mode 100644 index 0000000000..3f8a1eec90 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/pystate.c @@ -0,0 +1,665 @@ + +/* Thread and interpreter state structures and their interfaces */ + +#include "Python.h" + +/* -------------------------------------------------------------------------- +CAUTION + +Always use malloc() and free() directly in this file. A number of these +functions are advertised as safe to call when the GIL isn't held, and in +a debug build Python redirects (e.g.) PyMem_NEW (etc) to Python's debugging +obmalloc functions. Those aren't thread-safe (they rely on the GIL to avoid +the expense of doing their own locking). +-------------------------------------------------------------------------- */ + +#ifdef HAVE_DLOPEN +#ifdef HAVE_DLFCN_H +#include +#endif +#ifndef RTLD_LAZY +#define RTLD_LAZY 1 +#endif +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +#ifdef WITH_THREAD +#include "pythread.h" +static PyThread_type_lock head_mutex = NULL; /* Protects interp->tstate_head */ +#define HEAD_INIT() (void)(head_mutex || (head_mutex = PyThread_allocate_lock())) +#define HEAD_LOCK() PyThread_acquire_lock(head_mutex, WAIT_LOCK) +#define HEAD_UNLOCK() PyThread_release_lock(head_mutex) + +/* The single PyInterpreterState used by this process' + GILState implementation +*/ +static PyInterpreterState *autoInterpreterState = NULL; +static int autoTLSkey = 0; +#else +#define HEAD_INIT() /* Nothing */ +#define HEAD_LOCK() /* Nothing */ +#define HEAD_UNLOCK() /* Nothing */ +#endif + +static PyInterpreterState *interp_head = NULL; + +PyThreadState *_PyThreadState_Current = NULL; +PyThreadFrameGetter _PyThreadState_GetFrame = NULL; + +#ifdef WITH_THREAD +static void _PyGILState_NoteThreadState(PyThreadState* tstate); +#endif + + +PyInterpreterState * +PyInterpreterState_New(void) +{ + PyInterpreterState *interp = (PyInterpreterState *) + malloc(sizeof(PyInterpreterState)); + + if (interp != NULL) { + HEAD_INIT(); +#ifdef WITH_THREAD + if (head_mutex == NULL) + Py_FatalError("Can't initialize threads for interpreter"); +#endif + interp->modules = NULL; + interp->modules_reloading = NULL; + interp->sysdict = NULL; + interp->builtins = NULL; + interp->tstate_head = NULL; + interp->codec_search_path = NULL; + interp->codec_search_cache = NULL; + interp->codec_error_registry = NULL; +#ifdef HAVE_DLOPEN +#ifdef RTLD_NOW + interp->dlopenflags = RTLD_NOW; +#else + interp->dlopenflags = RTLD_LAZY; +#endif +#endif +#ifdef WITH_TSC + interp->tscdump = 0; +#endif + + HEAD_LOCK(); + interp->next = interp_head; + interp_head = interp; + HEAD_UNLOCK(); + } + + return interp; +} + + +void +PyInterpreterState_Clear(PyInterpreterState *interp) +{ + PyThreadState *p; + HEAD_LOCK(); + for (p = interp->tstate_head; p != NULL; p = p->next) + PyThreadState_Clear(p); + HEAD_UNLOCK(); + Py_CLEAR(interp->codec_search_path); + Py_CLEAR(interp->codec_search_cache); + Py_CLEAR(interp->codec_error_registry); + Py_CLEAR(interp->modules); + Py_CLEAR(interp->modules_reloading); + Py_CLEAR(interp->sysdict); + Py_CLEAR(interp->builtins); +} + + +static void +zapthreads(PyInterpreterState *interp) +{ + PyThreadState *p; + /* No need to lock the mutex here because this should only happen + when the threads are all really dead (XXX famous last words). */ + while ((p = interp->tstate_head) != NULL) { + PyThreadState_Delete(p); + } +} + + +void +PyInterpreterState_Delete(PyInterpreterState *interp) +{ + PyInterpreterState **p; + zapthreads(interp); + HEAD_LOCK(); + for (p = &interp_head; ; p = &(*p)->next) { + if (*p == NULL) + Py_FatalError( + "PyInterpreterState_Delete: invalid interp"); + if (*p == interp) + break; + } + if (interp->tstate_head != NULL) + Py_FatalError("PyInterpreterState_Delete: remaining threads"); + *p = interp->next; + HEAD_UNLOCK(); + free(interp); +} + + +/* Default implementation for _PyThreadState_GetFrame */ +static struct _frame * +threadstate_getframe(PyThreadState *self) +{ + return self->frame; +} + +static PyThreadState * +new_threadstate(PyInterpreterState *interp, int init) +{ + PyThreadState *tstate = (PyThreadState *)malloc(sizeof(PyThreadState)); + + if (_PyThreadState_GetFrame == NULL) + _PyThreadState_GetFrame = threadstate_getframe; + + if (tstate != NULL) { + tstate->interp = interp; + + tstate->frame = NULL; + tstate->recursion_depth = 0; + tstate->tracing = 0; + tstate->use_tracing = 0; + tstate->tick_counter = 0; + tstate->gilstate_counter = 0; + tstate->async_exc = NULL; +#ifdef WITH_THREAD + tstate->thread_id = PyThread_get_thread_ident(); +#else + tstate->thread_id = 0; +#endif + + tstate->dict = NULL; + + tstate->curexc_type = NULL; + tstate->curexc_value = NULL; + tstate->curexc_traceback = NULL; + + tstate->exc_type = NULL; + tstate->exc_value = NULL; + tstate->exc_traceback = NULL; + + tstate->c_profilefunc = NULL; + tstate->c_tracefunc = NULL; + tstate->c_profileobj = NULL; + tstate->c_traceobj = NULL; + + tstate->trash_delete_nesting = 0; + tstate->trash_delete_later = NULL; + + if (init) + _PyThreadState_Init(tstate); + + HEAD_LOCK(); + tstate->next = interp->tstate_head; + interp->tstate_head = tstate; + HEAD_UNLOCK(); + } + + return tstate; +} + +PyThreadState * +PyThreadState_New(PyInterpreterState *interp) +{ + return new_threadstate(interp, 1); +} + +PyThreadState * +_PyThreadState_Prealloc(PyInterpreterState *interp) +{ + return new_threadstate(interp, 0); +} + +void +_PyThreadState_Init(PyThreadState *tstate) +{ +#ifdef WITH_THREAD + _PyGILState_NoteThreadState(tstate); +#endif +} + +void +PyThreadState_Clear(PyThreadState *tstate) +{ + if (Py_VerboseFlag && tstate->frame != NULL) + fprintf(stderr, + "PyThreadState_Clear: warning: thread still has a frame\n"); + + Py_CLEAR(tstate->frame); + + Py_CLEAR(tstate->dict); + Py_CLEAR(tstate->async_exc); + + Py_CLEAR(tstate->curexc_type); + Py_CLEAR(tstate->curexc_value); + Py_CLEAR(tstate->curexc_traceback); + + Py_CLEAR(tstate->exc_type); + Py_CLEAR(tstate->exc_value); + Py_CLEAR(tstate->exc_traceback); + + tstate->c_profilefunc = NULL; + tstate->c_tracefunc = NULL; + Py_CLEAR(tstate->c_profileobj); + Py_CLEAR(tstate->c_traceobj); +} + + +/* Common code for PyThreadState_Delete() and PyThreadState_DeleteCurrent() */ +static void +tstate_delete_common(PyThreadState *tstate) +{ + PyInterpreterState *interp; + PyThreadState **p; + PyThreadState *prev_p = NULL; + if (tstate == NULL) + Py_FatalError("PyThreadState_Delete: NULL tstate"); + interp = tstate->interp; + if (interp == NULL) + Py_FatalError("PyThreadState_Delete: NULL interp"); + HEAD_LOCK(); + for (p = &interp->tstate_head; ; p = &(*p)->next) { + if (*p == NULL) + Py_FatalError( + "PyThreadState_Delete: invalid tstate"); + if (*p == tstate) + break; + /* Sanity check. These states should never happen but if + * they do we must abort. Otherwise we'll end up spinning in + * in a tight loop with the lock held. A similar check is done + * in thread.c find_key(). */ + if (*p == prev_p) + Py_FatalError( + "PyThreadState_Delete: small circular list(!)" + " and tstate not found."); + prev_p = *p; + if ((*p)->next == interp->tstate_head) + Py_FatalError( + "PyThreadState_Delete: circular list(!) and" + " tstate not found."); + } + *p = tstate->next; + HEAD_UNLOCK(); + free(tstate); +} + + +void +PyThreadState_Delete(PyThreadState *tstate) +{ + if (tstate == _PyThreadState_Current) + Py_FatalError("PyThreadState_Delete: tstate is still current"); + tstate_delete_common(tstate); +#ifdef WITH_THREAD + if (autoInterpreterState && PyThread_get_key_value(autoTLSkey) == tstate) + PyThread_delete_key_value(autoTLSkey); +#endif /* WITH_THREAD */ +} + + +#ifdef WITH_THREAD +void +PyThreadState_DeleteCurrent() +{ + PyThreadState *tstate = _PyThreadState_Current; + if (tstate == NULL) + Py_FatalError( + "PyThreadState_DeleteCurrent: no current tstate"); + _PyThreadState_Current = NULL; + if (autoInterpreterState && PyThread_get_key_value(autoTLSkey) == tstate) + PyThread_delete_key_value(autoTLSkey); + tstate_delete_common(tstate); + PyEval_ReleaseLock(); +} +#endif /* WITH_THREAD */ + + +PyThreadState * +PyThreadState_Get(void) +{ + if (_PyThreadState_Current == NULL) + Py_FatalError("PyThreadState_Get: no current thread"); + + return _PyThreadState_Current; +} + + +PyThreadState * +PyThreadState_Swap(PyThreadState *newts) +{ + PyThreadState *oldts = _PyThreadState_Current; + + _PyThreadState_Current = newts; + /* It should not be possible for more than one thread state + to be used for a thread. Check this the best we can in debug + builds. + */ +#if defined(Py_DEBUG) && defined(WITH_THREAD) + if (newts) { + /* This can be called from PyEval_RestoreThread(). Similar + to it, we need to ensure errno doesn't change. + */ + int err = errno; + PyThreadState *check = PyGILState_GetThisThreadState(); + if (check && check->interp == newts->interp && check != newts) + Py_FatalError("Invalid thread state for this thread"); + errno = err; + } +#endif + return oldts; +} + +/* An extension mechanism to store arbitrary additional per-thread state. + PyThreadState_GetDict() returns a dictionary that can be used to hold such + state; the caller should pick a unique key and store its state there. If + PyThreadState_GetDict() returns NULL, an exception has *not* been raised + and the caller should assume no per-thread state is available. */ + +PyObject * +PyThreadState_GetDict(void) +{ + if (_PyThreadState_Current == NULL) + return NULL; + + if (_PyThreadState_Current->dict == NULL) { + PyObject *d; + _PyThreadState_Current->dict = d = PyDict_New(); + if (d == NULL) + PyErr_Clear(); + } + return _PyThreadState_Current->dict; +} + + +/* Asynchronously raise an exception in a thread. + Requested by Just van Rossum and Alex Martelli. + To prevent naive misuse, you must write your own extension + to call this, or use ctypes. Must be called with the GIL held. + Returns the number of tstates modified (normally 1, but 0 if `id` didn't + match any known thread id). Can be called with exc=NULL to clear an + existing async exception. This raises no exceptions. */ + +int +PyThreadState_SetAsyncExc(long id, PyObject *exc) { + PyThreadState *tstate = PyThreadState_GET(); + PyInterpreterState *interp = tstate->interp; + PyThreadState *p; + + /* Although the GIL is held, a few C API functions can be called + * without the GIL held, and in particular some that create and + * destroy thread and interpreter states. Those can mutate the + * list of thread states we're traversing, so to prevent that we lock + * head_mutex for the duration. + */ + HEAD_LOCK(); + for (p = interp->tstate_head; p != NULL; p = p->next) { + if (p->thread_id == id) { + /* Tricky: we need to decref the current value + * (if any) in p->async_exc, but that can in turn + * allow arbitrary Python code to run, including + * perhaps calls to this function. To prevent + * deadlock, we need to release head_mutex before + * the decref. + */ + PyObject *old_exc = p->async_exc; + Py_XINCREF(exc); + p->async_exc = exc; + HEAD_UNLOCK(); + Py_XDECREF(old_exc); + return 1; + } + } + HEAD_UNLOCK(); + return 0; +} + + +/* Routines for advanced debuggers, requested by David Beazley. + Don't use unless you know what you are doing! */ + +PyInterpreterState * +PyInterpreterState_Head(void) +{ + return interp_head; +} + +PyInterpreterState * +PyInterpreterState_Next(PyInterpreterState *interp) { + return interp->next; +} + +PyThreadState * +PyInterpreterState_ThreadHead(PyInterpreterState *interp) { + return interp->tstate_head; +} + +PyThreadState * +PyThreadState_Next(PyThreadState *tstate) { + return tstate->next; +} + +/* The implementation of sys._current_frames(). This is intended to be + called with the GIL held, as it will be when called via + sys._current_frames(). It's possible it would work fine even without + the GIL held, but haven't thought enough about that. +*/ +PyObject * +_PyThread_CurrentFrames(void) +{ + PyObject *result; + PyInterpreterState *i; + + result = PyDict_New(); + if (result == NULL) + return NULL; + + /* for i in all interpreters: + * for t in all of i's thread states: + * if t's frame isn't NULL, map t's id to its frame + * Because these lists can mutate even when the GIL is held, we + * need to grab head_mutex for the duration. + */ + HEAD_LOCK(); + for (i = interp_head; i != NULL; i = i->next) { + PyThreadState *t; + for (t = i->tstate_head; t != NULL; t = t->next) { + PyObject *id; + int stat; + struct _frame *frame = t->frame; + if (frame == NULL) + continue; + id = PyInt_FromLong(t->thread_id); + if (id == NULL) + goto Fail; + stat = PyDict_SetItem(result, id, (PyObject *)frame); + Py_DECREF(id); + if (stat < 0) + goto Fail; + } + } + HEAD_UNLOCK(); + return result; + + Fail: + HEAD_UNLOCK(); + Py_DECREF(result); + return NULL; +} + +/* Python "auto thread state" API. */ +#ifdef WITH_THREAD + +/* Keep this as a static, as it is not reliable! It can only + ever be compared to the state for the *current* thread. + * If not equal, then it doesn't matter that the actual + value may change immediately after comparison, as it can't + possibly change to the current thread's state. + * If equal, then the current thread holds the lock, so the value can't + change until we yield the lock. +*/ +static int +PyThreadState_IsCurrent(PyThreadState *tstate) +{ + /* Must be the tstate for this thread */ + assert(PyGILState_GetThisThreadState()==tstate); + /* On Windows at least, simple reads and writes to 32 bit values + are atomic. + */ + return tstate == _PyThreadState_Current; +} + +/* Internal initialization/finalization functions called by + Py_Initialize/Py_Finalize +*/ +void +_PyGILState_Init(PyInterpreterState *i, PyThreadState *t) +{ + assert(i && t); /* must init with valid states */ + autoTLSkey = PyThread_create_key(); + autoInterpreterState = i; + assert(PyThread_get_key_value(autoTLSkey) == NULL); + assert(t->gilstate_counter == 0); + + _PyGILState_NoteThreadState(t); +} + +void +_PyGILState_Fini(void) +{ + PyThread_delete_key(autoTLSkey); + autoInterpreterState = NULL; +} + +/* When a thread state is created for a thread by some mechanism other than + PyGILState_Ensure, it's important that the GILState machinery knows about + it so it doesn't try to create another thread state for the thread (this is + a better fix for SF bug #1010677 than the first one attempted). +*/ +static void +_PyGILState_NoteThreadState(PyThreadState* tstate) +{ + /* If autoTLSkey isn't initialized, this must be the very first + threadstate created in Py_Initialize(). Don't do anything for now + (we'll be back here when _PyGILState_Init is called). */ + if (!autoInterpreterState) + return; + + /* Stick the thread state for this thread in thread local storage. + + The only situation where you can legitimately have more than one + thread state for an OS level thread is when there are multiple + interpreters, when: + + a) You shouldn't really be using the PyGILState_ APIs anyway, + and: + + b) The slightly odd way PyThread_set_key_value works (see + comments by its implementation) means that the first thread + state created for that given OS level thread will "win", + which seems reasonable behaviour. + */ + if (PyThread_set_key_value(autoTLSkey, (void *)tstate) < 0) + Py_FatalError("Couldn't create autoTLSkey mapping"); + + /* PyGILState_Release must not try to delete this thread state. */ + tstate->gilstate_counter = 1; +} + +/* The public functions */ +PyThreadState * +PyGILState_GetThisThreadState(void) +{ + if (autoInterpreterState == NULL) + return NULL; + return (PyThreadState *)PyThread_get_key_value(autoTLSkey); +} + +PyGILState_STATE +PyGILState_Ensure(void) +{ + int current; + PyThreadState *tcur; + /* Note that we do not auto-init Python here - apart from + potential races with 2 threads auto-initializing, pep-311 + spells out other issues. Embedders are expected to have + called Py_Initialize() and usually PyEval_InitThreads(). + */ + assert(autoInterpreterState); /* Py_Initialize() hasn't been called! */ + tcur = (PyThreadState *)PyThread_get_key_value(autoTLSkey); + if (tcur == NULL) { + /* Create a new thread state for this thread */ + tcur = PyThreadState_New(autoInterpreterState); + if (tcur == NULL) + Py_FatalError("Couldn't create thread-state for new thread"); + /* This is our thread state! We'll need to delete it in the + matching call to PyGILState_Release(). */ + tcur->gilstate_counter = 0; + current = 0; /* new thread state is never current */ + } + else + current = PyThreadState_IsCurrent(tcur); + if (current == 0) + PyEval_RestoreThread(tcur); + /* Update our counter in the thread-state - no need for locks: + - tcur will remain valid as we hold the GIL. + - the counter is safe as we are the only thread "allowed" + to modify this value + */ + ++tcur->gilstate_counter; + return current ? PyGILState_LOCKED : PyGILState_UNLOCKED; +} + +void +PyGILState_Release(PyGILState_STATE oldstate) +{ + PyThreadState *tcur = (PyThreadState *)PyThread_get_key_value( + autoTLSkey); + if (tcur == NULL) + Py_FatalError("auto-releasing thread-state, " + "but no thread-state for this thread"); + /* We must hold the GIL and have our thread state current */ + /* XXX - remove the check - the assert should be fine, + but while this is very new (April 2003), the extra check + by release-only users can't hurt. + */ + if (! PyThreadState_IsCurrent(tcur)) + Py_FatalError("This thread state must be current when releasing"); + assert(PyThreadState_IsCurrent(tcur)); + --tcur->gilstate_counter; + assert(tcur->gilstate_counter >= 0); /* illegal counter value */ + + /* If we're going to destroy this thread-state, we must + * clear it while the GIL is held, as destructors may run. + */ + if (tcur->gilstate_counter == 0) { + /* can't have been locked when we created it */ + assert(oldstate == PyGILState_UNLOCKED); + PyThreadState_Clear(tcur); + /* Delete the thread-state. Note this releases the GIL too! + * It's vital that the GIL be held here, to avoid shutdown + * races; see bugs 225673 and 1061968 (that nasty bug has a + * habit of coming back). + */ + PyThreadState_DeleteCurrent(); + } + /* Release the lock if necessary */ + else if (oldstate == PyGILState_UNLOCKED) + PyEval_SaveThread(); +} + +#endif /* WITH_THREAD */ + +#ifdef __cplusplus +} +#endif + + diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/pystrcmp.c b/AppPkg/Applications/Python/Python-2.7.10/Python/pystrcmp.c new file mode 100644 index 0000000000..f1b12b4116 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/pystrcmp.c @@ -0,0 +1,26 @@ +/* Cross platform case insensitive string compare functions + */ + +#include "Python.h" + +int +PyOS_mystrnicmp(const char *s1, const char *s2, Py_ssize_t size) +{ + if (size == 0) + return 0; + while ((--size > 0) && + (tolower((unsigned)*s1) == tolower((unsigned)*s2))) { + if (!*s1++ || !*s2++) + break; + } + return tolower((unsigned)*s1) - tolower((unsigned)*s2); +} + +int +PyOS_mystricmp(const char *s1, const char *s2) +{ + while (*s1 && (tolower((unsigned)*s1++) == tolower((unsigned)*s2++))) { + ; + } + return (tolower((unsigned)*s1) - tolower((unsigned)*s2)); +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/pystrtod.c b/AppPkg/Applications/Python/Python-2.7.10/Python/pystrtod.c new file mode 100644 index 0000000000..3d925a1a36 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/pystrtod.c @@ -0,0 +1,1249 @@ +/* -*- Mode: C; c-file-style: "python" -*- */ + +#include +#include + +/* Case-insensitive string match used for nan and inf detection; t should be + lower-case. Returns 1 for a successful match, 0 otherwise. */ + +static int +case_insensitive_match(const char *s, const char *t) +{ + while(*t && Py_TOLOWER(*s) == *t) { + s++; + t++; + } + return *t ? 0 : 1; +} + +/* _Py_parse_inf_or_nan: Attempt to parse a string of the form "nan", "inf" or + "infinity", with an optional leading sign of "+" or "-". On success, + return the NaN or Infinity as a double and set *endptr to point just beyond + the successfully parsed portion of the string. On failure, return -1.0 and + set *endptr to point to the start of the string. */ + +double +_Py_parse_inf_or_nan(const char *p, char **endptr) +{ + double retval; + const char *s; + int negate = 0; + + s = p; + if (*s == '-') { + negate = 1; + s++; + } + else if (*s == '+') { + s++; + } + if (case_insensitive_match(s, "inf")) { + s += 3; + if (case_insensitive_match(s, "inity")) + s += 5; + retval = negate ? -Py_HUGE_VAL : Py_HUGE_VAL; + } +#ifdef Py_NAN + else if (case_insensitive_match(s, "nan")) { + s += 3; + retval = negate ? -Py_NAN : Py_NAN; + } +#endif + else { + s = p; + retval = -1.0; + } + *endptr = (char *)s; + return retval; +} + +/** + * PyOS_ascii_strtod: + * @nptr: the string to convert to a numeric value. + * @endptr: if non-%NULL, it returns the character after + * the last character used in the conversion. + * + * Converts a string to a #gdouble value. + * This function behaves like the standard strtod() function + * does in the C locale. It does this without actually + * changing the current locale, since that would not be + * thread-safe. + * + * This function is typically used when reading configuration + * files or other non-user input that should be locale independent. + * To handle input from the user you should normally use the + * locale-sensitive system strtod() function. + * + * If the correct value would cause overflow, plus or minus %HUGE_VAL + * is returned (according to the sign of the value), and %ERANGE is + * stored in %errno. If the correct value would cause underflow, + * zero is returned and %ERANGE is stored in %errno. + * If memory allocation fails, %ENOMEM is stored in %errno. + * + * This function resets %errno before calling strtod() so that + * you can reliably detect overflow and underflow. + * + * Return value: the #gdouble value. + **/ + +#ifndef PY_NO_SHORT_FLOAT_REPR + +double +_PyOS_ascii_strtod(const char *nptr, char **endptr) +{ + double result; + _Py_SET_53BIT_PRECISION_HEADER; + + assert(nptr != NULL); + /* Set errno to zero, so that we can distinguish zero results + and underflows */ + errno = 0; + + _Py_SET_53BIT_PRECISION_START; + result = _Py_dg_strtod(nptr, endptr); + _Py_SET_53BIT_PRECISION_END; + + if (*endptr == nptr) + /* string might represent an inf or nan */ + result = _Py_parse_inf_or_nan(nptr, endptr); + + return result; + +} + +#else + +/* + Use system strtod; since strtod is locale aware, we may + have to first fix the decimal separator. + + Note that unlike _Py_dg_strtod, the system strtod may not always give + correctly rounded results. +*/ + +double +_PyOS_ascii_strtod(const char *nptr, char **endptr) +{ + char *fail_pos; + double val = -1.0; + struct lconv *locale_data; + const char *decimal_point; + size_t decimal_point_len; + const char *p, *decimal_point_pos; + const char *end = NULL; /* Silence gcc */ + const char *digits_pos = NULL; + int negate = 0; + + assert(nptr != NULL); + + fail_pos = NULL; + + locale_data = localeconv(); + decimal_point = locale_data->decimal_point; + decimal_point_len = strlen(decimal_point); + + assert(decimal_point_len != 0); + + decimal_point_pos = NULL; + + /* Parse infinities and nans */ + val = _Py_parse_inf_or_nan(nptr, endptr); + if (*endptr != nptr) + return val; + + /* Set errno to zero, so that we can distinguish zero results + and underflows */ + errno = 0; + + /* We process the optional sign manually, then pass the remainder to + the system strtod. This ensures that the result of an underflow + has the correct sign. (bug #1725) */ + p = nptr; + /* Process leading sign, if present */ + if (*p == '-') { + negate = 1; + p++; + } + else if (*p == '+') { + p++; + } + + /* Some platform strtods accept hex floats; Python shouldn't (at the + moment), so we check explicitly for strings starting with '0x'. */ + if (*p == '0' && (*(p+1) == 'x' || *(p+1) == 'X')) + goto invalid_string; + + /* Check that what's left begins with a digit or decimal point */ + if (!Py_ISDIGIT(*p) && *p != '.') + goto invalid_string; + + digits_pos = p; + if (decimal_point[0] != '.' || + decimal_point[1] != 0) + { + /* Look for a '.' in the input; if present, it'll need to be + swapped for the current locale's decimal point before we + call strtod. On the other hand, if we find the current + locale's decimal point then the input is invalid. */ + while (Py_ISDIGIT(*p)) + p++; + + if (*p == '.') + { + decimal_point_pos = p++; + + /* locate end of number */ + while (Py_ISDIGIT(*p)) + p++; + + if (*p == 'e' || *p == 'E') + p++; + if (*p == '+' || *p == '-') + p++; + while (Py_ISDIGIT(*p)) + p++; + end = p; + } + else if (strncmp(p, decimal_point, decimal_point_len) == 0) + /* Python bug #1417699 */ + goto invalid_string; + /* For the other cases, we need not convert the decimal + point */ + } + + if (decimal_point_pos) { + char *copy, *c; + /* Create a copy of the input, with the '.' converted to the + locale-specific decimal point */ + copy = (char *)PyMem_MALLOC(end - digits_pos + + 1 + decimal_point_len); + if (copy == NULL) { + *endptr = (char *)nptr; + errno = ENOMEM; + return val; + } + + c = copy; + memcpy(c, digits_pos, decimal_point_pos - digits_pos); + c += decimal_point_pos - digits_pos; + memcpy(c, decimal_point, decimal_point_len); + c += decimal_point_len; + memcpy(c, decimal_point_pos + 1, + end - (decimal_point_pos + 1)); + c += end - (decimal_point_pos + 1); + *c = 0; + + val = strtod(copy, &fail_pos); + + if (fail_pos) + { + if (fail_pos > decimal_point_pos) + fail_pos = (char *)digits_pos + + (fail_pos - copy) - + (decimal_point_len - 1); + else + fail_pos = (char *)digits_pos + + (fail_pos - copy); + } + + PyMem_FREE(copy); + + } + else { + val = strtod(digits_pos, &fail_pos); + } + + if (fail_pos == digits_pos) + goto invalid_string; + + if (negate && fail_pos != nptr) + val = -val; + *endptr = fail_pos; + + return val; + + invalid_string: + *endptr = (char*)nptr; + errno = EINVAL; + return -1.0; +} + +#endif + +/* PyOS_ascii_strtod is DEPRECATED in Python 2.7 and 3.1 */ + +double +PyOS_ascii_strtod(const char *nptr, char **endptr) +{ + char *fail_pos; + const char *p; + double x; + + if (PyErr_WarnEx(PyExc_DeprecationWarning, + "PyOS_ascii_strtod and PyOS_ascii_atof are " + "deprecated. Use PyOS_string_to_double " + "instead.", 1) < 0) + return -1.0; + + /* _PyOS_ascii_strtod already does everything that we want, + except that it doesn't parse leading whitespace */ + p = nptr; + while (Py_ISSPACE(*p)) + p++; + x = _PyOS_ascii_strtod(p, &fail_pos); + if (fail_pos == p) + fail_pos = (char *)nptr; + if (endptr) + *endptr = (char *)fail_pos; + return x; +} + +/* PyOS_ascii_strtod is DEPRECATED in Python 2.7 and 3.1 */ + +double +PyOS_ascii_atof(const char *nptr) +{ + return PyOS_ascii_strtod(nptr, NULL); +} + +/* PyOS_string_to_double is the recommended replacement for the deprecated + PyOS_ascii_strtod and PyOS_ascii_atof functions. It converts a + null-terminated byte string s (interpreted as a string of ASCII characters) + to a float. The string should not have leading or trailing whitespace (in + contrast, PyOS_ascii_strtod allows leading whitespace but not trailing + whitespace). The conversion is independent of the current locale. + + If endptr is NULL, try to convert the whole string. Raise ValueError and + return -1.0 if the string is not a valid representation of a floating-point + number. + + If endptr is non-NULL, try to convert as much of the string as possible. + If no initial segment of the string is the valid representation of a + floating-point number then *endptr is set to point to the beginning of the + string, -1.0 is returned and again ValueError is raised. + + On overflow (e.g., when trying to convert '1e500' on an IEEE 754 machine), + if overflow_exception is NULL then +-Py_HUGE_VAL is returned, and no Python + exception is raised. Otherwise, overflow_exception should point to + a Python exception, this exception will be raised, -1.0 will be returned, + and *endptr will point just past the end of the converted value. + + If any other failure occurs (for example lack of memory), -1.0 is returned + and the appropriate Python exception will have been set. +*/ + +double +PyOS_string_to_double(const char *s, + char **endptr, + PyObject *overflow_exception) +{ + double x, result=-1.0; + char *fail_pos; + + errno = 0; + PyFPE_START_PROTECT("PyOS_string_to_double", return -1.0) + x = _PyOS_ascii_strtod(s, &fail_pos); + PyFPE_END_PROTECT(x) + + if (errno == ENOMEM) { + PyErr_NoMemory(); + fail_pos = (char *)s; + } + else if (!endptr && (fail_pos == s || *fail_pos != '\0')) + PyErr_Format(PyExc_ValueError, + "could not convert string to float: " + "%.200s", s); + else if (fail_pos == s) + PyErr_Format(PyExc_ValueError, + "could not convert string to float: " + "%.200s", s); + else if (errno == ERANGE && fabs(x) >= 1.0 && overflow_exception) + PyErr_Format(overflow_exception, + "value too large to convert to float: " + "%.200s", s); + else + result = x; + + if (endptr != NULL) + *endptr = fail_pos; + return result; +} + +/* Given a string that may have a decimal point in the current + locale, change it back to a dot. Since the string cannot get + longer, no need for a maximum buffer size parameter. */ +Py_LOCAL_INLINE(void) +change_decimal_from_locale_to_dot(char* buffer) +{ + struct lconv *locale_data = localeconv(); + const char *decimal_point = locale_data->decimal_point; + + if (decimal_point[0] != '.' || decimal_point[1] != 0) { + size_t decimal_point_len = strlen(decimal_point); + + if (*buffer == '+' || *buffer == '-') + buffer++; + while (Py_ISDIGIT(*buffer)) + buffer++; + if (strncmp(buffer, decimal_point, decimal_point_len) == 0) { + *buffer = '.'; + buffer++; + if (decimal_point_len > 1) { + /* buffer needs to get smaller */ + size_t rest_len = strlen(buffer + + (decimal_point_len - 1)); + memmove(buffer, + buffer + (decimal_point_len - 1), + rest_len); + buffer[rest_len] = 0; + } + } + } +} + + +/* From the C99 standard, section 7.19.6: +The exponent always contains at least two digits, and only as many more digits +as necessary to represent the exponent. +*/ +#define MIN_EXPONENT_DIGITS 2 + +/* Ensure that any exponent, if present, is at least MIN_EXPONENT_DIGITS + in length. */ +Py_LOCAL_INLINE(void) +ensure_minimum_exponent_length(char* buffer, size_t buf_size) +{ + char *p = strpbrk(buffer, "eE"); + if (p && (*(p + 1) == '-' || *(p + 1) == '+')) { + char *start = p + 2; + int exponent_digit_cnt = 0; + int leading_zero_cnt = 0; + int in_leading_zeros = 1; + int significant_digit_cnt; + + /* Skip over the exponent and the sign. */ + p += 2; + + /* Find the end of the exponent, keeping track of leading + zeros. */ + while (*p && Py_ISDIGIT(*p)) { + if (in_leading_zeros && *p == '0') + ++leading_zero_cnt; + if (*p != '0') + in_leading_zeros = 0; + ++p; + ++exponent_digit_cnt; + } + + significant_digit_cnt = exponent_digit_cnt - leading_zero_cnt; + if (exponent_digit_cnt == MIN_EXPONENT_DIGITS) { + /* If there are 2 exactly digits, we're done, + regardless of what they contain */ + } + else if (exponent_digit_cnt > MIN_EXPONENT_DIGITS) { + int extra_zeros_cnt; + + /* There are more than 2 digits in the exponent. See + if we can delete some of the leading zeros */ + if (significant_digit_cnt < MIN_EXPONENT_DIGITS) + significant_digit_cnt = MIN_EXPONENT_DIGITS; + extra_zeros_cnt = exponent_digit_cnt - + significant_digit_cnt; + + /* Delete extra_zeros_cnt worth of characters from the + front of the exponent */ + assert(extra_zeros_cnt >= 0); + + /* Add one to significant_digit_cnt to copy the + trailing 0 byte, thus setting the length */ + memmove(start, + start + extra_zeros_cnt, + significant_digit_cnt + 1); + } + else { + /* If there are fewer than 2 digits, add zeros + until there are 2, if there's enough room */ + int zeros = MIN_EXPONENT_DIGITS - exponent_digit_cnt; + if (start + zeros + exponent_digit_cnt + 1 + < buffer + buf_size) { + memmove(start + zeros, start, + exponent_digit_cnt + 1); + memset(start, '0', zeros); + } + } + } +} + +/* Remove trailing zeros after the decimal point from a numeric string; also + remove the decimal point if all digits following it are zero. The numeric + string must end in '\0', and should not have any leading or trailing + whitespace. Assumes that the decimal point is '.'. */ +Py_LOCAL_INLINE(void) +remove_trailing_zeros(char *buffer) +{ + char *old_fraction_end, *new_fraction_end, *end, *p; + + p = buffer; + if (*p == '-' || *p == '+') + /* Skip leading sign, if present */ + ++p; + while (Py_ISDIGIT(*p)) + ++p; + + /* if there's no decimal point there's nothing to do */ + if (*p++ != '.') + return; + + /* scan any digits after the point */ + while (Py_ISDIGIT(*p)) + ++p; + old_fraction_end = p; + + /* scan up to ending '\0' */ + while (*p != '\0') + p++; + /* +1 to make sure that we move the null byte as well */ + end = p+1; + + /* scan back from fraction_end, looking for removable zeros */ + p = old_fraction_end; + while (*(p-1) == '0') + --p; + /* and remove point if we've got that far */ + if (*(p-1) == '.') + --p; + new_fraction_end = p; + + memmove(new_fraction_end, old_fraction_end, end-old_fraction_end); +} + +/* Ensure that buffer has a decimal point in it. The decimal point will not + be in the current locale, it will always be '.'. Don't add a decimal point + if an exponent is present. Also, convert to exponential notation where + adding a '.0' would produce too many significant digits (see issue 5864). + + Returns a pointer to the fixed buffer, or NULL on failure. +*/ +Py_LOCAL_INLINE(char *) +ensure_decimal_point(char* buffer, size_t buf_size, int precision) +{ + int digit_count, insert_count = 0, convert_to_exp = 0; + char *chars_to_insert, *digits_start; + + /* search for the first non-digit character */ + char *p = buffer; + if (*p == '-' || *p == '+') + /* Skip leading sign, if present. I think this could only + ever be '-', but it can't hurt to check for both. */ + ++p; + digits_start = p; + while (*p && Py_ISDIGIT(*p)) + ++p; + digit_count = Py_SAFE_DOWNCAST(p - digits_start, Py_ssize_t, int); + + if (*p == '.') { + if (Py_ISDIGIT(*(p+1))) { + /* Nothing to do, we already have a decimal + point and a digit after it */ + } + else { + /* We have a decimal point, but no following + digit. Insert a zero after the decimal. */ + /* can't ever get here via PyOS_double_to_string */ + assert(precision == -1); + ++p; + chars_to_insert = "0"; + insert_count = 1; + } + } + else if (!(*p == 'e' || *p == 'E')) { + /* Don't add ".0" if we have an exponent. */ + if (digit_count == precision) { + /* issue 5864: don't add a trailing .0 in the case + where the '%g'-formatted result already has as many + significant digits as were requested. Switch to + exponential notation instead. */ + convert_to_exp = 1; + /* no exponent, no point, and we shouldn't land here + for infs and nans, so we must be at the end of the + string. */ + assert(*p == '\0'); + } + else { + assert(precision == -1 || digit_count < precision); + chars_to_insert = ".0"; + insert_count = 2; + } + } + if (insert_count) { + size_t buf_len = strlen(buffer); + if (buf_len + insert_count + 1 >= buf_size) { + /* If there is not enough room in the buffer + for the additional text, just skip it. It's + not worth generating an error over. */ + } + else { + memmove(p + insert_count, p, + buffer + strlen(buffer) - p + 1); + memcpy(p, chars_to_insert, insert_count); + } + } + if (convert_to_exp) { + int written; + size_t buf_avail; + p = digits_start; + /* insert decimal point */ + assert(digit_count >= 1); + memmove(p+2, p+1, digit_count); /* safe, but overwrites nul */ + p[1] = '.'; + p += digit_count+1; + assert(p <= buf_size+buffer); + buf_avail = buf_size+buffer-p; + if (buf_avail == 0) + return NULL; + /* Add exponent. It's okay to use lower case 'e': we only + arrive here as a result of using the empty format code or + repr/str builtins and those never want an upper case 'E' */ + written = PyOS_snprintf(p, buf_avail, "e%+.02d", digit_count-1); + if (!(0 <= written && + written < Py_SAFE_DOWNCAST(buf_avail, size_t, int))) + /* output truncated, or something else bad happened */ + return NULL; + remove_trailing_zeros(buffer); + } + return buffer; +} + +/* see FORMATBUFLEN in unicodeobject.c */ +#define FLOAT_FORMATBUFLEN 120 + +/** + * PyOS_ascii_formatd: + * @buffer: A buffer to place the resulting string in + * @buf_size: The length of the buffer. + * @format: The printf()-style format to use for the + * code to use for converting. + * @d: The #gdouble to convert + * + * Converts a #gdouble to a string, using the '.' as + * decimal point. To format the number you pass in + * a printf()-style format string. Allowed conversion + * specifiers are 'e', 'E', 'f', 'F', 'g', 'G', and 'Z'. + * + * 'Z' is the same as 'g', except it always has a decimal and + * at least one digit after the decimal. + * + * Return value: The pointer to the buffer with the converted string. + * On failure returns NULL but does not set any Python exception. + **/ +char * +_PyOS_ascii_formatd(char *buffer, + size_t buf_size, + const char *format, + double d, + int precision) +{ + char format_char; + size_t format_len = strlen(format); + + /* Issue 2264: code 'Z' requires copying the format. 'Z' is 'g', but + also with at least one character past the decimal. */ + char tmp_format[FLOAT_FORMATBUFLEN]; + + /* The last character in the format string must be the format char */ + format_char = format[format_len - 1]; + + if (format[0] != '%') + return NULL; + + /* I'm not sure why this test is here. It's ensuring that the format + string after the first character doesn't have a single quote, a + lowercase l, or a percent. This is the reverse of the commented-out + test about 10 lines ago. */ + if (strpbrk(format + 1, "'l%")) + return NULL; + + /* Also curious about this function is that it accepts format strings + like "%xg", which are invalid for floats. In general, the + interface to this function is not very good, but changing it is + difficult because it's a public API. */ + + if (!(format_char == 'e' || format_char == 'E' || + format_char == 'f' || format_char == 'F' || + format_char == 'g' || format_char == 'G' || + format_char == 'Z')) + return NULL; + + /* Map 'Z' format_char to 'g', by copying the format string and + replacing the final char with a 'g' */ + if (format_char == 'Z') { + if (format_len + 1 >= sizeof(tmp_format)) { + /* The format won't fit in our copy. Error out. In + practice, this will never happen and will be + detected by returning NULL */ + return NULL; + } + strcpy(tmp_format, format); + tmp_format[format_len - 1] = 'g'; + format = tmp_format; + } + + + /* Have PyOS_snprintf do the hard work */ + PyOS_snprintf(buffer, buf_size, format, d); + + /* Do various fixups on the return string */ + + /* Get the current locale, and find the decimal point string. + Convert that string back to a dot. */ + change_decimal_from_locale_to_dot(buffer); + + /* If an exponent exists, ensure that the exponent is at least + MIN_EXPONENT_DIGITS digits, providing the buffer is large enough + for the extra zeros. Also, if there are more than + MIN_EXPONENT_DIGITS, remove as many zeros as possible until we get + back to MIN_EXPONENT_DIGITS */ + ensure_minimum_exponent_length(buffer, buf_size); + + /* If format_char is 'Z', make sure we have at least one character + after the decimal point (and make sure we have a decimal point); + also switch to exponential notation in some edge cases where the + extra character would produce more significant digits that we + really want. */ + if (format_char == 'Z') + buffer = ensure_decimal_point(buffer, buf_size, precision); + + return buffer; +} + +char * +PyOS_ascii_formatd(char *buffer, + size_t buf_size, + const char *format, + double d) +{ + if (PyErr_WarnEx(PyExc_DeprecationWarning, + "PyOS_ascii_formatd is deprecated, " + "use PyOS_double_to_string instead", 1) < 0) + return NULL; + + return _PyOS_ascii_formatd(buffer, buf_size, format, d, -1); +} + +#ifdef PY_NO_SHORT_FLOAT_REPR + +/* The fallback code to use if _Py_dg_dtoa is not available. */ + +PyAPI_FUNC(char *) PyOS_double_to_string(double val, + char format_code, + int precision, + int flags, + int *type) +{ + char format[32]; + Py_ssize_t bufsize; + char *buf; + int t, exp; + int upper = 0; + + /* Validate format_code, and map upper and lower case */ + switch (format_code) { + case 'e': /* exponent */ + case 'f': /* fixed */ + case 'g': /* general */ + break; + case 'E': + upper = 1; + format_code = 'e'; + break; + case 'F': + upper = 1; + format_code = 'f'; + break; + case 'G': + upper = 1; + format_code = 'g'; + break; + case 'r': /* repr format */ + /* Supplied precision is unused, must be 0. */ + if (precision != 0) { + PyErr_BadInternalCall(); + return NULL; + } + /* The repr() precision (17 significant decimal digits) is the + minimal number that is guaranteed to have enough precision + so that if the number is read back in the exact same binary + value is recreated. This is true for IEEE floating point + by design, and also happens to work for all other modern + hardware. */ + precision = 17; + format_code = 'g'; + break; + default: + PyErr_BadInternalCall(); + return NULL; + } + + /* Here's a quick-and-dirty calculation to figure out how big a buffer + we need. In general, for a finite float we need: + + 1 byte for each digit of the decimal significand, and + + 1 for a possible sign + 1 for a possible decimal point + 2 for a possible [eE][+-] + 1 for each digit of the exponent; if we allow 19 digits + total then we're safe up to exponents of 2**63. + 1 for the trailing nul byte + + This gives a total of 24 + the number of digits in the significand, + and the number of digits in the significand is: + + for 'g' format: at most precision, except possibly + when precision == 0, when it's 1. + for 'e' format: precision+1 + for 'f' format: precision digits after the point, at least 1 + before. To figure out how many digits appear before the point + we have to examine the size of the number. If fabs(val) < 1.0 + then there will be only one digit before the point. If + fabs(val) >= 1.0, then there are at most + + 1+floor(log10(ceiling(fabs(val)))) + + digits before the point (where the 'ceiling' allows for the + possibility that the rounding rounds the integer part of val + up). A safe upper bound for the above quantity is + 1+floor(exp/3), where exp is the unique integer such that 0.5 + <= fabs(val)/2**exp < 1.0. This exp can be obtained from + frexp. + + So we allow room for precision+1 digits for all formats, plus an + extra floor(exp/3) digits for 'f' format. + + */ + + if (Py_IS_NAN(val) || Py_IS_INFINITY(val)) + /* 3 for 'inf'/'nan', 1 for sign, 1 for '\0' */ + bufsize = 5; + else { + bufsize = 25 + precision; + if (format_code == 'f' && fabs(val) >= 1.0) { + frexp(val, &exp); + bufsize += exp/3; + } + } + + buf = PyMem_Malloc(bufsize); + if (buf == NULL) { + PyErr_NoMemory(); + return NULL; + } + + /* Handle nan and inf. */ + if (Py_IS_NAN(val)) { + strcpy(buf, "nan"); + t = Py_DTST_NAN; + } else if (Py_IS_INFINITY(val)) { + if (copysign(1., val) == 1.) + strcpy(buf, "inf"); + else + strcpy(buf, "-inf"); + t = Py_DTST_INFINITE; + } else { + t = Py_DTST_FINITE; + if (flags & Py_DTSF_ADD_DOT_0) + format_code = 'Z'; + + PyOS_snprintf(format, sizeof(format), "%%%s.%i%c", + (flags & Py_DTSF_ALT ? "#" : ""), precision, + format_code); + _PyOS_ascii_formatd(buf, bufsize, format, val, precision); + } + + /* Add sign when requested. It's convenient (esp. when formatting + complex numbers) to include a sign even for inf and nan. */ + if (flags & Py_DTSF_SIGN && buf[0] != '-') { + size_t len = strlen(buf); + /* the bufsize calculations above should ensure that we've got + space to add a sign */ + assert((size_t)bufsize >= len+2); + memmove(buf+1, buf, len+1); + buf[0] = '+'; + } + if (upper) { + /* Convert to upper case. */ + char *p1; + for (p1 = buf; *p1; p1++) + *p1 = Py_TOUPPER(*p1); + } + + if (type) + *type = t; + return buf; +} + +#else + +/* _Py_dg_dtoa is available. */ + +/* I'm using a lookup table here so that I don't have to invent a non-locale + specific way to convert to uppercase */ +#define OFS_INF 0 +#define OFS_NAN 1 +#define OFS_E 2 + +/* The lengths of these are known to the code below, so don't change them */ +static char *lc_float_strings[] = { + "inf", + "nan", + "e", +}; +static char *uc_float_strings[] = { + "INF", + "NAN", + "E", +}; + + +/* Convert a double d to a string, and return a PyMem_Malloc'd block of + memory contain the resulting string. + + Arguments: + d is the double to be converted + format_code is one of 'e', 'f', 'g', 'r'. 'e', 'f' and 'g' + correspond to '%e', '%f' and '%g'; 'r' corresponds to repr. + mode is one of '0', '2' or '3', and is completely determined by + format_code: 'e' and 'g' use mode 2; 'f' mode 3, 'r' mode 0. + precision is the desired precision + always_add_sign is nonzero if a '+' sign should be included for positive + numbers + add_dot_0_if_integer is nonzero if integers in non-exponential form + should have ".0" added. Only applies to format codes 'r' and 'g'. + use_alt_formatting is nonzero if alternative formatting should be + used. Only applies to format codes 'e', 'f' and 'g'. For code 'g', + at most one of use_alt_formatting and add_dot_0_if_integer should + be nonzero. + type, if non-NULL, will be set to one of these constants to identify + the type of the 'd' argument: + Py_DTST_FINITE + Py_DTST_INFINITE + Py_DTST_NAN + + Returns a PyMem_Malloc'd block of memory containing the resulting string, + or NULL on error. If NULL is returned, the Python error has been set. + */ + +static char * +format_float_short(double d, char format_code, + int mode, Py_ssize_t precision, + int always_add_sign, int add_dot_0_if_integer, + int use_alt_formatting, char **float_strings, int *type) +{ + char *buf = NULL; + char *p = NULL; + Py_ssize_t bufsize = 0; + char *digits, *digits_end; + int decpt_as_int, sign, exp_len, exp = 0, use_exp = 0; + Py_ssize_t decpt, digits_len, vdigits_start, vdigits_end; + _Py_SET_53BIT_PRECISION_HEADER; + + /* _Py_dg_dtoa returns a digit string (no decimal point or exponent). + Must be matched by a call to _Py_dg_freedtoa. */ + _Py_SET_53BIT_PRECISION_START; + digits = _Py_dg_dtoa(d, mode, precision, &decpt_as_int, &sign, + &digits_end); + _Py_SET_53BIT_PRECISION_END; + + decpt = (Py_ssize_t)decpt_as_int; + if (digits == NULL) { + /* The only failure mode is no memory. */ + PyErr_NoMemory(); + goto exit; + } + assert(digits_end != NULL && digits_end >= digits); + digits_len = digits_end - digits; + + if (digits_len && !Py_ISDIGIT(digits[0])) { + /* Infinities and nans here; adapt Gay's output, + so convert Infinity to inf and NaN to nan, and + ignore sign of nan. Then return. */ + + /* ignore the actual sign of a nan */ + if (digits[0] == 'n' || digits[0] == 'N') + sign = 0; + + /* We only need 5 bytes to hold the result "+inf\0" . */ + bufsize = 5; /* Used later in an assert. */ + buf = (char *)PyMem_Malloc(bufsize); + if (buf == NULL) { + PyErr_NoMemory(); + goto exit; + } + p = buf; + + if (sign == 1) { + *p++ = '-'; + } + else if (always_add_sign) { + *p++ = '+'; + } + if (digits[0] == 'i' || digits[0] == 'I') { + strncpy(p, float_strings[OFS_INF], 3); + p += 3; + + if (type) + *type = Py_DTST_INFINITE; + } + else if (digits[0] == 'n' || digits[0] == 'N') { + strncpy(p, float_strings[OFS_NAN], 3); + p += 3; + + if (type) + *type = Py_DTST_NAN; + } + else { + /* shouldn't get here: Gay's code should always return + something starting with a digit, an 'I', or 'N' */ + strncpy(p, "ERR", 3); + p += 3; + assert(0); + } + goto exit; + } + + /* The result must be finite (not inf or nan). */ + if (type) + *type = Py_DTST_FINITE; + + + /* We got digits back, format them. We may need to pad 'digits' + either on the left or right (or both) with extra zeros, so in + general the resulting string has the form + + [][] + + where either of the pieces could be empty, and there's a + decimal point that could appear either in or in the + leading or trailing . + + Imagine an infinite 'virtual' string vdigits, consisting of the + string 'digits' (starting at index 0) padded on both the left and + right with infinite strings of zeros. We want to output a slice + + vdigits[vdigits_start : vdigits_end] + + of this virtual string. Thus if vdigits_start < 0 then we'll end + up producing some leading zeros; if vdigits_end > digits_len there + will be trailing zeros in the output. The next section of code + determines whether to use an exponent or not, figures out the + position 'decpt' of the decimal point, and computes 'vdigits_start' + and 'vdigits_end'. */ + vdigits_end = digits_len; + switch (format_code) { + case 'e': + use_exp = 1; + vdigits_end = precision; + break; + case 'f': + vdigits_end = decpt + precision; + break; + case 'g': + if (decpt <= -4 || decpt > + (add_dot_0_if_integer ? precision-1 : precision)) + use_exp = 1; + if (use_alt_formatting) + vdigits_end = precision; + break; + case 'r': + /* convert to exponential format at 1e16. We used to convert + at 1e17, but that gives odd-looking results for some values + when a 16-digit 'shortest' repr is padded with bogus zeros. + For example, repr(2e16+8) would give 20000000000000010.0; + the true value is 20000000000000008.0. */ + if (decpt <= -4 || decpt > 16) + use_exp = 1; + break; + default: + PyErr_BadInternalCall(); + goto exit; + } + + /* if using an exponent, reset decimal point position to 1 and adjust + exponent accordingly.*/ + if (use_exp) { + exp = decpt - 1; + decpt = 1; + } + /* ensure vdigits_start < decpt <= vdigits_end, or vdigits_start < + decpt < vdigits_end if add_dot_0_if_integer and no exponent */ + vdigits_start = decpt <= 0 ? decpt-1 : 0; + if (!use_exp && add_dot_0_if_integer) + vdigits_end = vdigits_end > decpt ? vdigits_end : decpt + 1; + else + vdigits_end = vdigits_end > decpt ? vdigits_end : decpt; + + /* double check inequalities */ + assert(vdigits_start <= 0 && + 0 <= digits_len && + digits_len <= vdigits_end); + /* decimal point should be in (vdigits_start, vdigits_end] */ + assert(vdigits_start < decpt && decpt <= vdigits_end); + + /* Compute an upper bound how much memory we need. This might be a few + chars too long, but no big deal. */ + bufsize = + /* sign, decimal point and trailing 0 byte */ + 3 + + + /* total digit count (including zero padding on both sides) */ + (vdigits_end - vdigits_start) + + + /* exponent "e+100", max 3 numerical digits */ + (use_exp ? 5 : 0); + + /* Now allocate the memory and initialize p to point to the start of + it. */ + buf = (char *)PyMem_Malloc(bufsize); + if (buf == NULL) { + PyErr_NoMemory(); + goto exit; + } + p = buf; + + /* Add a negative sign if negative, and a plus sign if non-negative + and always_add_sign is true. */ + if (sign == 1) + *p++ = '-'; + else if (always_add_sign) + *p++ = '+'; + + /* note that exactly one of the three 'if' conditions is true, + so we include exactly one decimal point */ + /* Zero padding on left of digit string */ + if (decpt <= 0) { + memset(p, '0', decpt-vdigits_start); + p += decpt - vdigits_start; + *p++ = '.'; + memset(p, '0', 0-decpt); + p += 0-decpt; + } + else { + memset(p, '0', 0-vdigits_start); + p += 0 - vdigits_start; + } + + /* Digits, with included decimal point */ + if (0 < decpt && decpt <= digits_len) { + strncpy(p, digits, decpt-0); + p += decpt-0; + *p++ = '.'; + strncpy(p, digits+decpt, digits_len-decpt); + p += digits_len-decpt; + } + else { + strncpy(p, digits, digits_len); + p += digits_len; + } + + /* And zeros on the right */ + if (digits_len < decpt) { + memset(p, '0', decpt-digits_len); + p += decpt-digits_len; + *p++ = '.'; + memset(p, '0', vdigits_end-decpt); + p += vdigits_end-decpt; + } + else { + memset(p, '0', vdigits_end-digits_len); + p += vdigits_end-digits_len; + } + + /* Delete a trailing decimal pt unless using alternative formatting. */ + if (p[-1] == '.' && !use_alt_formatting) + p--; + + /* Now that we've done zero padding, add an exponent if needed. */ + if (use_exp) { + *p++ = float_strings[OFS_E][0]; + exp_len = sprintf(p, "%+.02d", exp); + p += exp_len; + } + exit: + if (buf) { + *p = '\0'; + /* It's too late if this fails, as we've already stepped on + memory that isn't ours. But it's an okay debugging test. */ + assert(p-buf < bufsize); + } + if (digits) + _Py_dg_freedtoa(digits); + + return buf; +} + + +PyAPI_FUNC(char *) PyOS_double_to_string(double val, + char format_code, + int precision, + int flags, + int *type) +{ + char **float_strings = lc_float_strings; + int mode; + + /* Validate format_code, and map upper and lower case. Compute the + mode and make any adjustments as needed. */ + switch (format_code) { + /* exponent */ + case 'E': + float_strings = uc_float_strings; + format_code = 'e'; + /* Fall through. */ + case 'e': + mode = 2; + precision++; + break; + + /* fixed */ + case 'F': + float_strings = uc_float_strings; + format_code = 'f'; + /* Fall through. */ + case 'f': + mode = 3; + break; + + /* general */ + case 'G': + float_strings = uc_float_strings; + format_code = 'g'; + /* Fall through. */ + case 'g': + mode = 2; + /* precision 0 makes no sense for 'g' format; interpret as 1 */ + if (precision == 0) + precision = 1; + break; + + /* repr format */ + case 'r': + mode = 0; + /* Supplied precision is unused, must be 0. */ + if (precision != 0) { + PyErr_BadInternalCall(); + return NULL; + } + break; + + default: + PyErr_BadInternalCall(); + return NULL; + } + + return format_float_short(val, format_code, mode, precision, + flags & Py_DTSF_SIGN, + flags & Py_DTSF_ADD_DOT_0, + flags & Py_DTSF_ALT, + float_strings, type); +} +#endif /* ifdef PY_NO_SHORT_FLOAT_REPR */ diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/pythonrun.c b/AppPkg/Applications/Python/Python-2.7.10/Python/pythonrun.c new file mode 100644 index 0000000000..0f76758179 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/pythonrun.c @@ -0,0 +1,2029 @@ + +/* Python interpreter top-level routines, including init/exit */ + +#include "Python.h" + +#include "Python-ast.h" +#undef Yield /* undefine macro conflicting with winbase.h */ +#include "grammar.h" +#include "node.h" +#include "token.h" +#include "parsetok.h" +#include "errcode.h" +#include "code.h" +#include "compile.h" +#include "symtable.h" +#include "pyarena.h" +#include "ast.h" +#include "eval.h" +#include "marshal.h" +#include "abstract.h" + +#ifdef HAVE_SIGNAL_H +#include +#endif + +#ifdef MS_WINDOWS +#include "malloc.h" /* for alloca */ +#endif + +#ifdef HAVE_LANGINFO_H +#include +#include +#endif + +#ifdef MS_WINDOWS +#undef BYTE +#include "windows.h" +#endif + +#ifndef Py_REF_DEBUG +#define PRINT_TOTAL_REFS() +#else /* Py_REF_DEBUG */ +#define PRINT_TOTAL_REFS() fprintf(stderr, \ + "[%" PY_FORMAT_SIZE_T "d refs]\n", \ + _Py_GetRefTotal()) +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +extern char *Py_GetPath(void); + +extern grammar _PyParser_Grammar; /* From graminit.c */ + +/* Forward */ +static void initmain(void); +static void initsite(void); +static PyObject *run_mod(mod_ty, const char *, PyObject *, PyObject *, + PyCompilerFlags *, PyArena *); +static PyObject *run_pyc_file(FILE *, const char *, PyObject *, PyObject *, + PyCompilerFlags *); +static void err_input(perrdetail *); +static void initsigs(void); +static void wait_for_thread_shutdown(void); +static void call_sys_exitfunc(void); +static void call_ll_exitfuncs(void); +extern void _PyUnicode_Init(void); +extern void _PyUnicode_Fini(void); + +#ifdef WITH_THREAD +extern void _PyGILState_Init(PyInterpreterState *, PyThreadState *); +extern void _PyGILState_Fini(void); +#endif /* WITH_THREAD */ + +int Py_DebugFlag; /* Needed by parser.c */ +int Py_VerboseFlag; /* Needed by import.c */ +int Py_InteractiveFlag; /* Needed by Py_FdIsInteractive() below */ +int Py_InspectFlag; /* Needed to determine whether to exit at SystemExit */ +int Py_NoSiteFlag; /* Suppress 'import site' */ +int Py_BytesWarningFlag; /* Warn on str(bytes) and str(buffer) */ +int Py_DontWriteBytecodeFlag; /* Suppress writing bytecode files (*.py[co]) */ +int Py_UseClassExceptionsFlag = 1; /* Needed by bltinmodule.c: deprecated */ +int Py_FrozenFlag; /* Needed by getpath.c */ +int Py_UnicodeFlag = 0; /* Needed by compile.c */ +int Py_IgnoreEnvironmentFlag; /* e.g. PYTHONPATH, PYTHONHOME */ +/* _XXX Py_QnewFlag should go away in 2.3. It's true iff -Qnew is passed, + on the command line, and is used in 2.2 by ceval.c to make all "/" divisions + true divisions (which they will be in 2.3). */ +int _Py_QnewFlag = 0; +int Py_NoUserSiteDirectory = 0; /* for -s and site.py */ +int Py_HashRandomizationFlag = 0; /* for -R and PYTHONHASHSEED */ + + +/* Hack to force loading of object files */ +int (*_PyOS_mystrnicmp_hack)(const char *, const char *, Py_ssize_t) = \ + PyOS_mystrnicmp; /* Python/pystrcmp.o */ + +/* PyModule_GetWarningsModule is no longer necessary as of 2.6 +since _warnings is builtin. This API should not be used. */ +PyObject * +PyModule_GetWarningsModule(void) +{ + return PyImport_ImportModule("warnings"); +} + +static int initialized = 0; + +/* API to access the initialized flag -- useful for esoteric use */ + +int +Py_IsInitialized(void) +{ + return initialized; +} + +/* Global initializations. Can be undone by Py_Finalize(). Don't + call this twice without an intervening Py_Finalize() call. When + initializations fail, a fatal error is issued and the function does + not return. On return, the first thread and interpreter state have + been created. + + Locking: you must hold the interpreter lock while calling this. + (If the lock has not yet been initialized, that's equivalent to + having the lock, but you cannot use multiple threads.) + +*/ + +static int +add_flag(int flag, const char *envs) +{ + int env = atoi(envs); + if (flag < env) + flag = env; + if (flag < 1) + flag = 1; + return flag; +} + +void +Py_InitializeEx(int install_sigs) +{ + PyInterpreterState *interp; + PyThreadState *tstate; + PyObject *bimod, *sysmod; + char *p; + char *icodeset = NULL; /* On Windows, input codeset may theoretically + differ from output codeset. */ + char *codeset = NULL; + char *errors = NULL; + int free_codeset = 0; + int overridden = 0; + PyObject *sys_stream, *sys_isatty; +#if defined(Py_USING_UNICODE) && defined(HAVE_LANGINFO_H) && defined(CODESET) + char *saved_locale, *loc_codeset; +#endif +#ifdef MS_WINDOWS + char ibuf[128]; + char buf[128]; +#endif + extern void _Py_ReadyTypes(void); + + if (initialized) + return; + initialized = 1; + + if ((p = Py_GETENV("PYTHONDEBUG")) && *p != '\0') + Py_DebugFlag = add_flag(Py_DebugFlag, p); + if ((p = Py_GETENV("PYTHONVERBOSE")) && *p != '\0') + Py_VerboseFlag = add_flag(Py_VerboseFlag, p); + if ((p = Py_GETENV("PYTHONOPTIMIZE")) && *p != '\0') + Py_OptimizeFlag = add_flag(Py_OptimizeFlag, p); + if ((p = Py_GETENV("PYTHONDONTWRITEBYTECODE")) && *p != '\0') + Py_DontWriteBytecodeFlag = add_flag(Py_DontWriteBytecodeFlag, p); + /* The variable is only tested for existence here; _PyRandom_Init will + check its value further. */ + if ((p = Py_GETENV("PYTHONHASHSEED")) && *p != '\0') + Py_HashRandomizationFlag = add_flag(Py_HashRandomizationFlag, p); + + _PyRandom_Init(); + + interp = PyInterpreterState_New(); + if (interp == NULL) + Py_FatalError("Py_Initialize: can't make first interpreter"); + + tstate = PyThreadState_New(interp); + if (tstate == NULL) + Py_FatalError("Py_Initialize: can't make first thread"); + (void) PyThreadState_Swap(tstate); + + _Py_ReadyTypes(); + + if (!_PyFrame_Init()) + Py_FatalError("Py_Initialize: can't init frames"); + + if (!_PyInt_Init()) + Py_FatalError("Py_Initialize: can't init ints"); + + if (!_PyLong_Init()) + Py_FatalError("Py_Initialize: can't init longs"); + + if (!PyByteArray_Init()) + Py_FatalError("Py_Initialize: can't init bytearray"); + + _PyFloat_Init(); + + interp->modules = PyDict_New(); + if (interp->modules == NULL) + Py_FatalError("Py_Initialize: can't make modules dictionary"); + interp->modules_reloading = PyDict_New(); + if (interp->modules_reloading == NULL) + Py_FatalError("Py_Initialize: can't make modules_reloading dictionary"); + +#ifdef Py_USING_UNICODE + /* Init Unicode implementation; relies on the codec registry */ + _PyUnicode_Init(); +#endif + + bimod = _PyBuiltin_Init(); + if (bimod == NULL) + Py_FatalError("Py_Initialize: can't initialize __builtin__"); + interp->builtins = PyModule_GetDict(bimod); + if (interp->builtins == NULL) + Py_FatalError("Py_Initialize: can't initialize builtins dict"); + Py_INCREF(interp->builtins); + + sysmod = _PySys_Init(); + if (sysmod == NULL) + Py_FatalError("Py_Initialize: can't initialize sys"); + interp->sysdict = PyModule_GetDict(sysmod); + if (interp->sysdict == NULL) + Py_FatalError("Py_Initialize: can't initialize sys dict"); + Py_INCREF(interp->sysdict); + _PyImport_FixupExtension("sys", "sys"); + PySys_SetPath(Py_GetPath()); + PyDict_SetItemString(interp->sysdict, "modules", + interp->modules); + + _PyImport_Init(); + + /* initialize builtin exceptions */ + _PyExc_Init(); + _PyImport_FixupExtension("exceptions", "exceptions"); + + /* phase 2 of builtins */ + _PyImport_FixupExtension("__builtin__", "__builtin__"); + + _PyImportHooks_Init(); + + if (install_sigs) + initsigs(); /* Signal handling stuff, including initintr() */ + + /* Initialize warnings. */ + _PyWarnings_Init(); + if (PySys_HasWarnOptions()) { + PyObject *warnings_module = PyImport_ImportModule("warnings"); + if (!warnings_module) + PyErr_Clear(); + Py_XDECREF(warnings_module); + } + + initmain(); /* Module __main__ */ + + /* auto-thread-state API, if available */ +#ifdef WITH_THREAD + _PyGILState_Init(interp, tstate); +#endif /* WITH_THREAD */ + + if (!Py_NoSiteFlag) + initsite(); /* Module site */ + + if ((p = Py_GETENV("PYTHONIOENCODING")) && *p != '\0') { + p = icodeset = codeset = strdup(p); + free_codeset = 1; + errors = strchr(p, ':'); + if (errors) { + *errors = '\0'; + errors++; + } + overridden = 1; + } + +#if defined(Py_USING_UNICODE) && defined(HAVE_LANGINFO_H) && defined(CODESET) + /* On Unix, set the file system encoding according to the + user's preference, if the CODESET names a well-known + Python codec, and Py_FileSystemDefaultEncoding isn't + initialized by other means. Also set the encoding of + stdin and stdout if these are terminals, unless overridden. */ + + if (!overridden || !Py_FileSystemDefaultEncoding) { + saved_locale = strdup(setlocale(LC_CTYPE, NULL)); + setlocale(LC_CTYPE, ""); + loc_codeset = nl_langinfo(CODESET); + if (loc_codeset && *loc_codeset) { + PyObject *enc = PyCodec_Encoder(loc_codeset); + if (enc) { + loc_codeset = strdup(loc_codeset); + Py_DECREF(enc); + } else { + if (PyErr_ExceptionMatches(PyExc_LookupError)) { + PyErr_Clear(); + loc_codeset = NULL; + } else { + PyErr_Print(); + exit(1); + } + } + } else + loc_codeset = NULL; + setlocale(LC_CTYPE, saved_locale); + free(saved_locale); + + if (!overridden) { + codeset = icodeset = loc_codeset; + free_codeset = 1; + } + + /* Initialize Py_FileSystemDefaultEncoding from + locale even if PYTHONIOENCODING is set. */ + if (!Py_FileSystemDefaultEncoding) { + Py_FileSystemDefaultEncoding = loc_codeset; + if (!overridden) + free_codeset = 0; + } + } +#endif + +#ifdef MS_WINDOWS + if (!overridden) { + icodeset = ibuf; + codeset = buf; + sprintf(ibuf, "cp%d", GetConsoleCP()); + sprintf(buf, "cp%d", GetConsoleOutputCP()); + } +#endif + + if (codeset) { + sys_stream = PySys_GetObject("stdin"); + sys_isatty = PyObject_CallMethod(sys_stream, "isatty", ""); + if (!sys_isatty) + PyErr_Clear(); + if ((overridden || + (sys_isatty && PyObject_IsTrue(sys_isatty))) && + PyFile_Check(sys_stream)) { + if (!PyFile_SetEncodingAndErrors(sys_stream, icodeset, errors)) + Py_FatalError("Cannot set codeset of stdin"); + } + Py_XDECREF(sys_isatty); + + sys_stream = PySys_GetObject("stdout"); + sys_isatty = PyObject_CallMethod(sys_stream, "isatty", ""); + if (!sys_isatty) + PyErr_Clear(); + if ((overridden || + (sys_isatty && PyObject_IsTrue(sys_isatty))) && + PyFile_Check(sys_stream)) { + if (!PyFile_SetEncodingAndErrors(sys_stream, codeset, errors)) + Py_FatalError("Cannot set codeset of stdout"); + } + Py_XDECREF(sys_isatty); + + sys_stream = PySys_GetObject("stderr"); + sys_isatty = PyObject_CallMethod(sys_stream, "isatty", ""); + if (!sys_isatty) + PyErr_Clear(); + if((overridden || + (sys_isatty && PyObject_IsTrue(sys_isatty))) && + PyFile_Check(sys_stream)) { + if (!PyFile_SetEncodingAndErrors(sys_stream, codeset, errors)) + Py_FatalError("Cannot set codeset of stderr"); + } + Py_XDECREF(sys_isatty); + + if (free_codeset) + free(codeset); + } +} + +void +Py_Initialize(void) +{ + Py_InitializeEx(1); +} + + +#ifdef COUNT_ALLOCS +extern void dump_counts(FILE*); +#endif + +/* Undo the effect of Py_Initialize(). + + Beware: if multiple interpreter and/or thread states exist, these + are not wiped out; only the current thread and interpreter state + are deleted. But since everything else is deleted, those other + interpreter and thread states should no longer be used. + + (XXX We should do better, e.g. wipe out all interpreters and + threads.) + + Locking: as above. + +*/ + +void +Py_Finalize(void) +{ + PyInterpreterState *interp; + PyThreadState *tstate; + + if (!initialized) + return; + + wait_for_thread_shutdown(); + + /* The interpreter is still entirely intact at this point, and the + * exit funcs may be relying on that. In particular, if some thread + * or exit func is still waiting to do an import, the import machinery + * expects Py_IsInitialized() to return true. So don't say the + * interpreter is uninitialized until after the exit funcs have run. + * Note that Threading.py uses an exit func to do a join on all the + * threads created thru it, so this also protects pending imports in + * the threads created via Threading. + */ + call_sys_exitfunc(); + initialized = 0; + + /* Get current thread state and interpreter pointer */ + tstate = PyThreadState_GET(); + interp = tstate->interp; + + /* Disable signal handling */ + PyOS_FiniInterrupts(); + + /* Clear type lookup cache */ + PyType_ClearCache(); + + /* Collect garbage. This may call finalizers; it's nice to call these + * before all modules are destroyed. + * XXX If a __del__ or weakref callback is triggered here, and tries to + * XXX import a module, bad things can happen, because Python no + * XXX longer believes it's initialized. + * XXX Fatal Python error: Interpreter not initialized (version mismatch?) + * XXX is easy to provoke that way. I've also seen, e.g., + * XXX Exception exceptions.ImportError: 'No module named sha' + * XXX in ignored + * XXX but I'm unclear on exactly how that one happens. In any case, + * XXX I haven't seen a real-life report of either of these. + */ + PyGC_Collect(); +#ifdef COUNT_ALLOCS + /* With COUNT_ALLOCS, it helps to run GC multiple times: + each collection might release some types from the type + list, so they become garbage. */ + while (PyGC_Collect() > 0) + /* nothing */; +#endif + + /* Destroy all modules */ + PyImport_Cleanup(); + + /* Collect final garbage. This disposes of cycles created by + * new-style class definitions, for example. + * XXX This is disabled because it caused too many problems. If + * XXX a __del__ or weakref callback triggers here, Python code has + * XXX a hard time running, because even the sys module has been + * XXX cleared out (sys.stdout is gone, sys.excepthook is gone, etc). + * XXX One symptom is a sequence of information-free messages + * XXX coming from threads (if a __del__ or callback is invoked, + * XXX other threads can execute too, and any exception they encounter + * XXX triggers a comedy of errors as subsystem after subsystem + * XXX fails to find what it *expects* to find in sys to help report + * XXX the exception and consequent unexpected failures). I've also + * XXX seen segfaults then, after adding print statements to the + * XXX Python code getting called. + */ +#if 0 + PyGC_Collect(); +#endif + + /* Destroy the database used by _PyImport_{Fixup,Find}Extension */ + _PyImport_Fini(); + + /* Debugging stuff */ +#ifdef COUNT_ALLOCS + dump_counts(stdout); +#endif + + PRINT_TOTAL_REFS(); + +#ifdef Py_TRACE_REFS + /* Display all objects still alive -- this can invoke arbitrary + * __repr__ overrides, so requires a mostly-intact interpreter. + * Alas, a lot of stuff may still be alive now that will be cleaned + * up later. + */ + if (Py_GETENV("PYTHONDUMPREFS")) + _Py_PrintReferences(stderr); +#endif /* Py_TRACE_REFS */ + + /* Clear interpreter state */ + PyInterpreterState_Clear(interp); + + /* Now we decref the exception classes. After this point nothing + can raise an exception. That's okay, because each Fini() method + below has been checked to make sure no exceptions are ever + raised. + */ + + _PyExc_Fini(); + + /* Cleanup auto-thread-state */ +#ifdef WITH_THREAD + _PyGILState_Fini(); +#endif /* WITH_THREAD */ + + /* Delete current thread */ + PyThreadState_Swap(NULL); + PyInterpreterState_Delete(interp); + + /* Sundry finalizers */ + PyMethod_Fini(); + PyFrame_Fini(); + PyCFunction_Fini(); + PyTuple_Fini(); + PyList_Fini(); + PySet_Fini(); + PyString_Fini(); + PyByteArray_Fini(); + PyInt_Fini(); + PyFloat_Fini(); + PyDict_Fini(); + _PyRandom_Fini(); + +#ifdef Py_USING_UNICODE + /* Cleanup Unicode implementation */ + _PyUnicode_Fini(); +#endif + + /* XXX Still allocated: + - various static ad-hoc pointers to interned strings + - int and float free list blocks + - whatever various modules and libraries allocate + */ + + PyGrammar_RemoveAccelerators(&_PyParser_Grammar); + +#ifdef Py_TRACE_REFS + /* Display addresses (& refcnts) of all objects still alive. + * An address can be used to find the repr of the object, printed + * above by _Py_PrintReferences. + */ + if (Py_GETENV("PYTHONDUMPREFS")) + _Py_PrintReferenceAddresses(stderr); +#endif /* Py_TRACE_REFS */ +#ifdef PYMALLOC_DEBUG + if (Py_GETENV("PYTHONMALLOCSTATS")) + _PyObject_DebugMallocStats(); +#endif + + call_ll_exitfuncs(); +} + +/* Create and initialize a new interpreter and thread, and return the + new thread. This requires that Py_Initialize() has been called + first. + + Unsuccessful initialization yields a NULL pointer. Note that *no* + exception information is available even in this case -- the + exception information is held in the thread, and there is no + thread. + + Locking: as above. + +*/ + +PyThreadState * +Py_NewInterpreter(void) +{ + PyInterpreterState *interp; + PyThreadState *tstate, *save_tstate; + PyObject *bimod, *sysmod; + + if (!initialized) + Py_FatalError("Py_NewInterpreter: call Py_Initialize first"); + + interp = PyInterpreterState_New(); + if (interp == NULL) + return NULL; + + tstate = PyThreadState_New(interp); + if (tstate == NULL) { + PyInterpreterState_Delete(interp); + return NULL; + } + + save_tstate = PyThreadState_Swap(tstate); + + /* XXX The following is lax in error checking */ + + interp->modules = PyDict_New(); + interp->modules_reloading = PyDict_New(); + + bimod = _PyImport_FindExtension("__builtin__", "__builtin__"); + if (bimod != NULL) { + interp->builtins = PyModule_GetDict(bimod); + if (interp->builtins == NULL) + goto handle_error; + Py_INCREF(interp->builtins); + } + sysmod = _PyImport_FindExtension("sys", "sys"); + if (bimod != NULL && sysmod != NULL) { + interp->sysdict = PyModule_GetDict(sysmod); + if (interp->sysdict == NULL) + goto handle_error; + Py_INCREF(interp->sysdict); + PySys_SetPath(Py_GetPath()); + PyDict_SetItemString(interp->sysdict, "modules", + interp->modules); + _PyImportHooks_Init(); + initmain(); + if (!Py_NoSiteFlag) + initsite(); + } + + if (!PyErr_Occurred()) + return tstate; + +handle_error: + /* Oops, it didn't work. Undo it all. */ + + PyErr_Print(); + PyThreadState_Clear(tstate); + PyThreadState_Swap(save_tstate); + PyThreadState_Delete(tstate); + PyInterpreterState_Delete(interp); + + return NULL; +} + +/* Delete an interpreter and its last thread. This requires that the + given thread state is current, that the thread has no remaining + frames, and that it is its interpreter's only remaining thread. + It is a fatal error to violate these constraints. + + (Py_Finalize() doesn't have these constraints -- it zaps + everything, regardless.) + + Locking: as above. + +*/ + +void +Py_EndInterpreter(PyThreadState *tstate) +{ + PyInterpreterState *interp = tstate->interp; + + if (tstate != PyThreadState_GET()) + Py_FatalError("Py_EndInterpreter: thread is not current"); + if (tstate->frame != NULL) + Py_FatalError("Py_EndInterpreter: thread still has a frame"); + if (tstate != interp->tstate_head || tstate->next != NULL) + Py_FatalError("Py_EndInterpreter: not the last thread"); + + PyImport_Cleanup(); + PyInterpreterState_Clear(interp); + PyThreadState_Swap(NULL); + PyInterpreterState_Delete(interp); +} + +static char *progname = "python"; + +void +Py_SetProgramName(char *pn) +{ + if (pn && *pn) + progname = pn; +} + +char * +Py_GetProgramName(void) +{ + return progname; +} + +static char *default_home = NULL; + +void +Py_SetPythonHome(char *home) +{ + default_home = home; +} + +char * +Py_GetPythonHome(void) +{ + char *home = default_home; + if (home == NULL && !Py_IgnoreEnvironmentFlag) + home = Py_GETENV("PYTHONHOME"); + return home; +} + +/* Create __main__ module */ + +static void +initmain(void) +{ + PyObject *m, *d; + m = PyImport_AddModule("__main__"); + if (m == NULL) + Py_FatalError("can't create __main__ module"); + d = PyModule_GetDict(m); + if (PyDict_GetItemString(d, "__builtins__") == NULL) { + PyObject *bimod = PyImport_ImportModule("__builtin__"); + if (bimod == NULL || + PyDict_SetItemString(d, "__builtins__", bimod) != 0) + Py_FatalError("can't add __builtins__ to __main__"); + Py_XDECREF(bimod); + } +} + +/* Import the site module (not into __main__ though) */ + +static void +initsite(void) +{ + PyObject *m; + m = PyImport_ImportModule("site"); + if (m == NULL) { + PyErr_Print(); + Py_Finalize(); + exit(1); + } + else { + Py_DECREF(m); + } +} + +/* Parse input from a file and execute it */ + +int +PyRun_AnyFileExFlags(FILE *fp, const char *filename, int closeit, + PyCompilerFlags *flags) +{ + if (filename == NULL) + filename = "???"; + if (Py_FdIsInteractive(fp, filename)) { + int err = PyRun_InteractiveLoopFlags(fp, filename, flags); + if (closeit) + fclose(fp); + return err; + } + else + return PyRun_SimpleFileExFlags(fp, filename, closeit, flags); +} + +int +PyRun_InteractiveLoopFlags(FILE *fp, const char *filename, PyCompilerFlags *flags) +{ + PyObject *v; + int ret; + PyCompilerFlags local_flags; + + if (flags == NULL) { + flags = &local_flags; + local_flags.cf_flags = 0; + } + v = PySys_GetObject("ps1"); + if (v == NULL) { + PySys_SetObject("ps1", v = PyString_FromString(">>> ")); + Py_XDECREF(v); + } + v = PySys_GetObject("ps2"); + if (v == NULL) { + PySys_SetObject("ps2", v = PyString_FromString("... ")); + Py_XDECREF(v); + } + for (;;) { + ret = PyRun_InteractiveOneFlags(fp, filename, flags); + PRINT_TOTAL_REFS(); + if (ret == E_EOF) + return 0; + /* + if (ret == E_NOMEM) + return -1; + */ + } +} + +#if 0 +/* compute parser flags based on compiler flags */ +#define PARSER_FLAGS(flags) \ + ((flags) ? ((((flags)->cf_flags & PyCF_DONT_IMPLY_DEDENT) ? \ + PyPARSE_DONT_IMPLY_DEDENT : 0)) : 0) +#endif +#if 1 +/* Keep an example of flags with future keyword support. */ +#define PARSER_FLAGS(flags) \ + ((flags) ? ((((flags)->cf_flags & PyCF_DONT_IMPLY_DEDENT) ? \ + PyPARSE_DONT_IMPLY_DEDENT : 0) \ + | (((flags)->cf_flags & CO_FUTURE_PRINT_FUNCTION) ? \ + PyPARSE_PRINT_IS_FUNCTION : 0) \ + | (((flags)->cf_flags & CO_FUTURE_UNICODE_LITERALS) ? \ + PyPARSE_UNICODE_LITERALS : 0) \ + ) : 0) +#endif + +int +PyRun_InteractiveOneFlags(FILE *fp, const char *filename, PyCompilerFlags *flags) +{ + PyObject *m, *d, *v, *w; + mod_ty mod; + PyArena *arena; + char *ps1 = "", *ps2 = ""; + int errcode = 0; + + v = PySys_GetObject("ps1"); + if (v != NULL) { + v = PyObject_Str(v); + if (v == NULL) + PyErr_Clear(); + else if (PyString_Check(v)) + ps1 = PyString_AsString(v); + } + w = PySys_GetObject("ps2"); + if (w != NULL) { + w = PyObject_Str(w); + if (w == NULL) + PyErr_Clear(); + else if (PyString_Check(w)) + ps2 = PyString_AsString(w); + } + arena = PyArena_New(); + if (arena == NULL) { + Py_XDECREF(v); + Py_XDECREF(w); + return -1; + } + mod = PyParser_ASTFromFile(fp, filename, + Py_single_input, ps1, ps2, + flags, &errcode, arena); + Py_XDECREF(v); + Py_XDECREF(w); + if (mod == NULL) { + PyArena_Free(arena); + if (errcode == E_EOF) { + PyErr_Clear(); + return E_EOF; + } + PyErr_Print(); + return -1; + } + m = PyImport_AddModule("__main__"); + if (m == NULL) { + PyArena_Free(arena); + return -1; + } + d = PyModule_GetDict(m); + v = run_mod(mod, filename, d, d, flags, arena); + PyArena_Free(arena); + if (v == NULL) { + PyErr_Print(); + return -1; + } + Py_DECREF(v); + if (Py_FlushLine()) + PyErr_Clear(); + return 0; +} + +/* Check whether a file maybe a pyc file: Look at the extension, + the file type, and, if we may close it, at the first few bytes. */ + +static int +maybe_pyc_file(FILE *fp, const char* filename, const char* ext, int closeit) +{ + if (strcmp(ext, ".pyc") == 0 || strcmp(ext, ".pyo") == 0) + return 1; + + /* Only look into the file if we are allowed to close it, since + it then should also be seekable. */ + if (closeit) { + /* Read only two bytes of the magic. If the file was opened in + text mode, the bytes 3 and 4 of the magic (\r\n) might not + be read as they are on disk. */ + unsigned int halfmagic = PyImport_GetMagicNumber() & 0xFFFF; + unsigned char buf[2]; + /* Mess: In case of -x, the stream is NOT at its start now, + and ungetc() was used to push back the first newline, + which makes the current stream position formally undefined, + and a x-platform nightmare. + Unfortunately, we have no direct way to know whether -x + was specified. So we use a terrible hack: if the current + stream position is not 0, we assume -x was specified, and + give up. Bug 132850 on SourceForge spells out the + hopelessness of trying anything else (fseek and ftell + don't work predictably x-platform for text-mode files). + */ + int ispyc = 0; + if (ftell(fp) == 0) { + if (fread(buf, 1, 2, fp) == 2 && + ((unsigned int)buf[1]<<8 | buf[0]) == halfmagic) + ispyc = 1; + rewind(fp); + } + return ispyc; + } + return 0; +} + +int +PyRun_SimpleFileExFlags(FILE *fp, const char *filename, int closeit, + PyCompilerFlags *flags) +{ + PyObject *m, *d, *v; + const char *ext; + int set_file_name = 0, len, ret = -1; + + m = PyImport_AddModule("__main__"); + if (m == NULL) + return -1; + Py_INCREF(m); + d = PyModule_GetDict(m); + if (PyDict_GetItemString(d, "__file__") == NULL) { + PyObject *f = PyString_FromString(filename); + if (f == NULL) + goto done; + if (PyDict_SetItemString(d, "__file__", f) < 0) { + Py_DECREF(f); + goto done; + } + set_file_name = 1; + Py_DECREF(f); + } + len = strlen(filename); + ext = filename + len - (len > 4 ? 4 : 0); + if (maybe_pyc_file(fp, filename, ext, closeit)) { + /* Try to run a pyc file. First, re-open in binary */ + if (closeit) + fclose(fp); + if ((fp = fopen(filename, "rb")) == NULL) { + fprintf(stderr, "python: Can't reopen .pyc file\n"); + goto done; + } + /* Turn on optimization if a .pyo file is given */ + if (strcmp(ext, ".pyo") == 0) + Py_OptimizeFlag = 1; + v = run_pyc_file(fp, filename, d, d, flags); + } else { + v = PyRun_FileExFlags(fp, filename, Py_file_input, d, d, + closeit, flags); + } + if (v == NULL) { + PyErr_Print(); + goto done; + } + Py_DECREF(v); + if (Py_FlushLine()) + PyErr_Clear(); + ret = 0; + done: + if (set_file_name && PyDict_DelItemString(d, "__file__")) + PyErr_Clear(); + Py_DECREF(m); + return ret; +} + +int +PyRun_SimpleStringFlags(const char *command, PyCompilerFlags *flags) +{ + PyObject *m, *d, *v; + m = PyImport_AddModule("__main__"); + if (m == NULL) + return -1; + d = PyModule_GetDict(m); + v = PyRun_StringFlags(command, Py_file_input, d, d, flags); + if (v == NULL) { + PyErr_Print(); + return -1; + } + Py_DECREF(v); + if (Py_FlushLine()) + PyErr_Clear(); + return 0; +} + +static int +parse_syntax_error(PyObject *err, PyObject **message, const char **filename, + int *lineno, int *offset, const char **text) +{ + long hold; + PyObject *v; + + /* old style errors */ + if (PyTuple_Check(err)) + return PyArg_ParseTuple(err, "O(ziiz)", message, filename, + lineno, offset, text); + + *message = NULL; + + /* new style errors. `err' is an instance */ + *message = PyObject_GetAttrString(err, "msg"); + if (!*message) + goto finally; + + v = PyObject_GetAttrString(err, "filename"); + if (!v) + goto finally; + if (v == Py_None) { + Py_DECREF(v); + *filename = NULL; + } + else { + *filename = PyString_AsString(v); + Py_DECREF(v); + if (!*filename) + goto finally; + } + + v = PyObject_GetAttrString(err, "lineno"); + if (!v) + goto finally; + hold = PyInt_AsLong(v); + Py_DECREF(v); + if (hold < 0 && PyErr_Occurred()) + goto finally; + *lineno = (int)hold; + + v = PyObject_GetAttrString(err, "offset"); + if (!v) + goto finally; + if (v == Py_None) { + *offset = -1; + Py_DECREF(v); + } else { + hold = PyInt_AsLong(v); + Py_DECREF(v); + if (hold < 0 && PyErr_Occurred()) + goto finally; + *offset = (int)hold; + } + + v = PyObject_GetAttrString(err, "text"); + if (!v) + goto finally; + if (v == Py_None) { + Py_DECREF(v); + *text = NULL; + } + else { + *text = PyString_AsString(v); + Py_DECREF(v); + if (!*text) + goto finally; + } + return 1; + +finally: + Py_XDECREF(*message); + return 0; +} + +void +PyErr_Print(void) +{ + PyErr_PrintEx(1); +} + +static void +print_error_text(PyObject *f, int offset, const char *text) +{ + char *nl; + if (offset >= 0) { + if (offset > 0 && offset == strlen(text) && text[offset - 1] == '\n') + offset--; + for (;;) { + nl = strchr(text, '\n'); + if (nl == NULL || nl-text >= offset) + break; + offset -= (int)(nl+1-text); + text = nl+1; + } + while (*text == ' ' || *text == '\t') { + text++; + offset--; + } + } + PyFile_WriteString(" ", f); + PyFile_WriteString(text, f); + if (*text == '\0' || text[strlen(text)-1] != '\n') + PyFile_WriteString("\n", f); + if (offset == -1) + return; + PyFile_WriteString(" ", f); + offset--; + while (offset > 0) { + PyFile_WriteString(" ", f); + offset--; + } + PyFile_WriteString("^\n", f); +} + +static void +handle_system_exit(void) +{ + PyObject *exception, *value, *tb; + int exitcode = 0; + + if (Py_InspectFlag) + /* Don't exit if -i flag was given. This flag is set to 0 + * when entering interactive mode for inspecting. */ + return; + + PyErr_Fetch(&exception, &value, &tb); + if (Py_FlushLine()) + PyErr_Clear(); + fflush(stdout); + if (value == NULL || value == Py_None) + goto done; + if (PyExceptionInstance_Check(value)) { + /* The error code should be in the `code' attribute. */ + PyObject *code = PyObject_GetAttrString(value, "code"); + if (code) { + Py_DECREF(value); + value = code; + if (value == Py_None) + goto done; + } + /* If we failed to dig out the 'code' attribute, + just let the else clause below print the error. */ + } + if (PyInt_Check(value)) + exitcode = (int)PyInt_AsLong(value); + else { + PyObject *sys_stderr = PySys_GetObject("stderr"); + if (sys_stderr != NULL && sys_stderr != Py_None) { + PyFile_WriteObject(value, sys_stderr, Py_PRINT_RAW); + } else { + PyObject_Print(value, stderr, Py_PRINT_RAW); + fflush(stderr); + } + PySys_WriteStderr("\n"); + exitcode = 1; + } + done: + /* Restore and clear the exception info, in order to properly decref + * the exception, value, and traceback. If we just exit instead, + * these leak, which confuses PYTHONDUMPREFS output, and may prevent + * some finalizers from running. + */ + PyErr_Restore(exception, value, tb); + PyErr_Clear(); + Py_Exit(exitcode); + /* NOTREACHED */ +} + +void +PyErr_PrintEx(int set_sys_last_vars) +{ + PyObject *exception, *v, *tb, *hook; + + if (PyErr_ExceptionMatches(PyExc_SystemExit)) { + handle_system_exit(); + } + PyErr_Fetch(&exception, &v, &tb); + if (exception == NULL) + return; + PyErr_NormalizeException(&exception, &v, &tb); + if (exception == NULL) + return; + /* Now we know v != NULL too */ + if (set_sys_last_vars) { + PySys_SetObject("last_type", exception); + PySys_SetObject("last_value", v); + PySys_SetObject("last_traceback", tb); + } + hook = PySys_GetObject("excepthook"); + if (hook && hook != Py_None) { + PyObject *args = PyTuple_Pack(3, + exception, v, tb ? tb : Py_None); + PyObject *result = PyEval_CallObject(hook, args); + if (result == NULL) { + PyObject *exception2, *v2, *tb2; + if (PyErr_ExceptionMatches(PyExc_SystemExit)) { + handle_system_exit(); + } + PyErr_Fetch(&exception2, &v2, &tb2); + PyErr_NormalizeException(&exception2, &v2, &tb2); + /* It should not be possible for exception2 or v2 + to be NULL. However PyErr_Display() can't + tolerate NULLs, so just be safe. */ + if (exception2 == NULL) { + exception2 = Py_None; + Py_INCREF(exception2); + } + if (v2 == NULL) { + v2 = Py_None; + Py_INCREF(v2); + } + if (Py_FlushLine()) + PyErr_Clear(); + fflush(stdout); + PySys_WriteStderr("Error in sys.excepthook:\n"); + PyErr_Display(exception2, v2, tb2); + PySys_WriteStderr("\nOriginal exception was:\n"); + PyErr_Display(exception, v, tb); + Py_DECREF(exception2); + Py_DECREF(v2); + Py_XDECREF(tb2); + } + Py_XDECREF(result); + Py_XDECREF(args); + } else { + PySys_WriteStderr("sys.excepthook is missing\n"); + PyErr_Display(exception, v, tb); + } + Py_XDECREF(exception); + Py_XDECREF(v); + Py_XDECREF(tb); +} + +void +PyErr_Display(PyObject *exception, PyObject *value, PyObject *tb) +{ + int err = 0; + PyObject *f = PySys_GetObject("stderr"); + Py_INCREF(value); + if (f == NULL || f == Py_None) + fprintf(stderr, "lost sys.stderr\n"); + else { + if (Py_FlushLine()) + PyErr_Clear(); + fflush(stdout); + if (tb && tb != Py_None) + err = PyTraceBack_Print(tb, f); + if (err == 0 && + PyObject_HasAttrString(value, "print_file_and_line")) + { + PyObject *message; + const char *filename, *text; + int lineno, offset; + if (!parse_syntax_error(value, &message, &filename, + &lineno, &offset, &text)) + PyErr_Clear(); + else { + char buf[10]; + PyFile_WriteString(" File \"", f); + if (filename == NULL) + PyFile_WriteString("", f); + else + PyFile_WriteString(filename, f); + PyFile_WriteString("\", line ", f); + PyOS_snprintf(buf, sizeof(buf), "%d", lineno); + PyFile_WriteString(buf, f); + PyFile_WriteString("\n", f); + if (text != NULL) + print_error_text(f, offset, text); + Py_DECREF(value); + value = message; + /* Can't be bothered to check all those + PyFile_WriteString() calls */ + if (PyErr_Occurred()) + err = -1; + } + } + if (err) { + /* Don't do anything else */ + } + else if (PyExceptionClass_Check(exception)) { + PyObject* moduleName; + char* className = PyExceptionClass_Name(exception); + if (className != NULL) { + char *dot = strrchr(className, '.'); + if (dot != NULL) + className = dot+1; + } + + moduleName = PyObject_GetAttrString(exception, "__module__"); + if (moduleName == NULL) + err = PyFile_WriteString("", f); + else { + char* modstr = PyString_AsString(moduleName); + if (modstr && strcmp(modstr, "exceptions")) + { + err = PyFile_WriteString(modstr, f); + err += PyFile_WriteString(".", f); + } + Py_DECREF(moduleName); + } + if (err == 0) { + if (className == NULL) + err = PyFile_WriteString("", f); + else + err = PyFile_WriteString(className, f); + } + } + else + err = PyFile_WriteObject(exception, f, Py_PRINT_RAW); + if (err == 0 && (value != Py_None)) { + PyObject *s = PyObject_Str(value); + /* only print colon if the str() of the + object is not the empty string + */ + if (s == NULL) + err = -1; + else if (!PyString_Check(s) || + PyString_GET_SIZE(s) != 0) + err = PyFile_WriteString(": ", f); + if (err == 0) + err = PyFile_WriteObject(s, f, Py_PRINT_RAW); + Py_XDECREF(s); + } + /* try to write a newline in any case */ + err += PyFile_WriteString("\n", f); + } + Py_DECREF(value); + /* If an error happened here, don't show it. + XXX This is wrong, but too many callers rely on this behavior. */ + if (err != 0) + PyErr_Clear(); +} + +PyObject * +PyRun_StringFlags(const char *str, int start, PyObject *globals, + PyObject *locals, PyCompilerFlags *flags) +{ + PyObject *ret = NULL; + mod_ty mod; + PyArena *arena = PyArena_New(); + if (arena == NULL) + return NULL; + + mod = PyParser_ASTFromString(str, "", start, flags, arena); + if (mod != NULL) + ret = run_mod(mod, "", globals, locals, flags, arena); + PyArena_Free(arena); + return ret; +} + +PyObject * +PyRun_FileExFlags(FILE *fp, const char *filename, int start, PyObject *globals, + PyObject *locals, int closeit, PyCompilerFlags *flags) +{ + PyObject *ret; + mod_ty mod; + PyArena *arena = PyArena_New(); + if (arena == NULL) + return NULL; + + mod = PyParser_ASTFromFile(fp, filename, start, 0, 0, + flags, NULL, arena); + if (closeit) + fclose(fp); + if (mod == NULL) { + PyArena_Free(arena); + return NULL; + } + ret = run_mod(mod, filename, globals, locals, flags, arena); + PyArena_Free(arena); + return ret; +} + +static PyObject * +run_mod(mod_ty mod, const char *filename, PyObject *globals, PyObject *locals, + PyCompilerFlags *flags, PyArena *arena) +{ + PyCodeObject *co; + PyObject *v; + co = PyAST_Compile(mod, filename, flags, arena); + if (co == NULL) + return NULL; + v = PyEval_EvalCode(co, globals, locals); + Py_DECREF(co); + return v; +} + +static PyObject * +run_pyc_file(FILE *fp, const char *filename, PyObject *globals, + PyObject *locals, PyCompilerFlags *flags) +{ + PyCodeObject *co; + PyObject *v; + long magic; + long PyImport_GetMagicNumber(void); + + magic = PyMarshal_ReadLongFromFile(fp); + if (magic != PyImport_GetMagicNumber()) { + PyErr_SetString(PyExc_RuntimeError, + "Bad magic number in .pyc file"); + return NULL; + } + (void) PyMarshal_ReadLongFromFile(fp); + v = PyMarshal_ReadLastObjectFromFile(fp); + fclose(fp); + if (v == NULL || !PyCode_Check(v)) { + Py_XDECREF(v); + PyErr_SetString(PyExc_RuntimeError, + "Bad code object in .pyc file"); + return NULL; + } + co = (PyCodeObject *)v; + v = PyEval_EvalCode(co, globals, locals); + if (v && flags) + flags->cf_flags |= (co->co_flags & PyCF_MASK); + Py_DECREF(co); + return v; +} + +PyObject * +Py_CompileStringFlags(const char *str, const char *filename, int start, + PyCompilerFlags *flags) +{ + PyCodeObject *co; + mod_ty mod; + PyArena *arena = PyArena_New(); + if (arena == NULL) + return NULL; + + mod = PyParser_ASTFromString(str, filename, start, flags, arena); + if (mod == NULL) { + PyArena_Free(arena); + return NULL; + } + if (flags && (flags->cf_flags & PyCF_ONLY_AST)) { + PyObject *result = PyAST_mod2obj(mod); + PyArena_Free(arena); + return result; + } + co = PyAST_Compile(mod, filename, flags, arena); + PyArena_Free(arena); + return (PyObject *)co; +} + +struct symtable * +Py_SymtableString(const char *str, const char *filename, int start) +{ + struct symtable *st; + mod_ty mod; + PyCompilerFlags flags; + PyArena *arena = PyArena_New(); + if (arena == NULL) + return NULL; + + flags.cf_flags = 0; + + mod = PyParser_ASTFromString(str, filename, start, &flags, arena); + if (mod == NULL) { + PyArena_Free(arena); + return NULL; + } + st = PySymtable_Build(mod, filename, 0); + PyArena_Free(arena); + return st; +} + +/* Preferred access to parser is through AST. */ +mod_ty +PyParser_ASTFromString(const char *s, const char *filename, int start, + PyCompilerFlags *flags, PyArena *arena) +{ + mod_ty mod; + PyCompilerFlags localflags; + perrdetail err; + int iflags = PARSER_FLAGS(flags); + + node *n = PyParser_ParseStringFlagsFilenameEx(s, filename, + &_PyParser_Grammar, start, &err, + &iflags); + if (flags == NULL) { + localflags.cf_flags = 0; + flags = &localflags; + } + if (n) { + flags->cf_flags |= iflags & PyCF_MASK; + mod = PyAST_FromNode(n, flags, filename, arena); + PyNode_Free(n); + return mod; + } + else { + err_input(&err); + return NULL; + } +} + +mod_ty +PyParser_ASTFromFile(FILE *fp, const char *filename, int start, char *ps1, + char *ps2, PyCompilerFlags *flags, int *errcode, + PyArena *arena) +{ + mod_ty mod; + PyCompilerFlags localflags; + perrdetail err; + int iflags = PARSER_FLAGS(flags); + + node *n = PyParser_ParseFileFlagsEx(fp, filename, &_PyParser_Grammar, + start, ps1, ps2, &err, &iflags); + if (flags == NULL) { + localflags.cf_flags = 0; + flags = &localflags; + } + if (n) { + flags->cf_flags |= iflags & PyCF_MASK; + mod = PyAST_FromNode(n, flags, filename, arena); + PyNode_Free(n); + return mod; + } + else { + err_input(&err); + if (errcode) + *errcode = err.error; + return NULL; + } +} + +/* Simplified interface to parsefile -- return node or set exception */ + +node * +PyParser_SimpleParseFileFlags(FILE *fp, const char *filename, int start, int flags) +{ + perrdetail err; + node *n = PyParser_ParseFileFlags(fp, filename, &_PyParser_Grammar, + start, NULL, NULL, &err, flags); + if (n == NULL) + err_input(&err); + + return n; +} + +/* Simplified interface to parsestring -- return node or set exception */ + +node * +PyParser_SimpleParseStringFlags(const char *str, int start, int flags) +{ + perrdetail err; + node *n = PyParser_ParseStringFlags(str, &_PyParser_Grammar, + start, &err, flags); + if (n == NULL) + err_input(&err); + return n; +} + +node * +PyParser_SimpleParseStringFlagsFilename(const char *str, const char *filename, + int start, int flags) +{ + perrdetail err; + node *n = PyParser_ParseStringFlagsFilename(str, filename, + &_PyParser_Grammar, start, &err, flags); + if (n == NULL) + err_input(&err); + return n; +} + +node * +PyParser_SimpleParseStringFilename(const char *str, const char *filename, int start) +{ + return PyParser_SimpleParseStringFlagsFilename(str, filename, start, 0); +} + +/* May want to move a more generalized form of this to parsetok.c or + even parser modules. */ + +void +PyParser_SetError(perrdetail *err) +{ + err_input(err); +} + +/* Set the error appropriate to the given input error code (see errcode.h) */ + +static void +err_input(perrdetail *err) +{ + PyObject *v, *w, *errtype; + PyObject* u = NULL; + char *msg = NULL; + errtype = PyExc_SyntaxError; + switch (err->error) { + case E_ERROR: + return; + case E_SYNTAX: + errtype = PyExc_IndentationError; + if (err->expected == INDENT) + msg = "expected an indented block"; + else if (err->token == INDENT) + msg = "unexpected indent"; + else if (err->token == DEDENT) + msg = "unexpected unindent"; + else { + errtype = PyExc_SyntaxError; + msg = "invalid syntax"; + } + break; + case E_TOKEN: + msg = "invalid token"; + break; + case E_EOFS: + msg = "EOF while scanning triple-quoted string literal"; + break; + case E_EOLS: + msg = "EOL while scanning string literal"; + break; + case E_INTR: + if (!PyErr_Occurred()) + PyErr_SetNone(PyExc_KeyboardInterrupt); + goto cleanup; + case E_NOMEM: + PyErr_NoMemory(); + goto cleanup; + case E_EOF: + msg = "unexpected EOF while parsing"; + break; + case E_TABSPACE: + errtype = PyExc_TabError; + msg = "inconsistent use of tabs and spaces in indentation"; + break; + case E_OVERFLOW: + msg = "expression too long"; + break; + case E_DEDENT: + errtype = PyExc_IndentationError; + msg = "unindent does not match any outer indentation level"; + break; + case E_TOODEEP: + errtype = PyExc_IndentationError; + msg = "too many levels of indentation"; + break; + case E_DECODE: { + PyObject *type, *value, *tb; + PyErr_Fetch(&type, &value, &tb); + if (value != NULL) { + u = PyObject_Str(value); + if (u != NULL) { + msg = PyString_AsString(u); + } + } + if (msg == NULL) + msg = "unknown decode error"; + Py_XDECREF(type); + Py_XDECREF(value); + Py_XDECREF(tb); + break; + } + case E_LINECONT: + msg = "unexpected character after line continuation character"; + break; + default: + fprintf(stderr, "error=%d\n", err->error); + msg = "unknown parsing error"; + break; + } + v = Py_BuildValue("(ziiz)", err->filename, + err->lineno, err->offset, err->text); + w = NULL; + if (v != NULL) + w = Py_BuildValue("(sO)", msg, v); + Py_XDECREF(u); + Py_XDECREF(v); + PyErr_SetObject(errtype, w); + Py_XDECREF(w); +cleanup: + if (err->text != NULL) { + PyObject_FREE(err->text); + err->text = NULL; + } +} + +/* Print fatal error message and abort */ + +void +Py_FatalError(const char *msg) +{ + fprintf(stderr, "Fatal Python error: %s\n", msg); + fflush(stderr); /* it helps in Windows debug build */ + +#ifdef MS_WINDOWS + { + size_t len = strlen(msg); + WCHAR* buffer; + size_t i; + + /* Convert the message to wchar_t. This uses a simple one-to-one + conversion, assuming that the this error message actually uses ASCII + only. If this ceases to be true, we will have to convert. */ + buffer = alloca( (len+1) * (sizeof *buffer)); + for( i=0; i<=len; ++i) + buffer[i] = msg[i]; + OutputDebugStringW(L"Fatal Python error: "); + OutputDebugStringW(buffer); + OutputDebugStringW(L"\n"); + } +#ifdef _DEBUG + DebugBreak(); +#endif +#endif /* MS_WINDOWS */ + abort(); +} + +/* Clean up and exit */ + +#ifdef WITH_THREAD +#include "pythread.h" +#endif + +/* Wait until threading._shutdown completes, provided + the threading module was imported in the first place. + The shutdown routine will wait until all non-daemon + "threading" threads have completed. */ +static void +wait_for_thread_shutdown(void) +{ +#ifdef WITH_THREAD + PyObject *result; + PyThreadState *tstate = PyThreadState_GET(); + PyObject *threading = PyMapping_GetItemString(tstate->interp->modules, + "threading"); + if (threading == NULL) { + /* threading not imported */ + PyErr_Clear(); + return; + } + result = PyObject_CallMethod(threading, "_shutdown", ""); + if (result == NULL) + PyErr_WriteUnraisable(threading); + else + Py_DECREF(result); + Py_DECREF(threading); +#endif +} + +#define NEXITFUNCS 32 +static void (*exitfuncs[NEXITFUNCS])(void); +static int nexitfuncs = 0; + +int Py_AtExit(void (*func)(void)) +{ + if (nexitfuncs >= NEXITFUNCS) + return -1; + exitfuncs[nexitfuncs++] = func; + return 0; +} + +static void +call_sys_exitfunc(void) +{ + PyObject *exitfunc = PySys_GetObject("exitfunc"); + + if (exitfunc) { + PyObject *res; + Py_INCREF(exitfunc); + PySys_SetObject("exitfunc", (PyObject *)NULL); + res = PyEval_CallObject(exitfunc, (PyObject *)NULL); + if (res == NULL) { + if (!PyErr_ExceptionMatches(PyExc_SystemExit)) { + PySys_WriteStderr("Error in sys.exitfunc:\n"); + } + PyErr_Print(); + } + Py_DECREF(exitfunc); + } + + if (Py_FlushLine()) + PyErr_Clear(); +} + +static void +call_ll_exitfuncs(void) +{ + while (nexitfuncs > 0) + (*exitfuncs[--nexitfuncs])(); + + fflush(stdout); + fflush(stderr); +} + +void +Py_Exit(int sts) +{ + Py_Finalize(); + + exit(sts); +} + +static void +initsigs(void) +{ +#ifdef SIGPIPE + PyOS_setsig(SIGPIPE, SIG_IGN); +#endif +#ifdef SIGXFZ + PyOS_setsig(SIGXFZ, SIG_IGN); +#endif +#ifdef SIGXFSZ + PyOS_setsig(SIGXFSZ, SIG_IGN); +#endif + PyOS_InitInterrupts(); /* May imply initsignal() */ +} + + +/* + * The file descriptor fd is considered ``interactive'' if either + * a) isatty(fd) is TRUE, or + * b) the -i flag was given, and the filename associated with + * the descriptor is NULL or "" or "???". + */ +int +Py_FdIsInteractive(FILE *fp, const char *filename) +{ + if (isatty((int)fileno(fp))) + return 1; + if (!Py_InteractiveFlag) + return 0; + return (filename == NULL) || + (strcmp(filename, "") == 0) || + (strcmp(filename, "???") == 0); +} + + +#if defined(USE_STACKCHECK) +#if defined(WIN32) && defined(_MSC_VER) + +/* Stack checking for Microsoft C */ + +#include +#include + +/* + * Return non-zero when we run out of memory on the stack; zero otherwise. + */ +int +PyOS_CheckStack(void) +{ + __try { + /* alloca throws a stack overflow exception if there's + not enough space left on the stack */ + alloca(PYOS_STACK_MARGIN * sizeof(void*)); + return 0; + } __except (GetExceptionCode() == STATUS_STACK_OVERFLOW ? + EXCEPTION_EXECUTE_HANDLER : + EXCEPTION_CONTINUE_SEARCH) { + int errcode = _resetstkoflw(); + if (errcode == 0) + { + Py_FatalError("Could not reset the stack!"); + } + } + return 1; +} + +#endif /* WIN32 && _MSC_VER */ + +/* Alternate implementations can be added here... */ + +#endif /* USE_STACKCHECK */ + + +/* Wrappers around sigaction() or signal(). */ + +PyOS_sighandler_t +PyOS_getsig(int sig) +{ +#ifdef HAVE_SIGACTION + struct sigaction context; + if (sigaction(sig, NULL, &context) == -1) + return SIG_ERR; + return context.sa_handler; +#else + PyOS_sighandler_t handler; +/* Special signal handling for the secure CRT in Visual Studio 2005 */ +#if defined(_MSC_VER) && _MSC_VER >= 1400 + switch (sig) { + /* Only these signals are valid */ + case SIGINT: + case SIGILL: + case SIGFPE: + case SIGSEGV: + case SIGTERM: + case SIGBREAK: + case SIGABRT: + break; + /* Don't call signal() with other values or it will assert */ + default: + return SIG_ERR; + } +#endif /* _MSC_VER && _MSC_VER >= 1400 */ + handler = signal(sig, SIG_IGN); + if (handler != SIG_ERR) + signal(sig, handler); + return handler; +#endif +} + +PyOS_sighandler_t +PyOS_setsig(int sig, PyOS_sighandler_t handler) +{ +#ifdef HAVE_SIGACTION + /* Some code in Modules/signalmodule.c depends on sigaction() being + * used here if HAVE_SIGACTION is defined. Fix that if this code + * changes to invalidate that assumption. + */ + struct sigaction context, ocontext; + context.sa_handler = handler; + sigemptyset(&context.sa_mask); + context.sa_flags = 0; + if (sigaction(sig, &context, &ocontext) == -1) + return SIG_ERR; + return ocontext.sa_handler; +#else + PyOS_sighandler_t oldhandler; + oldhandler = signal(sig, handler); +#ifdef HAVE_SIGINTERRUPT + siginterrupt(sig, 1); +#endif + return oldhandler; +#endif +} + +/* Deprecated C API functions still provided for binary compatiblity */ + +#undef PyParser_SimpleParseFile +PyAPI_FUNC(node *) +PyParser_SimpleParseFile(FILE *fp, const char *filename, int start) +{ + return PyParser_SimpleParseFileFlags(fp, filename, start, 0); +} + +#undef PyParser_SimpleParseString +PyAPI_FUNC(node *) +PyParser_SimpleParseString(const char *str, int start) +{ + return PyParser_SimpleParseStringFlags(str, start, 0); +} + +#undef PyRun_AnyFile +PyAPI_FUNC(int) +PyRun_AnyFile(FILE *fp, const char *name) +{ + return PyRun_AnyFileExFlags(fp, name, 0, NULL); +} + +#undef PyRun_AnyFileEx +PyAPI_FUNC(int) +PyRun_AnyFileEx(FILE *fp, const char *name, int closeit) +{ + return PyRun_AnyFileExFlags(fp, name, closeit, NULL); +} + +#undef PyRun_AnyFileFlags +PyAPI_FUNC(int) +PyRun_AnyFileFlags(FILE *fp, const char *name, PyCompilerFlags *flags) +{ + return PyRun_AnyFileExFlags(fp, name, 0, flags); +} + +#undef PyRun_File +PyAPI_FUNC(PyObject *) +PyRun_File(FILE *fp, const char *p, int s, PyObject *g, PyObject *l) +{ + return PyRun_FileExFlags(fp, p, s, g, l, 0, NULL); +} + +#undef PyRun_FileEx +PyAPI_FUNC(PyObject *) +PyRun_FileEx(FILE *fp, const char *p, int s, PyObject *g, PyObject *l, int c) +{ + return PyRun_FileExFlags(fp, p, s, g, l, c, NULL); +} + +#undef PyRun_FileFlags +PyAPI_FUNC(PyObject *) +PyRun_FileFlags(FILE *fp, const char *p, int s, PyObject *g, PyObject *l, + PyCompilerFlags *flags) +{ + return PyRun_FileExFlags(fp, p, s, g, l, 0, flags); +} + +#undef PyRun_SimpleFile +PyAPI_FUNC(int) +PyRun_SimpleFile(FILE *f, const char *p) +{ + return PyRun_SimpleFileExFlags(f, p, 0, NULL); +} + +#undef PyRun_SimpleFileEx +PyAPI_FUNC(int) +PyRun_SimpleFileEx(FILE *f, const char *p, int c) +{ + return PyRun_SimpleFileExFlags(f, p, c, NULL); +} + + +#undef PyRun_String +PyAPI_FUNC(PyObject *) +PyRun_String(const char *str, int s, PyObject *g, PyObject *l) +{ + return PyRun_StringFlags(str, s, g, l, NULL); +} + +#undef PyRun_SimpleString +PyAPI_FUNC(int) +PyRun_SimpleString(const char *s) +{ + return PyRun_SimpleStringFlags(s, NULL); +} + +#undef Py_CompileString +PyAPI_FUNC(PyObject *) +Py_CompileString(const char *str, const char *p, int s) +{ + return Py_CompileStringFlags(str, p, s, NULL); +} + +#undef PyRun_InteractiveOne +PyAPI_FUNC(int) +PyRun_InteractiveOne(FILE *f, const char *p) +{ + return PyRun_InteractiveOneFlags(f, p, NULL); +} + +#undef PyRun_InteractiveLoop +PyAPI_FUNC(int) +PyRun_InteractiveLoop(FILE *f, const char *p) +{ + return PyRun_InteractiveLoopFlags(f, p, NULL); +} + +#ifdef __cplusplus +} +#endif + diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/structmember.c b/AppPkg/Applications/Python/Python-2.7.10/Python/structmember.c new file mode 100644 index 0000000000..ce018c79a0 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/structmember.c @@ -0,0 +1,363 @@ + +/* Map C struct members to Python object attributes */ + +#include "Python.h" + +#include "structmember.h" + +static PyObject * +listmembers(struct memberlist *mlist) +{ + int i, n; + PyObject *v; + for (n = 0; mlist[n].name != NULL; n++) + ; + v = PyList_New(n); + if (v != NULL) { + for (i = 0; i < n; i++) + PyList_SetItem(v, i, + PyString_FromString(mlist[i].name)); + if (PyErr_Occurred()) { + Py_DECREF(v); + v = NULL; + } + else { + PyList_Sort(v); + } + } + return v; +} + +PyObject * +PyMember_Get(const char *addr, struct memberlist *mlist, const char *name) +{ + struct memberlist *l; + + if (strcmp(name, "__members__") == 0) + return listmembers(mlist); + for (l = mlist; l->name != NULL; l++) { + if (strcmp(l->name, name) == 0) { + PyMemberDef copy; + copy.name = l->name; + copy.type = l->type; + copy.offset = l->offset; + copy.flags = l->flags; + copy.doc = NULL; + return PyMember_GetOne(addr, ©); + } + } + PyErr_SetString(PyExc_AttributeError, name); + return NULL; +} + +PyObject * +PyMember_GetOne(const char *addr, PyMemberDef *l) +{ + PyObject *v; + if ((l->flags & READ_RESTRICTED) && + PyEval_GetRestricted()) { + PyErr_SetString(PyExc_RuntimeError, "restricted attribute"); + return NULL; + } + addr += l->offset; + switch (l->type) { + case T_BOOL: + v = PyBool_FromLong(*(char*)addr); + break; + case T_BYTE: + v = PyInt_FromLong(*(char*)addr); + break; + case T_UBYTE: + v = PyLong_FromUnsignedLong(*(unsigned char*)addr); + break; + case T_SHORT: + v = PyInt_FromLong(*(short*)addr); + break; + case T_USHORT: + v = PyLong_FromUnsignedLong(*(unsigned short*)addr); + break; + case T_INT: + v = PyInt_FromLong(*(int*)addr); + break; + case T_UINT: + v = PyLong_FromUnsignedLong(*(unsigned int*)addr); + break; + case T_LONG: + v = PyInt_FromLong(*(long*)addr); + break; + case T_ULONG: + v = PyLong_FromUnsignedLong(*(unsigned long*)addr); + break; + case T_PYSSIZET: + v = PyInt_FromSsize_t(*(Py_ssize_t*)addr); + break; + case T_FLOAT: + v = PyFloat_FromDouble((double)*(float*)addr); + break; + case T_DOUBLE: + v = PyFloat_FromDouble(*(double*)addr); + break; + case T_STRING: + if (*(char**)addr == NULL) { + Py_INCREF(Py_None); + v = Py_None; + } + else + v = PyString_FromString(*(char**)addr); + break; + case T_STRING_INPLACE: + v = PyString_FromString((char*)addr); + break; + case T_CHAR: + v = PyString_FromStringAndSize((char*)addr, 1); + break; + case T_OBJECT: + v = *(PyObject **)addr; + if (v == NULL) + v = Py_None; + Py_INCREF(v); + break; + case T_OBJECT_EX: + v = *(PyObject **)addr; + if (v == NULL) + PyErr_SetString(PyExc_AttributeError, l->name); + Py_XINCREF(v); + break; +#ifdef HAVE_LONG_LONG + case T_LONGLONG: + v = PyLong_FromLongLong(*(PY_LONG_LONG *)addr); + break; + case T_ULONGLONG: + v = PyLong_FromUnsignedLongLong(*(unsigned PY_LONG_LONG *)addr); + break; +#endif /* HAVE_LONG_LONG */ + default: + PyErr_SetString(PyExc_SystemError, "bad memberdescr type"); + v = NULL; + } + return v; +} + +int +PyMember_Set(char *addr, struct memberlist *mlist, const char *name, PyObject *v) +{ + struct memberlist *l; + + for (l = mlist; l->name != NULL; l++) { + if (strcmp(l->name, name) == 0) { + PyMemberDef copy; + copy.name = l->name; + copy.type = l->type; + copy.offset = l->offset; + copy.flags = l->flags; + copy.doc = NULL; + return PyMember_SetOne(addr, ©, v); + } + } + + PyErr_SetString(PyExc_AttributeError, name); + return -1; +} + +#define WARN(msg) \ + do { \ + if (PyErr_Warn(PyExc_RuntimeWarning, msg) < 0) \ + return -1; \ + } while (0) + +int +PyMember_SetOne(char *addr, PyMemberDef *l, PyObject *v) +{ + PyObject *oldv; + + addr += l->offset; + + if ((l->flags & READONLY)) + { + PyErr_SetString(PyExc_TypeError, "readonly attribute"); + return -1; + } + if ((l->flags & PY_WRITE_RESTRICTED) && PyEval_GetRestricted()) { + PyErr_SetString(PyExc_RuntimeError, "restricted attribute"); + return -1; + } + if (v == NULL) { + if (l->type == T_OBJECT_EX) { + /* Check if the attribute is set. */ + if (*(PyObject **)addr == NULL) { + PyErr_SetString(PyExc_AttributeError, l->name); + return -1; + } + } + else if (l->type != T_OBJECT) { + PyErr_SetString(PyExc_TypeError, + "can't delete numeric/char attribute"); + return -1; + } + } + switch (l->type) { + case T_BOOL:{ + if (!PyBool_Check(v)) { + PyErr_SetString(PyExc_TypeError, + "attribute value type must be bool"); + return -1; + } + if (v == Py_True) + *(char*)addr = (char) 1; + else + *(char*)addr = (char) 0; + break; + } + case T_BYTE:{ + long long_val = PyInt_AsLong(v); + if ((long_val == -1) && PyErr_Occurred()) + return -1; + *(char*)addr = (char)long_val; + /* XXX: For compatibility, only warn about truncations + for now. */ + if ((long_val > CHAR_MAX) || (long_val < CHAR_MIN)) + WARN("Truncation of value to char"); + break; + } + case T_UBYTE:{ + long long_val = PyInt_AsLong(v); + if ((long_val == -1) && PyErr_Occurred()) + return -1; + *(unsigned char*)addr = (unsigned char)long_val; + if ((long_val > UCHAR_MAX) || (long_val < 0)) + WARN("Truncation of value to unsigned char"); + break; + } + case T_SHORT:{ + long long_val = PyInt_AsLong(v); + if ((long_val == -1) && PyErr_Occurred()) + return -1; + *(short*)addr = (short)long_val; + if ((long_val > SHRT_MAX) || (long_val < SHRT_MIN)) + WARN("Truncation of value to short"); + break; + } + case T_USHORT:{ + long long_val = PyInt_AsLong(v); + if ((long_val == -1) && PyErr_Occurred()) + return -1; + *(unsigned short*)addr = (unsigned short)long_val; + if ((long_val > USHRT_MAX) || (long_val < 0)) + WARN("Truncation of value to unsigned short"); + break; + } + case T_INT:{ + long long_val = PyInt_AsLong(v); + if ((long_val == -1) && PyErr_Occurred()) + return -1; + *(int *)addr = (int)long_val; + if ((long_val > INT_MAX) || (long_val < INT_MIN)) + WARN("Truncation of value to int"); + break; + } + case T_UINT:{ + unsigned long ulong_val = PyLong_AsUnsignedLong(v); + if ((ulong_val == (unsigned long)-1) && PyErr_Occurred()) { + /* XXX: For compatibility, accept negative int values + as well. */ + PyErr_Clear(); + ulong_val = PyLong_AsLong(v); + if ((ulong_val == (unsigned long)-1) && + PyErr_Occurred()) + return -1; + *(unsigned int *)addr = (unsigned int)ulong_val; + WARN("Writing negative value into unsigned field"); + } else + *(unsigned int *)addr = (unsigned int)ulong_val; + if (ulong_val > UINT_MAX) + WARN("Truncation of value to unsigned int"); + break; + } + case T_LONG:{ + *(long*)addr = PyLong_AsLong(v); + if ((*(long*)addr == -1) && PyErr_Occurred()) + return -1; + break; + } + case T_ULONG:{ + *(unsigned long*)addr = PyLong_AsUnsignedLong(v); + if ((*(unsigned long*)addr == (unsigned long)-1) + && PyErr_Occurred()) { + /* XXX: For compatibility, accept negative int values + as well. */ + PyErr_Clear(); + *(unsigned long*)addr = PyLong_AsLong(v); + if ((*(unsigned long*)addr == (unsigned long)-1) + && PyErr_Occurred()) + return -1; + WARN("Writing negative value into unsigned field"); + } + break; + } + case T_PYSSIZET:{ + *(Py_ssize_t*)addr = PyInt_AsSsize_t(v); + if ((*(Py_ssize_t*)addr == (Py_ssize_t)-1) + && PyErr_Occurred()) + return -1; + break; + } + case T_FLOAT:{ + double double_val = PyFloat_AsDouble(v); + if ((double_val == -1) && PyErr_Occurred()) + return -1; + *(float*)addr = (float)double_val; + break; + } + case T_DOUBLE: + *(double*)addr = PyFloat_AsDouble(v); + if ((*(double*)addr == -1) && PyErr_Occurred()) + return -1; + break; + case T_OBJECT: + case T_OBJECT_EX: + Py_XINCREF(v); + oldv = *(PyObject **)addr; + *(PyObject **)addr = v; + Py_XDECREF(oldv); + break; + case T_CHAR: + if (PyString_Check(v) && PyString_Size(v) == 1) { + *(char*)addr = PyString_AsString(v)[0]; + } + else { + PyErr_BadArgument(); + return -1; + } + break; + case T_STRING: + case T_STRING_INPLACE: + PyErr_SetString(PyExc_TypeError, "readonly attribute"); + return -1; +#ifdef HAVE_LONG_LONG + case T_LONGLONG:{ + PY_LONG_LONG value; + *(PY_LONG_LONG*)addr = value = PyLong_AsLongLong(v); + if ((value == -1) && PyErr_Occurred()) + return -1; + break; + } + case T_ULONGLONG:{ + unsigned PY_LONG_LONG value; + /* ??? PyLong_AsLongLong accepts an int, but PyLong_AsUnsignedLongLong + doesn't ??? */ + if (PyLong_Check(v)) + *(unsigned PY_LONG_LONG*)addr = value = PyLong_AsUnsignedLongLong(v); + else + *(unsigned PY_LONG_LONG*)addr = value = PyInt_AsLong(v); + if ((value == (unsigned PY_LONG_LONG)-1) && PyErr_Occurred()) + return -1; + break; + } +#endif /* HAVE_LONG_LONG */ + default: + PyErr_Format(PyExc_SystemError, + "bad memberdescr type for %s", l->name); + return -1; + } + return 0; +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/symtable.c b/AppPkg/Applications/Python/Python-2.7.10/Python/symtable.c new file mode 100644 index 0000000000..661662f702 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/symtable.c @@ -0,0 +1,1556 @@ +#include "Python.h" +#include "Python-ast.h" +#include "code.h" +#include "symtable.h" +#include "structmember.h" + +/* error strings used for warnings */ +#define GLOBAL_AFTER_ASSIGN \ +"name '%.400s' is assigned to before global declaration" + +#define GLOBAL_AFTER_USE \ +"name '%.400s' is used prior to global declaration" + +#define IMPORT_STAR_WARNING "import * only allowed at module level" + +#define RETURN_VAL_IN_GENERATOR \ + "'return' with argument inside generator" + + +static PySTEntryObject * +ste_new(struct symtable *st, identifier name, _Py_block_ty block, + void *key, int lineno) +{ + PySTEntryObject *ste = NULL; + PyObject *k = NULL; + + k = PyLong_FromVoidPtr(key); + if (k == NULL) + goto fail; + ste = PyObject_New(PySTEntryObject, &PySTEntry_Type); + if (ste == NULL) { + Py_DECREF(k); + goto fail; + } + ste->ste_table = st; + ste->ste_id = k; /* ste owns reference to k */ + + ste->ste_name = name; + Py_INCREF(name); + + ste->ste_symbols = NULL; + ste->ste_varnames = NULL; + ste->ste_children = NULL; + + ste->ste_symbols = PyDict_New(); + if (ste->ste_symbols == NULL) + goto fail; + + ste->ste_varnames = PyList_New(0); + if (ste->ste_varnames == NULL) + goto fail; + + ste->ste_children = PyList_New(0); + if (ste->ste_children == NULL) + goto fail; + + ste->ste_type = block; + ste->ste_unoptimized = 0; + ste->ste_nested = 0; + ste->ste_free = 0; + ste->ste_varargs = 0; + ste->ste_varkeywords = 0; + ste->ste_opt_lineno = 0; + ste->ste_tmpname = 0; + ste->ste_lineno = lineno; + + if (st->st_cur != NULL && + (st->st_cur->ste_nested || + st->st_cur->ste_type == FunctionBlock)) + ste->ste_nested = 1; + ste->ste_child_free = 0; + ste->ste_generator = 0; + ste->ste_returns_value = 0; + + if (PyDict_SetItem(st->st_symbols, ste->ste_id, (PyObject *)ste) < 0) + goto fail; + + return ste; + fail: + Py_XDECREF(ste); + return NULL; +} + +static PyObject * +ste_repr(PySTEntryObject *ste) +{ + char buf[256]; + + PyOS_snprintf(buf, sizeof(buf), + "", + PyString_AS_STRING(ste->ste_name), + PyInt_AS_LONG(ste->ste_id), ste->ste_lineno); + return PyString_FromString(buf); +} + +static void +ste_dealloc(PySTEntryObject *ste) +{ + ste->ste_table = NULL; + Py_XDECREF(ste->ste_id); + Py_XDECREF(ste->ste_name); + Py_XDECREF(ste->ste_symbols); + Py_XDECREF(ste->ste_varnames); + Py_XDECREF(ste->ste_children); + PyObject_Del(ste); +} + +#define OFF(x) offsetof(PySTEntryObject, x) + +static PyMemberDef ste_memberlist[] = { + {"id", T_OBJECT, OFF(ste_id), READONLY}, + {"name", T_OBJECT, OFF(ste_name), READONLY}, + {"symbols", T_OBJECT, OFF(ste_symbols), READONLY}, + {"varnames", T_OBJECT, OFF(ste_varnames), READONLY}, + {"children", T_OBJECT, OFF(ste_children), READONLY}, + {"optimized",T_INT, OFF(ste_unoptimized), READONLY}, + {"nested", T_INT, OFF(ste_nested), READONLY}, + {"type", T_INT, OFF(ste_type), READONLY}, + {"lineno", T_INT, OFF(ste_lineno), READONLY}, + {NULL} +}; + +PyTypeObject PySTEntry_Type = { + PyVarObject_HEAD_INIT(&PyType_Type, 0) + "symtable entry", + sizeof(PySTEntryObject), + 0, + (destructor)ste_dealloc, /* tp_dealloc */ + 0, /* tp_print */ + 0, /* tp_getattr */ + 0, /* tp_setattr */ + 0, /* tp_compare */ + (reprfunc)ste_repr, /* tp_repr */ + 0, /* tp_as_number */ + 0, /* tp_as_sequence */ + 0, /* tp_as_mapping */ + 0, /* tp_hash */ + 0, /* tp_call */ + 0, /* tp_str */ + PyObject_GenericGetAttr, /* tp_getattro */ + 0, /* tp_setattro */ + 0, /* tp_as_buffer */ + Py_TPFLAGS_DEFAULT, /* tp_flags */ + 0, /* tp_doc */ + 0, /* tp_traverse */ + 0, /* tp_clear */ + 0, /* tp_richcompare */ + 0, /* tp_weaklistoffset */ + 0, /* tp_iter */ + 0, /* tp_iternext */ + 0, /* tp_methods */ + ste_memberlist, /* tp_members */ + 0, /* tp_getset */ + 0, /* tp_base */ + 0, /* tp_dict */ + 0, /* tp_descr_get */ + 0, /* tp_descr_set */ + 0, /* tp_dictoffset */ + 0, /* tp_init */ + 0, /* tp_alloc */ + 0, /* tp_new */ +}; + +static int symtable_analyze(struct symtable *st); +static int symtable_warn(struct symtable *st, char *msg, int lineno); +static int symtable_enter_block(struct symtable *st, identifier name, + _Py_block_ty block, void *ast, int lineno); +static int symtable_exit_block(struct symtable *st, void *ast); +static int symtable_visit_stmt(struct symtable *st, stmt_ty s); +static int symtable_visit_expr(struct symtable *st, expr_ty s); +static int symtable_visit_genexp(struct symtable *st, expr_ty s); +static int symtable_visit_setcomp(struct symtable *st, expr_ty e); +static int symtable_visit_dictcomp(struct symtable *st, expr_ty e); +static int symtable_visit_arguments(struct symtable *st, arguments_ty); +static int symtable_visit_excepthandler(struct symtable *st, excepthandler_ty); +static int symtable_visit_alias(struct symtable *st, alias_ty); +static int symtable_visit_comprehension(struct symtable *st, comprehension_ty); +static int symtable_visit_keyword(struct symtable *st, keyword_ty); +static int symtable_visit_slice(struct symtable *st, slice_ty); +static int symtable_visit_params(struct symtable *st, asdl_seq *args, int top); +static int symtable_visit_params_nested(struct symtable *st, asdl_seq *args); +static int symtable_implicit_arg(struct symtable *st, int pos); + + +static identifier top = NULL, lambda = NULL, genexpr = NULL, setcomp = NULL, + dictcomp = NULL; + +#define GET_IDENTIFIER(VAR) \ + ((VAR) ? (VAR) : ((VAR) = PyString_InternFromString(# VAR))) + +#define DUPLICATE_ARGUMENT \ +"duplicate argument '%s' in function definition" + +static struct symtable * +symtable_new(void) +{ + struct symtable *st; + + st = (struct symtable *)PyMem_Malloc(sizeof(struct symtable)); + if (st == NULL) + return NULL; + + st->st_filename = NULL; + st->st_symbols = NULL; + + if ((st->st_stack = PyList_New(0)) == NULL) + goto fail; + if ((st->st_symbols = PyDict_New()) == NULL) + goto fail; + st->st_cur = NULL; + st->st_private = NULL; + return st; + fail: + PySymtable_Free(st); + return NULL; +} + +struct symtable * +PySymtable_Build(mod_ty mod, const char *filename, PyFutureFeatures *future) +{ + struct symtable *st = symtable_new(); + asdl_seq *seq; + int i; + + if (st == NULL) + return st; + st->st_filename = filename; + st->st_future = future; + if (!GET_IDENTIFIER(top) || + !symtable_enter_block(st, top, ModuleBlock, (void *)mod, 0)) { + PySymtable_Free(st); + return NULL; + } + + st->st_top = st->st_cur; + st->st_cur->ste_unoptimized = OPT_TOPLEVEL; + /* Any other top-level initialization? */ + switch (mod->kind) { + case Module_kind: + seq = mod->v.Module.body; + for (i = 0; i < asdl_seq_LEN(seq); i++) + if (!symtable_visit_stmt(st, + (stmt_ty)asdl_seq_GET(seq, i))) + goto error; + break; + case Expression_kind: + if (!symtable_visit_expr(st, mod->v.Expression.body)) + goto error; + break; + case Interactive_kind: + seq = mod->v.Interactive.body; + for (i = 0; i < asdl_seq_LEN(seq); i++) + if (!symtable_visit_stmt(st, + (stmt_ty)asdl_seq_GET(seq, i))) + goto error; + break; + case Suite_kind: + PyErr_SetString(PyExc_RuntimeError, + "this compiler does not handle Suites"); + goto error; + } + if (!symtable_exit_block(st, (void *)mod)) { + PySymtable_Free(st); + return NULL; + } + if (symtable_analyze(st)) + return st; + PySymtable_Free(st); + return NULL; + error: + (void) symtable_exit_block(st, (void *)mod); + PySymtable_Free(st); + return NULL; +} + +void +PySymtable_Free(struct symtable *st) +{ + Py_XDECREF(st->st_symbols); + Py_XDECREF(st->st_stack); + PyMem_Free((void *)st); +} + +PySTEntryObject * +PySymtable_Lookup(struct symtable *st, void *key) +{ + PyObject *k, *v; + + k = PyLong_FromVoidPtr(key); + if (k == NULL) + return NULL; + v = PyDict_GetItem(st->st_symbols, k); + if (v) { + assert(PySTEntry_Check(v)); + Py_INCREF(v); + } + else { + PyErr_SetString(PyExc_KeyError, + "unknown symbol table entry"); + } + + Py_DECREF(k); + return (PySTEntryObject *)v; +} + +int +PyST_GetScope(PySTEntryObject *ste, PyObject *name) +{ + PyObject *v = PyDict_GetItem(ste->ste_symbols, name); + if (!v) + return 0; + assert(PyInt_Check(v)); + return (PyInt_AS_LONG(v) >> SCOPE_OFF) & SCOPE_MASK; +} + + +/* Analyze raw symbol information to determine scope of each name. + + The next several functions are helpers for PySymtable_Analyze(), + which determines whether a name is local, global, or free. In addition, + it determines which local variables are cell variables; they provide + bindings that are used for free variables in enclosed blocks. + + There are also two kinds of free variables, implicit and explicit. An + explicit global is declared with the global statement. An implicit + global is a free variable for which the compiler has found no binding + in an enclosing function scope. The implicit global is either a global + or a builtin. Python's module and class blocks use the xxx_NAME opcodes + to handle these names to implement slightly odd semantics. In such a + block, the name is treated as global until it is assigned to; then it + is treated as a local. + + The symbol table requires two passes to determine the scope of each name. + The first pass collects raw facts from the AST: the name is a parameter + here, the name is used by not defined here, etc. The second pass analyzes + these facts during a pass over the PySTEntryObjects created during pass 1. + + When a function is entered during the second pass, the parent passes + the set of all name bindings visible to its children. These bindings + are used to determine if the variable is free or an implicit global. + After doing the local analysis, it analyzes each of its child blocks + using an updated set of name bindings. + + The children update the free variable set. If a local variable is free + in a child, the variable is marked as a cell. The current function must + provide runtime storage for the variable that may outlive the function's + frame. Cell variables are removed from the free set before the analyze + function returns to its parent. + + The sets of bound and free variables are implemented as dictionaries + mapping strings to None. +*/ + +#define SET_SCOPE(DICT, NAME, I) { \ + PyObject *o = PyInt_FromLong(I); \ + if (!o) \ + return 0; \ + if (PyDict_SetItem((DICT), (NAME), o) < 0) { \ + Py_DECREF(o); \ + return 0; \ + } \ + Py_DECREF(o); \ +} + +/* Decide on scope of name, given flags. + + The namespace dictionaries may be modified to record information + about the new name. For example, a new global will add an entry to + global. A name that was global can be changed to local. +*/ + +static int +analyze_name(PySTEntryObject *ste, PyObject *dict, PyObject *name, long flags, + PyObject *bound, PyObject *local, PyObject *free, + PyObject *global) +{ + if (flags & DEF_GLOBAL) { + if (flags & DEF_PARAM) { + PyErr_Format(PyExc_SyntaxError, + "name '%s' is local and global", + PyString_AS_STRING(name)); + PyErr_SyntaxLocation(ste->ste_table->st_filename, + ste->ste_lineno); + + return 0; + } + SET_SCOPE(dict, name, GLOBAL_EXPLICIT); + if (PyDict_SetItem(global, name, Py_None) < 0) + return 0; + if (bound && PyDict_GetItem(bound, name)) { + if (PyDict_DelItem(bound, name) < 0) + return 0; + } + return 1; + } + if (flags & DEF_BOUND) { + SET_SCOPE(dict, name, LOCAL); + if (PyDict_SetItem(local, name, Py_None) < 0) + return 0; + if (PyDict_GetItem(global, name)) { + if (PyDict_DelItem(global, name) < 0) + return 0; + } + return 1; + } + /* If an enclosing block has a binding for this name, it + is a free variable rather than a global variable. + Note that having a non-NULL bound implies that the block + is nested. + */ + if (bound && PyDict_GetItem(bound, name)) { + SET_SCOPE(dict, name, FREE); + ste->ste_free = 1; + if (PyDict_SetItem(free, name, Py_None) < 0) + return 0; + return 1; + } + /* If a parent has a global statement, then call it global + explicit? It could also be global implicit. + */ + else if (global && PyDict_GetItem(global, name)) { + SET_SCOPE(dict, name, GLOBAL_IMPLICIT); + return 1; + } + else { + if (ste->ste_nested) + ste->ste_free = 1; + SET_SCOPE(dict, name, GLOBAL_IMPLICIT); + return 1; + } + /* Should never get here. */ + PyErr_Format(PyExc_SystemError, "failed to set scope for %s", + PyString_AS_STRING(name)); + return 0; +} + +#undef SET_SCOPE + +/* If a name is defined in free and also in locals, then this block + provides the binding for the free variable. The name should be + marked CELL in this block and removed from the free list. + + Note that the current block's free variables are included in free. + That's safe because no name can be free and local in the same scope. +*/ + +static int +analyze_cells(PyObject *scope, PyObject *free) +{ + PyObject *name, *v, *w; + int success = 0; + Py_ssize_t pos = 0; + + w = PyInt_FromLong(CELL); + if (!w) + return 0; + while (PyDict_Next(scope, &pos, &name, &v)) { + long flags; + assert(PyInt_Check(v)); + flags = PyInt_AS_LONG(v); + if (flags != LOCAL) + continue; + if (!PyDict_GetItem(free, name)) + continue; + /* Replace LOCAL with CELL for this name, and remove + from free. It is safe to replace the value of name + in the dict, because it will not cause a resize. + */ + if (PyDict_SetItem(scope, name, w) < 0) + goto error; + if (PyDict_DelItem(free, name) < 0) + goto error; + } + success = 1; + error: + Py_DECREF(w); + return success; +} + +/* Check for illegal statements in unoptimized namespaces */ +static int +check_unoptimized(const PySTEntryObject* ste) { + char buf[300]; + const char* trailer; + + if (ste->ste_type != FunctionBlock || !ste->ste_unoptimized + || !(ste->ste_free || ste->ste_child_free)) + return 1; + + trailer = (ste->ste_child_free ? + "contains a nested function with free variables" : + "is a nested function"); + + switch (ste->ste_unoptimized) { + case OPT_TOPLEVEL: /* exec / import * at top-level is fine */ + case OPT_EXEC: /* qualified exec is fine */ + return 1; + case OPT_IMPORT_STAR: + PyOS_snprintf(buf, sizeof(buf), + "import * is not allowed in function '%.100s' " + "because it %s", + PyString_AS_STRING(ste->ste_name), trailer); + break; + case OPT_BARE_EXEC: + PyOS_snprintf(buf, sizeof(buf), + "unqualified exec is not allowed in function " + "'%.100s' because it %s", + PyString_AS_STRING(ste->ste_name), trailer); + break; + default: + PyOS_snprintf(buf, sizeof(buf), + "function '%.100s' uses import * and bare exec, " + "which are illegal because it %s", + PyString_AS_STRING(ste->ste_name), trailer); + break; + } + + PyErr_SetString(PyExc_SyntaxError, buf); + PyErr_SyntaxLocation(ste->ste_table->st_filename, + ste->ste_opt_lineno); + return 0; +} + +/* Enter the final scope information into the st_symbols dict. + * + * All arguments are dicts. Modifies symbols, others are read-only. +*/ +static int +update_symbols(PyObject *symbols, PyObject *scope, + PyObject *bound, PyObject *free, int classflag) +{ + PyObject *name, *v, *u, *w, *free_value = NULL; + Py_ssize_t pos = 0; + + while (PyDict_Next(symbols, &pos, &name, &v)) { + long i, flags; + assert(PyInt_Check(v)); + flags = PyInt_AS_LONG(v); + w = PyDict_GetItem(scope, name); + assert(w && PyInt_Check(w)); + i = PyInt_AS_LONG(w); + flags |= (i << SCOPE_OFF); + u = PyInt_FromLong(flags); + if (!u) + return 0; + if (PyDict_SetItem(symbols, name, u) < 0) { + Py_DECREF(u); + return 0; + } + Py_DECREF(u); + } + + free_value = PyInt_FromLong(FREE << SCOPE_OFF); + if (!free_value) + return 0; + + /* add a free variable when it's only use is for creating a closure */ + pos = 0; + while (PyDict_Next(free, &pos, &name, &v)) { + PyObject *o = PyDict_GetItem(symbols, name); + + if (o) { + /* It could be a free variable in a method of + the class that has the same name as a local + or global in the class scope. + */ + if (classflag && + PyInt_AS_LONG(o) & (DEF_BOUND | DEF_GLOBAL)) { + long i = PyInt_AS_LONG(o) | DEF_FREE_CLASS; + o = PyInt_FromLong(i); + if (!o) { + Py_DECREF(free_value); + return 0; + } + if (PyDict_SetItem(symbols, name, o) < 0) { + Py_DECREF(o); + Py_DECREF(free_value); + return 0; + } + Py_DECREF(o); + } + /* else it's not free, probably a cell */ + continue; + } + if (!PyDict_GetItem(bound, name)) + continue; /* it's a global */ + + if (PyDict_SetItem(symbols, name, free_value) < 0) { + Py_DECREF(free_value); + return 0; + } + } + Py_DECREF(free_value); + return 1; +} + +/* Make final symbol table decisions for block of ste. + + Arguments: + ste -- current symtable entry (input/output) + bound -- set of variables bound in enclosing scopes (input). bound + is NULL for module blocks. + free -- set of free variables in enclosed scopes (output) + globals -- set of declared global variables in enclosing scopes (input) + + The implementation uses two mutually recursive functions, + analyze_block() and analyze_child_block(). analyze_block() is + responsible for analyzing the individual names defined in a block. + analyze_child_block() prepares temporary namespace dictionaries + used to evaluated nested blocks. + + The two functions exist because a child block should see the name + bindings of its enclosing blocks, but those bindings should not + propagate back to a parent block. +*/ + +static int +analyze_child_block(PySTEntryObject *entry, PyObject *bound, PyObject *free, + PyObject *global, PyObject* child_free); + +static int +analyze_block(PySTEntryObject *ste, PyObject *bound, PyObject *free, + PyObject *global) +{ + PyObject *name, *v, *local = NULL, *scope = NULL; + PyObject *newbound = NULL, *newglobal = NULL; + PyObject *newfree = NULL, *allfree = NULL; + int i, success = 0; + Py_ssize_t pos = 0; + + local = PyDict_New(); /* collect new names bound in block */ + if (!local) + goto error; + scope = PyDict_New(); /* collect scopes defined for each name */ + if (!scope) + goto error; + + /* Allocate new global and bound variable dictionaries. These + dictionaries hold the names visible in nested blocks. For + ClassBlocks, the bound and global names are initialized + before analyzing names, because class bindings aren't + visible in methods. For other blocks, they are initialized + after names are analyzed. + */ + + /* TODO(jhylton): Package these dicts in a struct so that we + can write reasonable helper functions? + */ + newglobal = PyDict_New(); + if (!newglobal) + goto error; + newbound = PyDict_New(); + if (!newbound) + goto error; + newfree = PyDict_New(); + if (!newfree) + goto error; + + if (ste->ste_type == ClassBlock) { + if (PyDict_Update(newglobal, global) < 0) + goto error; + if (bound) + if (PyDict_Update(newbound, bound) < 0) + goto error; + } + + while (PyDict_Next(ste->ste_symbols, &pos, &name, &v)) { + long flags = PyInt_AS_LONG(v); + if (!analyze_name(ste, scope, name, flags, + bound, local, free, global)) + goto error; + } + + if (ste->ste_type != ClassBlock) { + if (ste->ste_type == FunctionBlock) { + if (PyDict_Update(newbound, local) < 0) + goto error; + } + if (bound) { + if (PyDict_Update(newbound, bound) < 0) + goto error; + } + if (PyDict_Update(newglobal, global) < 0) + goto error; + } + + /* Recursively call analyze_block() on each child block. + + newbound, newglobal now contain the names visible in + nested blocks. The free variables in the children will + be collected in allfree. + */ + allfree = PyDict_New(); + if (!allfree) + goto error; + for (i = 0; i < PyList_GET_SIZE(ste->ste_children); ++i) { + PyObject *c = PyList_GET_ITEM(ste->ste_children, i); + PySTEntryObject* entry; + assert(c && PySTEntry_Check(c)); + entry = (PySTEntryObject*)c; + if (!analyze_child_block(entry, newbound, newfree, newglobal, + allfree)) + goto error; + if (entry->ste_free || entry->ste_child_free) + ste->ste_child_free = 1; + } + + if (PyDict_Update(newfree, allfree) < 0) + goto error; + if (ste->ste_type == FunctionBlock && !analyze_cells(scope, newfree)) + goto error; + if (!update_symbols(ste->ste_symbols, scope, bound, newfree, + ste->ste_type == ClassBlock)) + goto error; + if (!check_unoptimized(ste)) + goto error; + + if (PyDict_Update(free, newfree) < 0) + goto error; + success = 1; + error: + Py_XDECREF(local); + Py_XDECREF(scope); + Py_XDECREF(newbound); + Py_XDECREF(newglobal); + Py_XDECREF(newfree); + Py_XDECREF(allfree); + if (!success) + assert(PyErr_Occurred()); + return success; +} + +static int +analyze_child_block(PySTEntryObject *entry, PyObject *bound, PyObject *free, + PyObject *global, PyObject* child_free) +{ + PyObject *temp_bound = NULL, *temp_global = NULL, *temp_free = NULL; + + /* Copy the bound and global dictionaries. + + These dictionary are used by all blocks enclosed by the + current block. The analyze_block() call modifies these + dictionaries. + + */ + temp_bound = PyDict_New(); + if (!temp_bound) + goto error; + if (PyDict_Update(temp_bound, bound) < 0) + goto error; + temp_free = PyDict_New(); + if (!temp_free) + goto error; + if (PyDict_Update(temp_free, free) < 0) + goto error; + temp_global = PyDict_New(); + if (!temp_global) + goto error; + if (PyDict_Update(temp_global, global) < 0) + goto error; + + if (!analyze_block(entry, temp_bound, temp_free, temp_global)) + goto error; + if (PyDict_Update(child_free, temp_free) < 0) + goto error; + Py_DECREF(temp_bound); + Py_DECREF(temp_free); + Py_DECREF(temp_global); + return 1; + error: + Py_XDECREF(temp_bound); + Py_XDECREF(temp_free); + Py_XDECREF(temp_global); + return 0; +} + +static int +symtable_analyze(struct symtable *st) +{ + PyObject *free, *global; + int r; + + free = PyDict_New(); + if (!free) + return 0; + global = PyDict_New(); + if (!global) { + Py_DECREF(free); + return 0; + } + r = analyze_block(st->st_top, NULL, free, global); + Py_DECREF(free); + Py_DECREF(global); + return r; +} + + +static int +symtable_warn(struct symtable *st, char *msg, int lineno) +{ + if (PyErr_WarnExplicit(PyExc_SyntaxWarning, msg, st->st_filename, + lineno, NULL, NULL) < 0) { + if (PyErr_ExceptionMatches(PyExc_SyntaxWarning)) { + PyErr_SetString(PyExc_SyntaxError, msg); + PyErr_SyntaxLocation(st->st_filename, + st->st_cur->ste_lineno); + } + return 0; + } + return 1; +} + +/* symtable_enter_block() gets a reference via ste_new. + This reference is released when the block is exited, via the DECREF + in symtable_exit_block(). +*/ + +static int +symtable_exit_block(struct symtable *st, void *ast) +{ + Py_ssize_t end; + + Py_CLEAR(st->st_cur); + end = PyList_GET_SIZE(st->st_stack) - 1; + if (end >= 0) { + st->st_cur = (PySTEntryObject *)PyList_GET_ITEM(st->st_stack, + end); + if (st->st_cur == NULL) + return 0; + Py_INCREF(st->st_cur); + if (PySequence_DelItem(st->st_stack, end) < 0) + return 0; + } + return 1; +} + +static int +symtable_enter_block(struct symtable *st, identifier name, _Py_block_ty block, + void *ast, int lineno) +{ + PySTEntryObject *prev = NULL; + + if (st->st_cur) { + prev = st->st_cur; + if (PyList_Append(st->st_stack, (PyObject *)st->st_cur) < 0) { + return 0; + } + Py_DECREF(st->st_cur); + } + st->st_cur = ste_new(st, name, block, ast, lineno); + if (st->st_cur == NULL) + return 0; + if (block == ModuleBlock) + st->st_global = st->st_cur->ste_symbols; + if (prev) { + if (PyList_Append(prev->ste_children, + (PyObject *)st->st_cur) < 0) { + return 0; + } + } + return 1; +} + +static long +symtable_lookup(struct symtable *st, PyObject *name) +{ + PyObject *o; + PyObject *mangled = _Py_Mangle(st->st_private, name); + if (!mangled) + return 0; + o = PyDict_GetItem(st->st_cur->ste_symbols, mangled); + Py_DECREF(mangled); + if (!o) + return 0; + return PyInt_AsLong(o); +} + +static int +symtable_add_def(struct symtable *st, PyObject *name, int flag) +{ + PyObject *o; + PyObject *dict; + long val; + PyObject *mangled = _Py_Mangle(st->st_private, name); + + if (!mangled) + return 0; + dict = st->st_cur->ste_symbols; + if ((o = PyDict_GetItem(dict, mangled))) { + val = PyInt_AS_LONG(o); + if ((flag & DEF_PARAM) && (val & DEF_PARAM)) { + /* Is it better to use 'mangled' or 'name' here? */ + PyErr_Format(PyExc_SyntaxError, DUPLICATE_ARGUMENT, + PyString_AsString(name)); + PyErr_SyntaxLocation(st->st_filename, + st->st_cur->ste_lineno); + goto error; + } + val |= flag; + } else + val = flag; + o = PyInt_FromLong(val); + if (o == NULL) + goto error; + if (PyDict_SetItem(dict, mangled, o) < 0) { + Py_DECREF(o); + goto error; + } + Py_DECREF(o); + + if (flag & DEF_PARAM) { + if (PyList_Append(st->st_cur->ste_varnames, mangled) < 0) + goto error; + } else if (flag & DEF_GLOBAL) { + /* XXX need to update DEF_GLOBAL for other flags too; + perhaps only DEF_FREE_GLOBAL */ + val = flag; + if ((o = PyDict_GetItem(st->st_global, mangled))) { + val |= PyInt_AS_LONG(o); + } + o = PyInt_FromLong(val); + if (o == NULL) + goto error; + if (PyDict_SetItem(st->st_global, mangled, o) < 0) { + Py_DECREF(o); + goto error; + } + Py_DECREF(o); + } + Py_DECREF(mangled); + return 1; + +error: + Py_DECREF(mangled); + return 0; +} + +/* VISIT, VISIT_SEQ and VIST_SEQ_TAIL take an ASDL type as their second argument. + They use the ASDL name to synthesize the name of the C type and the visit + function. + + VISIT_SEQ_TAIL permits the start of an ASDL sequence to be skipped, which is + useful if the first node in the sequence requires special treatment. +*/ + +#define VISIT(ST, TYPE, V) \ + if (!symtable_visit_ ## TYPE((ST), (V))) \ + return 0; + +#define VISIT_IN_BLOCK(ST, TYPE, V, S) \ + if (!symtable_visit_ ## TYPE((ST), (V))) { \ + symtable_exit_block((ST), (S)); \ + return 0; \ + } + +#define VISIT_SEQ(ST, TYPE, SEQ) { \ + int i; \ + asdl_seq *seq = (SEQ); /* avoid variable capture */ \ + for (i = 0; i < asdl_seq_LEN(seq); i++) { \ + TYPE ## _ty elt = (TYPE ## _ty)asdl_seq_GET(seq, i); \ + if (!symtable_visit_ ## TYPE((ST), elt)) \ + return 0; \ + } \ +} + +#define VISIT_SEQ_IN_BLOCK(ST, TYPE, SEQ, S) { \ + int i; \ + asdl_seq *seq = (SEQ); /* avoid variable capture */ \ + for (i = 0; i < asdl_seq_LEN(seq); i++) { \ + TYPE ## _ty elt = (TYPE ## _ty)asdl_seq_GET(seq, i); \ + if (!symtable_visit_ ## TYPE((ST), elt)) { \ + symtable_exit_block((ST), (S)); \ + return 0; \ + } \ + } \ +} + +#define VISIT_SEQ_TAIL(ST, TYPE, SEQ, START) { \ + int i; \ + asdl_seq *seq = (SEQ); /* avoid variable capture */ \ + for (i = (START); i < asdl_seq_LEN(seq); i++) { \ + TYPE ## _ty elt = (TYPE ## _ty)asdl_seq_GET(seq, i); \ + if (!symtable_visit_ ## TYPE((ST), elt)) \ + return 0; \ + } \ +} + +#define VISIT_SEQ_TAIL_IN_BLOCK(ST, TYPE, SEQ, START, S) { \ + int i; \ + asdl_seq *seq = (SEQ); /* avoid variable capture */ \ + for (i = (START); i < asdl_seq_LEN(seq); i++) { \ + TYPE ## _ty elt = (TYPE ## _ty)asdl_seq_GET(seq, i); \ + if (!symtable_visit_ ## TYPE((ST), elt)) { \ + symtable_exit_block((ST), (S)); \ + return 0; \ + } \ + } \ +} + +static int +symtable_visit_stmt(struct symtable *st, stmt_ty s) +{ + switch (s->kind) { + case FunctionDef_kind: + if (!symtable_add_def(st, s->v.FunctionDef.name, DEF_LOCAL)) + return 0; + if (s->v.FunctionDef.args->defaults) + VISIT_SEQ(st, expr, s->v.FunctionDef.args->defaults); + if (s->v.FunctionDef.decorator_list) + VISIT_SEQ(st, expr, s->v.FunctionDef.decorator_list); + if (!symtable_enter_block(st, s->v.FunctionDef.name, + FunctionBlock, (void *)s, s->lineno)) + return 0; + VISIT_IN_BLOCK(st, arguments, s->v.FunctionDef.args, s); + VISIT_SEQ_IN_BLOCK(st, stmt, s->v.FunctionDef.body, s); + if (!symtable_exit_block(st, s)) + return 0; + break; + case ClassDef_kind: { + PyObject *tmp; + if (!symtable_add_def(st, s->v.ClassDef.name, DEF_LOCAL)) + return 0; + VISIT_SEQ(st, expr, s->v.ClassDef.bases); + if (s->v.ClassDef.decorator_list) + VISIT_SEQ(st, expr, s->v.ClassDef.decorator_list); + if (!symtable_enter_block(st, s->v.ClassDef.name, ClassBlock, + (void *)s, s->lineno)) + return 0; + tmp = st->st_private; + st->st_private = s->v.ClassDef.name; + VISIT_SEQ_IN_BLOCK(st, stmt, s->v.ClassDef.body, s); + st->st_private = tmp; + if (!symtable_exit_block(st, s)) + return 0; + break; + } + case Return_kind: + if (s->v.Return.value) { + VISIT(st, expr, s->v.Return.value); + st->st_cur->ste_returns_value = 1; + if (st->st_cur->ste_generator) { + PyErr_SetString(PyExc_SyntaxError, + RETURN_VAL_IN_GENERATOR); + PyErr_SyntaxLocation(st->st_filename, + s->lineno); + return 0; + } + } + break; + case Delete_kind: + VISIT_SEQ(st, expr, s->v.Delete.targets); + break; + case Assign_kind: + VISIT_SEQ(st, expr, s->v.Assign.targets); + VISIT(st, expr, s->v.Assign.value); + break; + case AugAssign_kind: + VISIT(st, expr, s->v.AugAssign.target); + VISIT(st, expr, s->v.AugAssign.value); + break; + case Print_kind: + if (s->v.Print.dest) + VISIT(st, expr, s->v.Print.dest); + VISIT_SEQ(st, expr, s->v.Print.values); + break; + case For_kind: + VISIT(st, expr, s->v.For.target); + VISIT(st, expr, s->v.For.iter); + VISIT_SEQ(st, stmt, s->v.For.body); + if (s->v.For.orelse) + VISIT_SEQ(st, stmt, s->v.For.orelse); + break; + case While_kind: + VISIT(st, expr, s->v.While.test); + VISIT_SEQ(st, stmt, s->v.While.body); + if (s->v.While.orelse) + VISIT_SEQ(st, stmt, s->v.While.orelse); + break; + case If_kind: + /* XXX if 0: and lookup_yield() hacks */ + VISIT(st, expr, s->v.If.test); + VISIT_SEQ(st, stmt, s->v.If.body); + if (s->v.If.orelse) + VISIT_SEQ(st, stmt, s->v.If.orelse); + break; + case Raise_kind: + if (s->v.Raise.type) { + VISIT(st, expr, s->v.Raise.type); + if (s->v.Raise.inst) { + VISIT(st, expr, s->v.Raise.inst); + if (s->v.Raise.tback) + VISIT(st, expr, s->v.Raise.tback); + } + } + break; + case TryExcept_kind: + VISIT_SEQ(st, stmt, s->v.TryExcept.body); + VISIT_SEQ(st, stmt, s->v.TryExcept.orelse); + VISIT_SEQ(st, excepthandler, s->v.TryExcept.handlers); + break; + case TryFinally_kind: + VISIT_SEQ(st, stmt, s->v.TryFinally.body); + VISIT_SEQ(st, stmt, s->v.TryFinally.finalbody); + break; + case Assert_kind: + VISIT(st, expr, s->v.Assert.test); + if (s->v.Assert.msg) + VISIT(st, expr, s->v.Assert.msg); + break; + case Import_kind: + VISIT_SEQ(st, alias, s->v.Import.names); + /* XXX Don't have the lineno available inside + visit_alias */ + if (st->st_cur->ste_unoptimized && !st->st_cur->ste_opt_lineno) + st->st_cur->ste_opt_lineno = s->lineno; + break; + case ImportFrom_kind: + VISIT_SEQ(st, alias, s->v.ImportFrom.names); + /* XXX Don't have the lineno available inside + visit_alias */ + if (st->st_cur->ste_unoptimized && !st->st_cur->ste_opt_lineno) + st->st_cur->ste_opt_lineno = s->lineno; + break; + case Exec_kind: + VISIT(st, expr, s->v.Exec.body); + if (!st->st_cur->ste_opt_lineno) + st->st_cur->ste_opt_lineno = s->lineno; + if (s->v.Exec.globals) { + st->st_cur->ste_unoptimized |= OPT_EXEC; + VISIT(st, expr, s->v.Exec.globals); + if (s->v.Exec.locals) + VISIT(st, expr, s->v.Exec.locals); + } else { + st->st_cur->ste_unoptimized |= OPT_BARE_EXEC; + } + break; + case Global_kind: { + int i; + asdl_seq *seq = s->v.Global.names; + for (i = 0; i < asdl_seq_LEN(seq); i++) { + identifier name = (identifier)asdl_seq_GET(seq, i); + char *c_name = PyString_AS_STRING(name); + long cur = symtable_lookup(st, name); + if (cur < 0) + return 0; + if (cur & (DEF_LOCAL | USE)) { + char buf[256]; + if (cur & DEF_LOCAL) + PyOS_snprintf(buf, sizeof(buf), + GLOBAL_AFTER_ASSIGN, + c_name); + else + PyOS_snprintf(buf, sizeof(buf), + GLOBAL_AFTER_USE, + c_name); + if (!symtable_warn(st, buf, s->lineno)) + return 0; + } + if (!symtable_add_def(st, name, DEF_GLOBAL)) + return 0; + } + break; + } + case Expr_kind: + VISIT(st, expr, s->v.Expr.value); + break; + case Pass_kind: + case Break_kind: + case Continue_kind: + /* nothing to do here */ + break; + case With_kind: + VISIT(st, expr, s->v.With.context_expr); + if (s->v.With.optional_vars) { + VISIT(st, expr, s->v.With.optional_vars); + } + VISIT_SEQ(st, stmt, s->v.With.body); + break; + } + return 1; +} + +static int +symtable_visit_expr(struct symtable *st, expr_ty e) +{ + switch (e->kind) { + case BoolOp_kind: + VISIT_SEQ(st, expr, e->v.BoolOp.values); + break; + case BinOp_kind: + VISIT(st, expr, e->v.BinOp.left); + VISIT(st, expr, e->v.BinOp.right); + break; + case UnaryOp_kind: + VISIT(st, expr, e->v.UnaryOp.operand); + break; + case Lambda_kind: { + if (!GET_IDENTIFIER(lambda)) + return 0; + if (e->v.Lambda.args->defaults) + VISIT_SEQ(st, expr, e->v.Lambda.args->defaults); + if (!symtable_enter_block(st, lambda, + FunctionBlock, (void *)e, e->lineno)) + return 0; + VISIT_IN_BLOCK(st, arguments, e->v.Lambda.args, (void*)e); + VISIT_IN_BLOCK(st, expr, e->v.Lambda.body, (void*)e); + if (!symtable_exit_block(st, (void *)e)) + return 0; + break; + } + case IfExp_kind: + VISIT(st, expr, e->v.IfExp.test); + VISIT(st, expr, e->v.IfExp.body); + VISIT(st, expr, e->v.IfExp.orelse); + break; + case Dict_kind: + VISIT_SEQ(st, expr, e->v.Dict.keys); + VISIT_SEQ(st, expr, e->v.Dict.values); + break; + case Set_kind: + VISIT_SEQ(st, expr, e->v.Set.elts); + break; + case ListComp_kind: + VISIT(st, expr, e->v.ListComp.elt); + VISIT_SEQ(st, comprehension, e->v.ListComp.generators); + break; + case GeneratorExp_kind: + if (!symtable_visit_genexp(st, e)) + return 0; + break; + case SetComp_kind: + if (!symtable_visit_setcomp(st, e)) + return 0; + break; + case DictComp_kind: + if (!symtable_visit_dictcomp(st, e)) + return 0; + break; + case Yield_kind: + if (e->v.Yield.value) + VISIT(st, expr, e->v.Yield.value); + st->st_cur->ste_generator = 1; + if (st->st_cur->ste_returns_value) { + PyErr_SetString(PyExc_SyntaxError, + RETURN_VAL_IN_GENERATOR); + PyErr_SyntaxLocation(st->st_filename, + e->lineno); + return 0; + } + break; + case Compare_kind: + VISIT(st, expr, e->v.Compare.left); + VISIT_SEQ(st, expr, e->v.Compare.comparators); + break; + case Call_kind: + VISIT(st, expr, e->v.Call.func); + VISIT_SEQ(st, expr, e->v.Call.args); + VISIT_SEQ(st, keyword, e->v.Call.keywords); + if (e->v.Call.starargs) + VISIT(st, expr, e->v.Call.starargs); + if (e->v.Call.kwargs) + VISIT(st, expr, e->v.Call.kwargs); + break; + case Repr_kind: + VISIT(st, expr, e->v.Repr.value); + break; + case Num_kind: + case Str_kind: + /* Nothing to do here. */ + break; + /* The following exprs can be assignment targets. */ + case Attribute_kind: + VISIT(st, expr, e->v.Attribute.value); + break; + case Subscript_kind: + VISIT(st, expr, e->v.Subscript.value); + VISIT(st, slice, e->v.Subscript.slice); + break; + case Name_kind: + if (!symtable_add_def(st, e->v.Name.id, + e->v.Name.ctx == Load ? USE : DEF_LOCAL)) + return 0; + break; + /* child nodes of List and Tuple will have expr_context set */ + case List_kind: + VISIT_SEQ(st, expr, e->v.List.elts); + break; + case Tuple_kind: + VISIT_SEQ(st, expr, e->v.Tuple.elts); + break; + } + return 1; +} + +static int +symtable_implicit_arg(struct symtable *st, int pos) +{ + PyObject *id = PyString_FromFormat(".%d", pos); + if (id == NULL) + return 0; + if (!symtable_add_def(st, id, DEF_PARAM)) { + Py_DECREF(id); + return 0; + } + Py_DECREF(id); + return 1; +} + +static int +symtable_visit_params(struct symtable *st, asdl_seq *args, int toplevel) +{ + int i; + + /* go through all the toplevel arguments first */ + for (i = 0; i < asdl_seq_LEN(args); i++) { + expr_ty arg = (expr_ty)asdl_seq_GET(args, i); + if (arg->kind == Name_kind) { + assert(arg->v.Name.ctx == Param || + (arg->v.Name.ctx == Store && !toplevel)); + if (!symtable_add_def(st, arg->v.Name.id, DEF_PARAM)) + return 0; + } + else if (arg->kind == Tuple_kind) { + assert(arg->v.Tuple.ctx == Store); + if (toplevel) { + if (!symtable_implicit_arg(st, i)) + return 0; + } + } + else { + PyErr_SetString(PyExc_SyntaxError, + "invalid expression in parameter list"); + PyErr_SyntaxLocation(st->st_filename, + st->st_cur->ste_lineno); + return 0; + } + } + + if (!toplevel) { + if (!symtable_visit_params_nested(st, args)) + return 0; + } + + return 1; +} + +static int +symtable_visit_params_nested(struct symtable *st, asdl_seq *args) +{ + int i; + for (i = 0; i < asdl_seq_LEN(args); i++) { + expr_ty arg = (expr_ty)asdl_seq_GET(args, i); + if (arg->kind == Tuple_kind && + !symtable_visit_params(st, arg->v.Tuple.elts, 0)) + return 0; + } + + return 1; +} + +static int +symtable_visit_arguments(struct symtable *st, arguments_ty a) +{ + /* skip default arguments inside function block + XXX should ast be different? + */ + if (a->args && !symtable_visit_params(st, a->args, 1)) + return 0; + if (a->vararg) { + if (!symtable_add_def(st, a->vararg, DEF_PARAM)) + return 0; + st->st_cur->ste_varargs = 1; + } + if (a->kwarg) { + if (!symtable_add_def(st, a->kwarg, DEF_PARAM)) + return 0; + st->st_cur->ste_varkeywords = 1; + } + if (a->args && !symtable_visit_params_nested(st, a->args)) + return 0; + return 1; +} + + +static int +symtable_visit_excepthandler(struct symtable *st, excepthandler_ty eh) +{ + if (eh->v.ExceptHandler.type) + VISIT(st, expr, eh->v.ExceptHandler.type); + if (eh->v.ExceptHandler.name) + VISIT(st, expr, eh->v.ExceptHandler.name); + VISIT_SEQ(st, stmt, eh->v.ExceptHandler.body); + return 1; +} + + +static int +symtable_visit_alias(struct symtable *st, alias_ty a) +{ + /* Compute store_name, the name actually bound by the import + operation. It is different than a->name when a->name is a + dotted package name (e.g. spam.eggs) + */ + PyObject *store_name; + PyObject *name = (a->asname == NULL) ? a->name : a->asname; + const char *base = PyString_AS_STRING(name); + char *dot = strchr(base, '.'); + if (dot) { + store_name = PyString_FromStringAndSize(base, dot - base); + if (!store_name) + return 0; + } + else { + store_name = name; + Py_INCREF(store_name); + } + if (strcmp(PyString_AS_STRING(name), "*")) { + int r = symtable_add_def(st, store_name, DEF_IMPORT); + Py_DECREF(store_name); + return r; + } + else { + if (st->st_cur->ste_type != ModuleBlock) { + int lineno = st->st_cur->ste_lineno; + if (!symtable_warn(st, IMPORT_STAR_WARNING, lineno)) { + Py_DECREF(store_name); + return 0; + } + } + st->st_cur->ste_unoptimized |= OPT_IMPORT_STAR; + Py_DECREF(store_name); + return 1; + } +} + + +static int +symtable_visit_comprehension(struct symtable *st, comprehension_ty lc) +{ + VISIT(st, expr, lc->target); + VISIT(st, expr, lc->iter); + VISIT_SEQ(st, expr, lc->ifs); + return 1; +} + + +static int +symtable_visit_keyword(struct symtable *st, keyword_ty k) +{ + VISIT(st, expr, k->value); + return 1; +} + + +static int +symtable_visit_slice(struct symtable *st, slice_ty s) +{ + switch (s->kind) { + case Slice_kind: + if (s->v.Slice.lower) + VISIT(st, expr, s->v.Slice.lower) + if (s->v.Slice.upper) + VISIT(st, expr, s->v.Slice.upper) + if (s->v.Slice.step) + VISIT(st, expr, s->v.Slice.step) + break; + case ExtSlice_kind: + VISIT_SEQ(st, slice, s->v.ExtSlice.dims) + break; + case Index_kind: + VISIT(st, expr, s->v.Index.value) + break; + case Ellipsis_kind: + break; + } + return 1; +} + +static int +symtable_new_tmpname(struct symtable *st) +{ + char tmpname[256]; + identifier tmp; + + PyOS_snprintf(tmpname, sizeof(tmpname), "_[%d]", + ++st->st_cur->ste_tmpname); + tmp = PyString_InternFromString(tmpname); + if (!tmp) + return 0; + if (!symtable_add_def(st, tmp, DEF_LOCAL)) + return 0; + Py_DECREF(tmp); + return 1; +} + +static int +symtable_handle_comprehension(struct symtable *st, expr_ty e, + identifier scope_name, asdl_seq *generators, + expr_ty elt, expr_ty value) +{ + int is_generator = (e->kind == GeneratorExp_kind); + int needs_tmp = !is_generator; + comprehension_ty outermost = ((comprehension_ty) + asdl_seq_GET(generators, 0)); + /* Outermost iterator is evaluated in current scope */ + VISIT(st, expr, outermost->iter); + /* Create comprehension scope for the rest */ + if (!scope_name || + !symtable_enter_block(st, scope_name, FunctionBlock, (void *)e, 0)) { + return 0; + } + st->st_cur->ste_generator = is_generator; + /* Outermost iter is received as an argument */ + if (!symtable_implicit_arg(st, 0)) { + symtable_exit_block(st, (void *)e); + return 0; + } + /* Allocate temporary name if needed */ + if (needs_tmp && !symtable_new_tmpname(st)) { + symtable_exit_block(st, (void *)e); + return 0; + } + VISIT_IN_BLOCK(st, expr, outermost->target, (void*)e); + VISIT_SEQ_IN_BLOCK(st, expr, outermost->ifs, (void*)e); + VISIT_SEQ_TAIL_IN_BLOCK(st, comprehension, + generators, 1, (void*)e); + if (value) + VISIT_IN_BLOCK(st, expr, value, (void*)e); + VISIT_IN_BLOCK(st, expr, elt, (void*)e); + return symtable_exit_block(st, (void *)e); +} + +static int +symtable_visit_genexp(struct symtable *st, expr_ty e) +{ + return symtable_handle_comprehension(st, e, GET_IDENTIFIER(genexpr), + e->v.GeneratorExp.generators, + e->v.GeneratorExp.elt, NULL); +} + +static int +symtable_visit_setcomp(struct symtable *st, expr_ty e) +{ + return symtable_handle_comprehension(st, e, GET_IDENTIFIER(setcomp), + e->v.SetComp.generators, + e->v.SetComp.elt, NULL); +} + +static int +symtable_visit_dictcomp(struct symtable *st, expr_ty e) +{ + return symtable_handle_comprehension(st, e, GET_IDENTIFIER(dictcomp), + e->v.DictComp.generators, + e->v.DictComp.key, + e->v.DictComp.value); +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/sysmodule.c b/AppPkg/Applications/Python/Python-2.7.10/Python/sysmodule.c new file mode 100644 index 0000000000..36e81b4889 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/sysmodule.c @@ -0,0 +1,1800 @@ + +/* System module */ + +/* +Various bits of information used by the interpreter are collected in +module 'sys'. +Function member: +- exit(sts): raise SystemExit +Data members: +- stdin, stdout, stderr: standard file objects +- modules: the table of modules (dictionary) +- path: module search path (list of strings) +- argv: script arguments (list of strings) +- ps1, ps2: optional primary and secondary prompts (strings) +*/ + +#include "Python.h" +#include "structseq.h" +#include "code.h" +#include "frameobject.h" +#include "eval.h" + +#include "osdefs.h" + +#ifdef MS_WINDOWS +#define WIN32_LEAN_AND_MEAN +#include "windows.h" +#endif /* MS_WINDOWS */ + +#ifdef MS_COREDLL +extern void *PyWin_DLLhModule; +/* A string loaded from the DLL at startup: */ +extern const char *PyWin_DLLVersionString; +#endif + +#ifdef __VMS +#include +#endif + +#ifdef MS_WINDOWS +#include +#endif + +#ifdef HAVE_LANGINFO_H +#include +#include +#endif + +PyObject * +PySys_GetObject(char *name) +{ + PyThreadState *tstate = PyThreadState_GET(); + PyObject *sd = tstate->interp->sysdict; + if (sd == NULL) + return NULL; + return PyDict_GetItemString(sd, name); +} + +FILE * +PySys_GetFile(char *name, FILE *def) +{ + FILE *fp = NULL; + PyObject *v = PySys_GetObject(name); + if (v != NULL && PyFile_Check(v)) + fp = PyFile_AsFile(v); + if (fp == NULL) + fp = def; + return fp; +} + +int +PySys_SetObject(char *name, PyObject *v) +{ + PyThreadState *tstate = PyThreadState_GET(); + PyObject *sd = tstate->interp->sysdict; + if (v == NULL) { + if (PyDict_GetItemString(sd, name) == NULL) + return 0; + else + return PyDict_DelItemString(sd, name); + } + else + return PyDict_SetItemString(sd, name, v); +} + +static PyObject * +sys_displayhook(PyObject *self, PyObject *o) +{ + PyObject *outf; + PyInterpreterState *interp = PyThreadState_GET()->interp; + PyObject *modules = interp->modules; + PyObject *builtins = PyDict_GetItemString(modules, "__builtin__"); + + if (builtins == NULL) { + PyErr_SetString(PyExc_RuntimeError, "lost __builtin__"); + return NULL; + } + + /* Print value except if None */ + /* After printing, also assign to '_' */ + /* Before, set '_' to None to avoid recursion */ + if (o == Py_None) { + Py_INCREF(Py_None); + return Py_None; + } + if (PyObject_SetAttrString(builtins, "_", Py_None) != 0) + return NULL; + if (Py_FlushLine() != 0) + return NULL; + outf = PySys_GetObject("stdout"); + if (outf == NULL) { + PyErr_SetString(PyExc_RuntimeError, "lost sys.stdout"); + return NULL; + } + if (PyFile_WriteObject(o, outf, 0) != 0) + return NULL; + PyFile_SoftSpace(outf, 1); + if (Py_FlushLine() != 0) + return NULL; + if (PyObject_SetAttrString(builtins, "_", o) != 0) + return NULL; + Py_INCREF(Py_None); + return Py_None; +} + +PyDoc_STRVAR(displayhook_doc, +"displayhook(object) -> None\n" +"\n" +"Print an object to sys.stdout and also save it in __builtin__._\n" +); + +static PyObject * +sys_excepthook(PyObject* self, PyObject* args) +{ + PyObject *exc, *value, *tb; + if (!PyArg_UnpackTuple(args, "excepthook", 3, 3, &exc, &value, &tb)) + return NULL; + PyErr_Display(exc, value, tb); + Py_INCREF(Py_None); + return Py_None; +} + +PyDoc_STRVAR(excepthook_doc, +"excepthook(exctype, value, traceback) -> None\n" +"\n" +"Handle an exception by displaying it with a traceback on sys.stderr.\n" +); + +static PyObject * +sys_exc_info(PyObject *self, PyObject *noargs) +{ + PyThreadState *tstate; + tstate = PyThreadState_GET(); + return Py_BuildValue( + "(OOO)", + tstate->exc_type != NULL ? tstate->exc_type : Py_None, + tstate->exc_value != NULL ? tstate->exc_value : Py_None, + tstate->exc_traceback != NULL ? + tstate->exc_traceback : Py_None); +} + +PyDoc_STRVAR(exc_info_doc, +"exc_info() -> (type, value, traceback)\n\ +\n\ +Return information about the most recent exception caught by an except\n\ +clause in the current stack frame or in an older stack frame." +); + +static PyObject * +sys_exc_clear(PyObject *self, PyObject *noargs) +{ + PyThreadState *tstate; + PyObject *tmp_type, *tmp_value, *tmp_tb; + + if (PyErr_WarnPy3k("sys.exc_clear() not supported in 3.x; " + "use except clauses", 1) < 0) + return NULL; + + tstate = PyThreadState_GET(); + tmp_type = tstate->exc_type; + tmp_value = tstate->exc_value; + tmp_tb = tstate->exc_traceback; + tstate->exc_type = NULL; + tstate->exc_value = NULL; + tstate->exc_traceback = NULL; + Py_XDECREF(tmp_type); + Py_XDECREF(tmp_value); + Py_XDECREF(tmp_tb); + /* For b/w compatibility */ + PySys_SetObject("exc_type", Py_None); + PySys_SetObject("exc_value", Py_None); + PySys_SetObject("exc_traceback", Py_None); + Py_INCREF(Py_None); + return Py_None; +} + +PyDoc_STRVAR(exc_clear_doc, +"exc_clear() -> None\n\ +\n\ +Clear global information on the current exception. Subsequent calls to\n\ +exc_info() will return (None,None,None) until another exception is raised\n\ +in the current thread or the execution stack returns to a frame where\n\ +another exception is being handled." +); + +static PyObject * +sys_exit(PyObject *self, PyObject *args) +{ + PyObject *exit_code = 0; + if (!PyArg_UnpackTuple(args, "exit", 0, 1, &exit_code)) + return NULL; + /* Raise SystemExit so callers may catch it or clean up. */ + PyErr_SetObject(PyExc_SystemExit, exit_code); + return NULL; +} + +PyDoc_STRVAR(exit_doc, +"exit([status])\n\ +\n\ +Exit the interpreter by raising SystemExit(status).\n\ +If the status is omitted or None, it defaults to zero (i.e., success).\n\ +If the status is an integer, it will be used as the system exit status.\n\ +If it is another kind of object, it will be printed and the system\n\ +exit status will be one (i.e., failure)." +); + +#ifdef Py_USING_UNICODE + +static PyObject * +sys_getdefaultencoding(PyObject *self) +{ + return PyString_FromString(PyUnicode_GetDefaultEncoding()); +} + +PyDoc_STRVAR(getdefaultencoding_doc, +"getdefaultencoding() -> string\n\ +\n\ +Return the current default string encoding used by the Unicode \n\ +implementation." +); + +static PyObject * +sys_setdefaultencoding(PyObject *self, PyObject *args) +{ + char *encoding; + if (!PyArg_ParseTuple(args, "s:setdefaultencoding", &encoding)) + return NULL; + if (PyUnicode_SetDefaultEncoding(encoding)) + return NULL; + Py_INCREF(Py_None); + return Py_None; +} + +PyDoc_STRVAR(setdefaultencoding_doc, +"setdefaultencoding(encoding)\n\ +\n\ +Set the current default string encoding used by the Unicode implementation." +); + +static PyObject * +sys_getfilesystemencoding(PyObject *self) +{ + if (Py_FileSystemDefaultEncoding) + return PyString_FromString(Py_FileSystemDefaultEncoding); + Py_INCREF(Py_None); + return Py_None; +} + +PyDoc_STRVAR(getfilesystemencoding_doc, +"getfilesystemencoding() -> string\n\ +\n\ +Return the encoding used to convert Unicode filenames in\n\ +operating system filenames." +); + +#endif + +/* + * Cached interned string objects used for calling the profile and + * trace functions. Initialized by trace_init(). + */ +static PyObject *whatstrings[7] = {NULL, NULL, NULL, NULL, NULL, NULL, NULL}; + +static int +trace_init(void) +{ + static char *whatnames[7] = {"call", "exception", "line", "return", + "c_call", "c_exception", "c_return"}; + PyObject *name; + int i; + for (i = 0; i < 7; ++i) { + if (whatstrings[i] == NULL) { + name = PyString_InternFromString(whatnames[i]); + if (name == NULL) + return -1; + whatstrings[i] = name; + } + } + return 0; +} + + +static PyObject * +call_trampoline(PyThreadState *tstate, PyObject* callback, + PyFrameObject *frame, int what, PyObject *arg) +{ + PyObject *args = PyTuple_New(3); + PyObject *whatstr; + PyObject *result; + + if (args == NULL) + return NULL; + Py_INCREF(frame); + whatstr = whatstrings[what]; + Py_INCREF(whatstr); + if (arg == NULL) + arg = Py_None; + Py_INCREF(arg); + PyTuple_SET_ITEM(args, 0, (PyObject *)frame); + PyTuple_SET_ITEM(args, 1, whatstr); + PyTuple_SET_ITEM(args, 2, arg); + + /* call the Python-level function */ + PyFrame_FastToLocals(frame); + result = PyEval_CallObject(callback, args); + PyFrame_LocalsToFast(frame, 1); + if (result == NULL) + PyTraceBack_Here(frame); + + /* cleanup */ + Py_DECREF(args); + return result; +} + +static int +profile_trampoline(PyObject *self, PyFrameObject *frame, + int what, PyObject *arg) +{ + PyThreadState *tstate = frame->f_tstate; + PyObject *result; + + if (arg == NULL) + arg = Py_None; + result = call_trampoline(tstate, self, frame, what, arg); + if (result == NULL) { + PyEval_SetProfile(NULL, NULL); + return -1; + } + Py_DECREF(result); + return 0; +} + +static int +trace_trampoline(PyObject *self, PyFrameObject *frame, + int what, PyObject *arg) +{ + PyThreadState *tstate = frame->f_tstate; + PyObject *callback; + PyObject *result; + + if (what == PyTrace_CALL) + callback = self; + else + callback = frame->f_trace; + if (callback == NULL) + return 0; + result = call_trampoline(tstate, callback, frame, what, arg); + if (result == NULL) { + PyEval_SetTrace(NULL, NULL); + Py_CLEAR(frame->f_trace); + return -1; + } + if (result != Py_None) { + PyObject *temp = frame->f_trace; + frame->f_trace = NULL; + Py_XDECREF(temp); + frame->f_trace = result; + } + else { + Py_DECREF(result); + } + return 0; +} + +static PyObject * +sys_settrace(PyObject *self, PyObject *args) +{ + if (trace_init() == -1) + return NULL; + if (args == Py_None) + PyEval_SetTrace(NULL, NULL); + else + PyEval_SetTrace(trace_trampoline, args); + Py_INCREF(Py_None); + return Py_None; +} + +PyDoc_STRVAR(settrace_doc, +"settrace(function)\n\ +\n\ +Set the global debug tracing function. It will be called on each\n\ +function call. See the debugger chapter in the library manual." +); + +static PyObject * +sys_gettrace(PyObject *self, PyObject *args) +{ + PyThreadState *tstate = PyThreadState_GET(); + PyObject *temp = tstate->c_traceobj; + + if (temp == NULL) + temp = Py_None; + Py_INCREF(temp); + return temp; +} + +PyDoc_STRVAR(gettrace_doc, +"gettrace()\n\ +\n\ +Return the global debug tracing function set with sys.settrace.\n\ +See the debugger chapter in the library manual." +); + +static PyObject * +sys_setprofile(PyObject *self, PyObject *args) +{ + if (trace_init() == -1) + return NULL; + if (args == Py_None) + PyEval_SetProfile(NULL, NULL); + else + PyEval_SetProfile(profile_trampoline, args); + Py_INCREF(Py_None); + return Py_None; +} + +PyDoc_STRVAR(setprofile_doc, +"setprofile(function)\n\ +\n\ +Set the profiling function. It will be called on each function call\n\ +and return. See the profiler chapter in the library manual." +); + +static PyObject * +sys_getprofile(PyObject *self, PyObject *args) +{ + PyThreadState *tstate = PyThreadState_GET(); + PyObject *temp = tstate->c_profileobj; + + if (temp == NULL) + temp = Py_None; + Py_INCREF(temp); + return temp; +} + +PyDoc_STRVAR(getprofile_doc, +"getprofile()\n\ +\n\ +Return the profiling function set with sys.setprofile.\n\ +See the profiler chapter in the library manual." +); + +static PyObject * +sys_setcheckinterval(PyObject *self, PyObject *args) +{ + if (!PyArg_ParseTuple(args, "i:setcheckinterval", &_Py_CheckInterval)) + return NULL; + _Py_Ticker = _Py_CheckInterval; + Py_INCREF(Py_None); + return Py_None; +} + +PyDoc_STRVAR(setcheckinterval_doc, +"setcheckinterval(n)\n\ +\n\ +Tell the Python interpreter to check for asynchronous events every\n\ +n instructions. This also affects how often thread switches occur." +); + +static PyObject * +sys_getcheckinterval(PyObject *self, PyObject *args) +{ + return PyInt_FromLong(_Py_CheckInterval); +} + +PyDoc_STRVAR(getcheckinterval_doc, +"getcheckinterval() -> current check interval; see setcheckinterval()." +); + +#ifdef WITH_TSC +static PyObject * +sys_settscdump(PyObject *self, PyObject *args) +{ + int bool; + PyThreadState *tstate = PyThreadState_Get(); + + if (!PyArg_ParseTuple(args, "i:settscdump", &bool)) + return NULL; + if (bool) + tstate->interp->tscdump = 1; + else + tstate->interp->tscdump = 0; + Py_INCREF(Py_None); + return Py_None; + +} + +PyDoc_STRVAR(settscdump_doc, +"settscdump(bool)\n\ +\n\ +If true, tell the Python interpreter to dump VM measurements to\n\ +stderr. If false, turn off dump. The measurements are based on the\n\ +processor's time-stamp counter." +); +#endif /* TSC */ + +static PyObject * +sys_setrecursionlimit(PyObject *self, PyObject *args) +{ + int new_limit; + if (!PyArg_ParseTuple(args, "i:setrecursionlimit", &new_limit)) + return NULL; + if (new_limit <= 0) { + PyErr_SetString(PyExc_ValueError, + "recursion limit must be positive"); + return NULL; + } + Py_SetRecursionLimit(new_limit); + Py_INCREF(Py_None); + return Py_None; +} + +PyDoc_STRVAR(setrecursionlimit_doc, +"setrecursionlimit(n)\n\ +\n\ +Set the maximum depth of the Python interpreter stack to n. This\n\ +limit prevents infinite recursion from causing an overflow of the C\n\ +stack and crashing Python. The highest possible limit is platform-\n\ +dependent." +); + +static PyObject * +sys_getrecursionlimit(PyObject *self) +{ + return PyInt_FromLong(Py_GetRecursionLimit()); +} + +PyDoc_STRVAR(getrecursionlimit_doc, +"getrecursionlimit()\n\ +\n\ +Return the current value of the recursion limit, the maximum depth\n\ +of the Python interpreter stack. This limit prevents infinite\n\ +recursion from causing an overflow of the C stack and crashing Python." +); + +#ifdef MS_WINDOWS +PyDoc_STRVAR(getwindowsversion_doc, +"getwindowsversion()\n\ +\n\ +Return information about the running version of Windows as a named tuple.\n\ +The members are named: major, minor, build, platform, service_pack,\n\ +service_pack_major, service_pack_minor, suite_mask, and product_type. For\n\ +backward compatibility, only the first 5 items are available by indexing.\n\ +All elements are numbers, except service_pack which is a string. Platform\n\ +may be 0 for win32s, 1 for Windows 9x/ME, 2 for Windows NT/2000/XP/Vista/7,\n\ +3 for Windows CE. Product_type may be 1 for a workstation, 2 for a domain\n\ +controller, 3 for a server." +); + +static PyTypeObject WindowsVersionType = {0, 0, 0, 0, 0, 0}; + +static PyStructSequence_Field windows_version_fields[] = { + {"major", "Major version number"}, + {"minor", "Minor version number"}, + {"build", "Build number"}, + {"platform", "Operating system platform"}, + {"service_pack", "Latest Service Pack installed on the system"}, + {"service_pack_major", "Service Pack major version number"}, + {"service_pack_minor", "Service Pack minor version number"}, + {"suite_mask", "Bit mask identifying available product suites"}, + {"product_type", "System product type"}, + {0} +}; + +static PyStructSequence_Desc windows_version_desc = { + "sys.getwindowsversion", /* name */ + getwindowsversion_doc, /* doc */ + windows_version_fields, /* fields */ + 5 /* For backward compatibility, + only the first 5 items are accessible + via indexing, the rest are name only */ +}; + +static PyObject * +sys_getwindowsversion(PyObject *self) +{ + PyObject *version; + int pos = 0; + OSVERSIONINFOEX ver; + ver.dwOSVersionInfoSize = sizeof(ver); + if (!GetVersionEx((OSVERSIONINFO*) &ver)) + return PyErr_SetFromWindowsErr(0); + + version = PyStructSequence_New(&WindowsVersionType); + if (version == NULL) + return NULL; + + PyStructSequence_SET_ITEM(version, pos++, PyInt_FromLong(ver.dwMajorVersion)); + PyStructSequence_SET_ITEM(version, pos++, PyInt_FromLong(ver.dwMinorVersion)); + PyStructSequence_SET_ITEM(version, pos++, PyInt_FromLong(ver.dwBuildNumber)); + PyStructSequence_SET_ITEM(version, pos++, PyInt_FromLong(ver.dwPlatformId)); + PyStructSequence_SET_ITEM(version, pos++, PyString_FromString(ver.szCSDVersion)); + PyStructSequence_SET_ITEM(version, pos++, PyInt_FromLong(ver.wServicePackMajor)); + PyStructSequence_SET_ITEM(version, pos++, PyInt_FromLong(ver.wServicePackMinor)); + PyStructSequence_SET_ITEM(version, pos++, PyInt_FromLong(ver.wSuiteMask)); + PyStructSequence_SET_ITEM(version, pos++, PyInt_FromLong(ver.wProductType)); + + if (PyErr_Occurred()) { + Py_DECREF(version); + return NULL; + } + return version; +} + +#endif /* MS_WINDOWS */ + +#ifdef HAVE_DLOPEN +static PyObject * +sys_setdlopenflags(PyObject *self, PyObject *args) +{ + int new_val; + PyThreadState *tstate = PyThreadState_GET(); + if (!PyArg_ParseTuple(args, "i:setdlopenflags", &new_val)) + return NULL; + if (!tstate) + return NULL; + tstate->interp->dlopenflags = new_val; + Py_INCREF(Py_None); + return Py_None; +} + +PyDoc_STRVAR(setdlopenflags_doc, +"setdlopenflags(n) -> None\n\ +\n\ +Set the flags used by the interpreter for dlopen calls, such as when the\n\ +interpreter loads extension modules. Among other things, this will enable\n\ +a lazy resolving of symbols when importing a module, if called as\n\ +sys.setdlopenflags(0). To share symbols across extension modules, call as\n\ +sys.setdlopenflags(ctypes.RTLD_GLOBAL). Symbolic names for the flag modules\n\ +can be either found in the ctypes module, or in the DLFCN module. If DLFCN\n\ +is not available, it can be generated from /usr/include/dlfcn.h using the\n\ +h2py script."); + +static PyObject * +sys_getdlopenflags(PyObject *self, PyObject *args) +{ + PyThreadState *tstate = PyThreadState_GET(); + if (!tstate) + return NULL; + return PyInt_FromLong(tstate->interp->dlopenflags); +} + +PyDoc_STRVAR(getdlopenflags_doc, +"getdlopenflags() -> int\n\ +\n\ +Return the current value of the flags that are used for dlopen calls.\n\ +The flag constants are defined in the ctypes and DLFCN modules."); + +#endif /* HAVE_DLOPEN */ + +#ifdef USE_MALLOPT +/* Link with -lmalloc (or -lmpc) on an SGI */ +#include + +static PyObject * +sys_mdebug(PyObject *self, PyObject *args) +{ + int flag; + if (!PyArg_ParseTuple(args, "i:mdebug", &flag)) + return NULL; + mallopt(M_DEBUG, flag); + Py_INCREF(Py_None); + return Py_None; +} +#endif /* USE_MALLOPT */ + +size_t +_PySys_GetSizeOf(PyObject *o) +{ + static PyObject *str__sizeof__ = NULL; + PyObject *res = NULL; + Py_ssize_t size; + + /* Make sure the type is initialized. float gets initialized late */ + if (PyType_Ready(Py_TYPE(o)) < 0) + return (size_t)-1; + + /* Instance of old-style class */ + if (PyInstance_Check(o)) + size = PyInstance_Type.tp_basicsize; + /* all other objects */ + else { + PyObject *method = _PyObject_LookupSpecial(o, "__sizeof__", + &str__sizeof__); + if (method == NULL) { + if (!PyErr_Occurred()) + PyErr_Format(PyExc_TypeError, + "Type %.100s doesn't define __sizeof__", + Py_TYPE(o)->tp_name); + } + else { + res = PyObject_CallFunctionObjArgs(method, NULL); + Py_DECREF(method); + } + + if (res == NULL) + return (size_t)-1; + + size = (size_t)PyInt_AsSsize_t(res); + Py_DECREF(res); + if (size == -1 && PyErr_Occurred()) + return (size_t)-1; + } + + if (size < 0) { + PyErr_SetString(PyExc_ValueError, "__sizeof__() should return >= 0"); + return (size_t)-1; + } + + /* add gc_head size */ + if (PyObject_IS_GC(o)) + return ((size_t)size) + sizeof(PyGC_Head); + return (size_t)size; +} + +static PyObject * +sys_getsizeof(PyObject *self, PyObject *args, PyObject *kwds) +{ + static char *kwlist[] = {"object", "default", 0}; + size_t size; + PyObject *o, *dflt = NULL; + + if (!PyArg_ParseTupleAndKeywords(args, kwds, "O|O:getsizeof", + kwlist, &o, &dflt)) + return NULL; + + size = _PySys_GetSizeOf(o); + + if (size == (size_t)-1 && PyErr_Occurred()) { + /* Has a default value been given */ + if (dflt != NULL && PyErr_ExceptionMatches(PyExc_TypeError)) { + PyErr_Clear(); + Py_INCREF(dflt); + return dflt; + } + else + return NULL; + } + + return PyInt_FromSize_t(size); +} + +PyDoc_STRVAR(getsizeof_doc, +"getsizeof(object, default) -> int\n\ +\n\ +Return the size of object in bytes."); + +static PyObject * +sys_getrefcount(PyObject *self, PyObject *arg) +{ + return PyInt_FromSsize_t(arg->ob_refcnt); +} + +#ifdef Py_REF_DEBUG +static PyObject * +sys_gettotalrefcount(PyObject *self) +{ + return PyInt_FromSsize_t(_Py_GetRefTotal()); +} +#endif /* Py_REF_DEBUG */ + +PyDoc_STRVAR(getrefcount_doc, +"getrefcount(object) -> integer\n\ +\n\ +Return the reference count of object. The count returned is generally\n\ +one higher than you might expect, because it includes the (temporary)\n\ +reference as an argument to getrefcount()." +); + +#ifdef COUNT_ALLOCS +static PyObject * +sys_getcounts(PyObject *self) +{ + extern PyObject *get_counts(void); + + return get_counts(); +} +#endif + +PyDoc_STRVAR(getframe_doc, +"_getframe([depth]) -> frameobject\n\ +\n\ +Return a frame object from the call stack. If optional integer depth is\n\ +given, return the frame object that many calls below the top of the stack.\n\ +If that is deeper than the call stack, ValueError is raised. The default\n\ +for depth is zero, returning the frame at the top of the call stack.\n\ +\n\ +This function should be used for internal and specialized\n\ +purposes only." +); + +static PyObject * +sys_getframe(PyObject *self, PyObject *args) +{ + PyFrameObject *f = PyThreadState_GET()->frame; + int depth = -1; + + if (!PyArg_ParseTuple(args, "|i:_getframe", &depth)) + return NULL; + + while (depth > 0 && f != NULL) { + f = f->f_back; + --depth; + } + if (f == NULL) { + PyErr_SetString(PyExc_ValueError, + "call stack is not deep enough"); + return NULL; + } + Py_INCREF(f); + return (PyObject*)f; +} + +PyDoc_STRVAR(current_frames_doc, +"_current_frames() -> dictionary\n\ +\n\ +Return a dictionary mapping each current thread T's thread id to T's\n\ +current stack frame.\n\ +\n\ +This function should be used for specialized purposes only." +); + +static PyObject * +sys_current_frames(PyObject *self, PyObject *noargs) +{ + return _PyThread_CurrentFrames(); +} + +PyDoc_STRVAR(call_tracing_doc, +"call_tracing(func, args) -> object\n\ +\n\ +Call func(*args), while tracing is enabled. The tracing state is\n\ +saved, and restored afterwards. This is intended to be called from\n\ +a debugger from a checkpoint, to recursively debug some other code." +); + +static PyObject * +sys_call_tracing(PyObject *self, PyObject *args) +{ + PyObject *func, *funcargs; + if (!PyArg_ParseTuple(args, "OO!:call_tracing", &func, &PyTuple_Type, &funcargs)) + return NULL; + return _PyEval_CallTracing(func, funcargs); +} + +PyDoc_STRVAR(callstats_doc, +"callstats() -> tuple of integers\n\ +\n\ +Return a tuple of function call statistics, if CALL_PROFILE was defined\n\ +when Python was built. Otherwise, return None.\n\ +\n\ +When enabled, this function returns detailed, implementation-specific\n\ +details about the number of function calls executed. The return value is\n\ +a 11-tuple where the entries in the tuple are counts of:\n\ +0. all function calls\n\ +1. calls to PyFunction_Type objects\n\ +2. PyFunction calls that do not create an argument tuple\n\ +3. PyFunction calls that do not create an argument tuple\n\ + and bypass PyEval_EvalCodeEx()\n\ +4. PyMethod calls\n\ +5. PyMethod calls on bound methods\n\ +6. PyType calls\n\ +7. PyCFunction calls\n\ +8. generator calls\n\ +9. All other calls\n\ +10. Number of stack pops performed by call_function()" +); + +#ifdef __cplusplus +extern "C" { +#endif + +#ifdef Py_TRACE_REFS +/* Defined in objects.c because it uses static globals if that file */ +extern PyObject *_Py_GetObjects(PyObject *, PyObject *); +#endif + +#ifdef DYNAMIC_EXECUTION_PROFILE +/* Defined in ceval.c because it uses static globals if that file */ +extern PyObject *_Py_GetDXProfile(PyObject *, PyObject *); +#endif + +#ifdef __cplusplus +} +#endif + +static PyObject * +sys_clear_type_cache(PyObject* self, PyObject* args) +{ + PyType_ClearCache(); + Py_RETURN_NONE; +} + +PyDoc_STRVAR(sys_clear_type_cache__doc__, +"_clear_type_cache() -> None\n\ +Clear the internal type lookup cache."); + + +static PyMethodDef sys_methods[] = { + /* Might as well keep this in alphabetic order */ + {"callstats", (PyCFunction)PyEval_GetCallStats, METH_NOARGS, + callstats_doc}, + {"_clear_type_cache", sys_clear_type_cache, METH_NOARGS, + sys_clear_type_cache__doc__}, + {"_current_frames", sys_current_frames, METH_NOARGS, + current_frames_doc}, + {"displayhook", sys_displayhook, METH_O, displayhook_doc}, + {"exc_info", sys_exc_info, METH_NOARGS, exc_info_doc}, + {"exc_clear", sys_exc_clear, METH_NOARGS, exc_clear_doc}, + {"excepthook", sys_excepthook, METH_VARARGS, excepthook_doc}, + {"exit", sys_exit, METH_VARARGS, exit_doc}, +#ifdef Py_USING_UNICODE + {"getdefaultencoding", (PyCFunction)sys_getdefaultencoding, + METH_NOARGS, getdefaultencoding_doc}, +#endif +#ifdef HAVE_DLOPEN + {"getdlopenflags", (PyCFunction)sys_getdlopenflags, METH_NOARGS, + getdlopenflags_doc}, +#endif +#ifdef COUNT_ALLOCS + {"getcounts", (PyCFunction)sys_getcounts, METH_NOARGS}, +#endif +#ifdef DYNAMIC_EXECUTION_PROFILE + {"getdxp", _Py_GetDXProfile, METH_VARARGS}, +#endif +#ifdef Py_USING_UNICODE + {"getfilesystemencoding", (PyCFunction)sys_getfilesystemencoding, + METH_NOARGS, getfilesystemencoding_doc}, +#endif +#ifdef Py_TRACE_REFS + {"getobjects", _Py_GetObjects, METH_VARARGS}, +#endif +#ifdef Py_REF_DEBUG + {"gettotalrefcount", (PyCFunction)sys_gettotalrefcount, METH_NOARGS}, +#endif + {"getrefcount", (PyCFunction)sys_getrefcount, METH_O, getrefcount_doc}, + {"getrecursionlimit", (PyCFunction)sys_getrecursionlimit, METH_NOARGS, + getrecursionlimit_doc}, + {"getsizeof", (PyCFunction)sys_getsizeof, + METH_VARARGS | METH_KEYWORDS, getsizeof_doc}, + {"_getframe", sys_getframe, METH_VARARGS, getframe_doc}, +#ifdef MS_WINDOWS + {"getwindowsversion", (PyCFunction)sys_getwindowsversion, METH_NOARGS, + getwindowsversion_doc}, +#endif /* MS_WINDOWS */ +#ifdef USE_MALLOPT + {"mdebug", sys_mdebug, METH_VARARGS}, +#endif +#ifdef Py_USING_UNICODE + {"setdefaultencoding", sys_setdefaultencoding, METH_VARARGS, + setdefaultencoding_doc}, +#endif + {"setcheckinterval", sys_setcheckinterval, METH_VARARGS, + setcheckinterval_doc}, + {"getcheckinterval", sys_getcheckinterval, METH_NOARGS, + getcheckinterval_doc}, +#ifdef HAVE_DLOPEN + {"setdlopenflags", sys_setdlopenflags, METH_VARARGS, + setdlopenflags_doc}, +#endif + {"setprofile", sys_setprofile, METH_O, setprofile_doc}, + {"getprofile", sys_getprofile, METH_NOARGS, getprofile_doc}, + {"setrecursionlimit", sys_setrecursionlimit, METH_VARARGS, + setrecursionlimit_doc}, +#ifdef WITH_TSC + {"settscdump", sys_settscdump, METH_VARARGS, settscdump_doc}, +#endif + {"settrace", sys_settrace, METH_O, settrace_doc}, + {"gettrace", sys_gettrace, METH_NOARGS, gettrace_doc}, + {"call_tracing", sys_call_tracing, METH_VARARGS, call_tracing_doc}, + {NULL, NULL} /* sentinel */ +}; + +static PyObject * +list_builtin_module_names(void) +{ + PyObject *list = PyList_New(0); + int i; + if (list == NULL) + return NULL; + for (i = 0; PyImport_Inittab[i].name != NULL; i++) { + PyObject *name = PyString_FromString( + PyImport_Inittab[i].name); + if (name == NULL) + break; + PyList_Append(list, name); + Py_DECREF(name); + } + if (PyList_Sort(list) != 0) { + Py_DECREF(list); + list = NULL; + } + if (list) { + PyObject *v = PyList_AsTuple(list); + Py_DECREF(list); + list = v; + } + return list; +} + +static PyObject *warnoptions = NULL; + +void +PySys_ResetWarnOptions(void) +{ + if (warnoptions == NULL || !PyList_Check(warnoptions)) + return; + PyList_SetSlice(warnoptions, 0, PyList_GET_SIZE(warnoptions), NULL); +} + +void +PySys_AddWarnOption(char *s) +{ + PyObject *str; + + if (warnoptions == NULL || !PyList_Check(warnoptions)) { + Py_XDECREF(warnoptions); + warnoptions = PyList_New(0); + if (warnoptions == NULL) + return; + } + str = PyString_FromString(s); + if (str != NULL) { + PyList_Append(warnoptions, str); + Py_DECREF(str); + } +} + +int +PySys_HasWarnOptions(void) +{ + return (warnoptions != NULL && (PyList_Size(warnoptions) > 0)) ? 1 : 0; +} + +/* XXX This doc string is too long to be a single string literal in VC++ 5.0. + Two literals concatenated works just fine. If you have a K&R compiler + or other abomination that however *does* understand longer strings, + get rid of the !!! comment in the middle and the quotes that surround it. */ +PyDoc_VAR(sys_doc) = +PyDoc_STR( +"This module provides access to some objects used or maintained by the\n\ +interpreter and to functions that interact strongly with the interpreter.\n\ +\n\ +Dynamic objects:\n\ +\n\ +argv -- command line arguments; argv[0] is the script pathname if known\n\ +path -- module search path; path[0] is the script directory, else ''\n\ +modules -- dictionary of loaded modules\n\ +\n\ +displayhook -- called to show results in an interactive session\n\ +excepthook -- called to handle any uncaught exception other than SystemExit\n\ + To customize printing in an interactive session or to install a custom\n\ + top-level exception handler, assign other functions to replace these.\n\ +\n\ +exitfunc -- if sys.exitfunc exists, this routine is called when Python exits\n\ + Assigning to sys.exitfunc is deprecated; use the atexit module instead.\n\ +\n\ +stdin -- standard input file object; used by raw_input() and input()\n\ +stdout -- standard output file object; used by the print statement\n\ +stderr -- standard error object; used for error messages\n\ + By assigning other file objects (or objects that behave like files)\n\ + to these, it is possible to redirect all of the interpreter's I/O.\n\ +\n\ +last_type -- type of last uncaught exception\n\ +last_value -- value of last uncaught exception\n\ +last_traceback -- traceback of last uncaught exception\n\ + These three are only available in an interactive session after a\n\ + traceback has been printed.\n\ +\n\ +exc_type -- type of exception currently being handled\n\ +exc_value -- value of exception currently being handled\n\ +exc_traceback -- traceback of exception currently being handled\n\ + The function exc_info() should be used instead of these three,\n\ + because it is thread-safe.\n\ +" +) +/* concatenating string here */ +PyDoc_STR( +"\n\ +Static objects:\n\ +\n\ +float_info -- a dict with information about the float inplementation.\n\ +long_info -- a struct sequence with information about the long implementation.\n\ +maxint -- the largest supported integer (the smallest is -maxint-1)\n\ +maxsize -- the largest supported length of containers.\n\ +maxunicode -- the largest supported character\n\ +builtin_module_names -- tuple of module names built into this interpreter\n\ +version -- the version of this interpreter as a string\n\ +version_info -- version information as a named tuple\n\ +hexversion -- version information encoded as a single integer\n\ +copyright -- copyright notice pertaining to this interpreter\n\ +platform -- platform identifier\n\ +executable -- absolute path of the executable binary of the Python interpreter\n\ +prefix -- prefix used to find the Python library\n\ +exec_prefix -- prefix used to find the machine-specific Python library\n\ +float_repr_style -- string indicating the style of repr() output for floats\n\ +" +) +#ifdef MS_WINDOWS +/* concatenating string here */ +PyDoc_STR( +"dllhandle -- [Windows only] integer handle of the Python DLL\n\ +winver -- [Windows only] version number of the Python DLL\n\ +" +) +#endif /* MS_WINDOWS */ +PyDoc_STR( +"__stdin__ -- the original stdin; don't touch!\n\ +__stdout__ -- the original stdout; don't touch!\n\ +__stderr__ -- the original stderr; don't touch!\n\ +__displayhook__ -- the original displayhook; don't touch!\n\ +__excepthook__ -- the original excepthook; don't touch!\n\ +\n\ +Functions:\n\ +\n\ +displayhook() -- print an object to the screen, and save it in __builtin__._\n\ +excepthook() -- print an exception and its traceback to sys.stderr\n\ +exc_info() -- return thread-safe information about the current exception\n\ +exc_clear() -- clear the exception state for the current thread\n\ +exit() -- exit the interpreter by raising SystemExit\n\ +getdlopenflags() -- returns flags to be used for dlopen() calls\n\ +getprofile() -- get the global profiling function\n\ +getrefcount() -- return the reference count for an object (plus one :-)\n\ +getrecursionlimit() -- return the max recursion depth for the interpreter\n\ +getsizeof() -- return the size of an object in bytes\n\ +gettrace() -- get the global debug tracing function\n\ +setcheckinterval() -- control how often the interpreter checks for events\n\ +setdlopenflags() -- set the flags to be used for dlopen() calls\n\ +setprofile() -- set the global profiling function\n\ +setrecursionlimit() -- set the max recursion depth for the interpreter\n\ +settrace() -- set the global debug tracing function\n\ +" +) +/* end of sys_doc */ ; + +static int +_check_and_flush (FILE *stream) +{ + int prev_fail = ferror (stream); + return fflush (stream) || prev_fail ? EOF : 0; +} + +/* Subversion branch and revision management */ +static int svn_initialized; +static char patchlevel_revision[50]; /* Just the number */ +static char branch[50]; +static char shortbranch[50]; +static const char *svn_revision; + +static void +svnversion_init(void) +{ + if (svn_initialized) + return; + svn_initialized = 1; + *patchlevel_revision = '\0'; + strcpy(branch, ""); + strcpy(shortbranch, "unknown"); + svn_revision = ""; + return; +} + +/* Return svnversion output if available. + Else return Revision of patchlevel.h if on branch. + Else return empty string */ +const char* +Py_SubversionRevision() +{ + svnversion_init(); + return svn_revision; +} + +const char* +Py_SubversionShortBranch() +{ + svnversion_init(); + return shortbranch; +} + + +PyDoc_STRVAR(flags__doc__, +"sys.flags\n\ +\n\ +Flags provided through command line arguments or environment vars."); + +static PyTypeObject FlagsType = {0, 0, 0, 0, 0, 0}; + +static PyStructSequence_Field flags_fields[] = { + {"debug", "-d"}, + {"py3k_warning", "-3"}, + {"division_warning", "-Q"}, + {"division_new", "-Qnew"}, + {"inspect", "-i"}, + {"interactive", "-i"}, + {"optimize", "-O or -OO"}, + {"dont_write_bytecode", "-B"}, + {"no_user_site", "-s"}, + {"no_site", "-S"}, + {"ignore_environment", "-E"}, + {"tabcheck", "-t or -tt"}, + {"verbose", "-v"}, +#ifdef RISCOS + {"riscos_wimp", "???"}, +#endif + /* {"unbuffered", "-u"}, */ + {"unicode", "-U"}, + /* {"skip_first", "-x"}, */ + {"bytes_warning", "-b"}, + {"hash_randomization", "-R"}, + {0} +}; + +static PyStructSequence_Desc flags_desc = { + "sys.flags", /* name */ + flags__doc__, /* doc */ + flags_fields, /* fields */ +#ifdef RISCOS + 17 +#else + 16 +#endif +}; + +static PyObject* +make_flags(void) +{ + int pos = 0; + PyObject *seq; + + seq = PyStructSequence_New(&FlagsType); + if (seq == NULL) + return NULL; + +#define SetFlag(flag) \ + PyStructSequence_SET_ITEM(seq, pos++, PyInt_FromLong(flag)) + + SetFlag(Py_DebugFlag); + SetFlag(Py_Py3kWarningFlag); + SetFlag(Py_DivisionWarningFlag); + SetFlag(_Py_QnewFlag); + SetFlag(Py_InspectFlag); + SetFlag(Py_InteractiveFlag); + SetFlag(Py_OptimizeFlag); + SetFlag(Py_DontWriteBytecodeFlag); + SetFlag(Py_NoUserSiteDirectory); + SetFlag(Py_NoSiteFlag); + SetFlag(Py_IgnoreEnvironmentFlag); + SetFlag(Py_TabcheckFlag); + SetFlag(Py_VerboseFlag); +#ifdef RISCOS + SetFlag(Py_RISCOSWimpFlag); +#endif + /* SetFlag(saw_unbuffered_flag); */ + SetFlag(Py_UnicodeFlag); + /* SetFlag(skipfirstline); */ + SetFlag(Py_BytesWarningFlag); + SetFlag(Py_HashRandomizationFlag); +#undef SetFlag + + if (PyErr_Occurred()) { + Py_DECREF(seq); + return NULL; + } + return seq; +} + +PyDoc_STRVAR(version_info__doc__, +"sys.version_info\n\ +\n\ +Version information as a named tuple."); + +static PyTypeObject VersionInfoType = {0, 0, 0, 0, 0, 0}; + +static PyStructSequence_Field version_info_fields[] = { + {"major", "Major release number"}, + {"minor", "Minor release number"}, + {"micro", "Patch release number"}, + {"releaselevel", "'alpha', 'beta', 'candidate', or 'release'"}, + {"serial", "Serial release number"}, + {0} +}; + +static PyStructSequence_Desc version_info_desc = { + "sys.version_info", /* name */ + version_info__doc__, /* doc */ + version_info_fields, /* fields */ + 5 +}; + +static PyObject * +make_version_info(void) +{ + PyObject *version_info; + char *s; + int pos = 0; + + version_info = PyStructSequence_New(&VersionInfoType); + if (version_info == NULL) { + return NULL; + } + + /* + * These release level checks are mutually exclusive and cover + * the field, so don't get too fancy with the pre-processor! + */ +#if PY_RELEASE_LEVEL == PY_RELEASE_LEVEL_ALPHA + s = "alpha"; +#elif PY_RELEASE_LEVEL == PY_RELEASE_LEVEL_BETA + s = "beta"; +#elif PY_RELEASE_LEVEL == PY_RELEASE_LEVEL_GAMMA + s = "candidate"; +#elif PY_RELEASE_LEVEL == PY_RELEASE_LEVEL_FINAL + s = "final"; +#endif + +#define SetIntItem(flag) \ + PyStructSequence_SET_ITEM(version_info, pos++, PyInt_FromLong(flag)) +#define SetStrItem(flag) \ + PyStructSequence_SET_ITEM(version_info, pos++, PyString_FromString(flag)) + + SetIntItem(PY_MAJOR_VERSION); + SetIntItem(PY_MINOR_VERSION); + SetIntItem(PY_MICRO_VERSION); + SetStrItem(s); + SetIntItem(PY_RELEASE_SERIAL); +#undef SetIntItem +#undef SetStrItem + + if (PyErr_Occurred()) { + Py_CLEAR(version_info); + return NULL; + } + return version_info; +} + +PyObject * +_PySys_Init(void) +{ + PyObject *m, *v, *sysdict; + PyObject *sysin, *sysout, *syserr; + char *s; + + m = Py_InitModule3("sys", sys_methods, sys_doc); + if (m == NULL) + return NULL; + sysdict = PyModule_GetDict(m); +#define SET_SYS_FROM_STRING(key, value) \ + v = value; \ + if (v != NULL) \ + PyDict_SetItemString(sysdict, key, v); \ + Py_XDECREF(v) + + /* Check that stdin is not a directory + Using shell redirection, you can redirect stdin to a directory, + crashing the Python interpreter. Catch this common mistake here + and output a useful error message. Note that under MS Windows, + the shell already prevents that. */ +#if !defined(MS_WINDOWS) + { + struct stat sb; + if (fstat(fileno(stdin), &sb) == 0 && + S_ISDIR(sb.st_mode)) { + /* There's nothing more we can do. */ + /* Py_FatalError() will core dump, so just exit. */ + PySys_WriteStderr("Python error: is a directory, cannot continue\n"); + exit(EXIT_FAILURE); + } + } +#endif + + /* Closing the standard FILE* if sys.std* goes aways causes problems + * for embedded Python usages. Closing them when somebody explicitly + * invokes .close() might be possible, but the FAQ promises they get + * never closed. However, we still need to get write errors when + * writing fails (e.g. because stdout is redirected), so we flush the + * streams and check for errors before the file objects are deleted. + * On OS X, fflush()ing stdin causes an error, so we exempt stdin + * from that procedure. + */ + sysin = PyFile_FromFile(stdin, "", "r", NULL); + sysout = PyFile_FromFile(stdout, "", "w", _check_and_flush); + syserr = PyFile_FromFile(stderr, "", "w", _check_and_flush); + if (PyErr_Occurred()) + return NULL; + + PyDict_SetItemString(sysdict, "stdin", sysin); + PyDict_SetItemString(sysdict, "stdout", sysout); + PyDict_SetItemString(sysdict, "stderr", syserr); + /* Make backup copies for cleanup */ + PyDict_SetItemString(sysdict, "__stdin__", sysin); + PyDict_SetItemString(sysdict, "__stdout__", sysout); + PyDict_SetItemString(sysdict, "__stderr__", syserr); + PyDict_SetItemString(sysdict, "__displayhook__", + PyDict_GetItemString(sysdict, "displayhook")); + PyDict_SetItemString(sysdict, "__excepthook__", + PyDict_GetItemString(sysdict, "excepthook")); + Py_XDECREF(sysin); + Py_XDECREF(sysout); + Py_XDECREF(syserr); + + SET_SYS_FROM_STRING("version", + PyString_FromString(Py_GetVersion())); + SET_SYS_FROM_STRING("hexversion", + PyInt_FromLong(PY_VERSION_HEX)); + svnversion_init(); + SET_SYS_FROM_STRING("subversion", + Py_BuildValue("(ssz)", "CPython", branch, + svn_revision)); + SET_SYS_FROM_STRING("_mercurial", + Py_BuildValue("(szz)", "CPython", _Py_hgidentifier(), + _Py_hgversion())); + SET_SYS_FROM_STRING("dont_write_bytecode", + PyBool_FromLong(Py_DontWriteBytecodeFlag)); + SET_SYS_FROM_STRING("api_version", + PyInt_FromLong(PYTHON_API_VERSION)); + SET_SYS_FROM_STRING("copyright", + PyString_FromString(Py_GetCopyright())); + SET_SYS_FROM_STRING("platform", + PyString_FromString(Py_GetPlatform())); + SET_SYS_FROM_STRING("executable", + PyString_FromString(Py_GetProgramFullPath())); + SET_SYS_FROM_STRING("prefix", + PyString_FromString(Py_GetPrefix())); + SET_SYS_FROM_STRING("exec_prefix", + PyString_FromString(Py_GetExecPrefix())); + SET_SYS_FROM_STRING("maxsize", + PyInt_FromSsize_t(PY_SSIZE_T_MAX)); + SET_SYS_FROM_STRING("maxint", + PyInt_FromLong(PyInt_GetMax())); + SET_SYS_FROM_STRING("py3kwarning", + PyBool_FromLong(Py_Py3kWarningFlag)); + SET_SYS_FROM_STRING("float_info", + PyFloat_GetInfo()); + SET_SYS_FROM_STRING("long_info", + PyLong_GetInfo()); +#ifdef Py_USING_UNICODE + SET_SYS_FROM_STRING("maxunicode", + PyInt_FromLong(PyUnicode_GetMax())); +#endif + SET_SYS_FROM_STRING("builtin_module_names", + list_builtin_module_names()); + { + /* Assumes that longs are at least 2 bytes long. + Should be safe! */ + unsigned long number = 1; + char *value; + + s = (char *) &number; + if (s[0] == 0) + value = "big"; + else + value = "little"; + SET_SYS_FROM_STRING("byteorder", + PyString_FromString(value)); + } +#ifdef MS_COREDLL + SET_SYS_FROM_STRING("dllhandle", + PyLong_FromVoidPtr(PyWin_DLLhModule)); + SET_SYS_FROM_STRING("winver", + PyString_FromString(PyWin_DLLVersionString)); +#endif + if (warnoptions == NULL) { + warnoptions = PyList_New(0); + } + else { + Py_INCREF(warnoptions); + } + if (warnoptions != NULL) { + PyDict_SetItemString(sysdict, "warnoptions", warnoptions); + } + + /* version_info */ + if (VersionInfoType.tp_name == 0) + PyStructSequence_InitType(&VersionInfoType, &version_info_desc); + SET_SYS_FROM_STRING("version_info", make_version_info()); + /* prevent user from creating new instances */ + VersionInfoType.tp_init = NULL; + VersionInfoType.tp_new = NULL; + + /* flags */ + if (FlagsType.tp_name == 0) + PyStructSequence_InitType(&FlagsType, &flags_desc); + SET_SYS_FROM_STRING("flags", make_flags()); + /* prevent user from creating new instances */ + FlagsType.tp_init = NULL; + FlagsType.tp_new = NULL; + + +#if defined(MS_WINDOWS) + /* getwindowsversion */ + if (WindowsVersionType.tp_name == 0) + PyStructSequence_InitType(&WindowsVersionType, &windows_version_desc); + /* prevent user from creating new instances */ + WindowsVersionType.tp_init = NULL; + WindowsVersionType.tp_new = NULL; +#endif + + /* float repr style: 0.03 (short) vs 0.029999999999999999 (legacy) */ +#ifndef PY_NO_SHORT_FLOAT_REPR + SET_SYS_FROM_STRING("float_repr_style", + PyString_FromString("short")); +#else + SET_SYS_FROM_STRING("float_repr_style", + PyString_FromString("legacy")); +#endif + +#undef SET_SYS_FROM_STRING + if (PyErr_Occurred()) + return NULL; + return m; +} + +static PyObject * +makepathobject(char *path, int delim) +{ + int i, n; + char *p; + PyObject *v, *w; + + n = 1; + p = path; + while ((p = strchr(p, delim)) != NULL) { + n++; + p++; + } + v = PyList_New(n); + if (v == NULL) + return NULL; + for (i = 0; ; i++) { + p = strchr(path, delim); + if (p == NULL) + p = strchr(path, '\0'); /* End of string */ + w = PyString_FromStringAndSize(path, (Py_ssize_t) (p - path)); + if (w == NULL) { + Py_DECREF(v); + return NULL; + } + PyList_SetItem(v, i, w); + if (*p == '\0') + break; + path = p+1; + } + return v; +} + +void +PySys_SetPath(char *path) +{ + PyObject *v; + if ((v = makepathobject(path, DELIM)) == NULL) + Py_FatalError("can't create sys.path"); + if (PySys_SetObject("path", v) != 0) + Py_FatalError("can't assign sys.path"); + Py_DECREF(v); +} + +static PyObject * +makeargvobject(int argc, char **argv) +{ + PyObject *av; + if (argc <= 0 || argv == NULL) { + /* Ensure at least one (empty) argument is seen */ + static char *empty_argv[1] = {""}; + argv = empty_argv; + argc = 1; + } + av = PyList_New(argc); + if (av != NULL) { + int i; + for (i = 0; i < argc; i++) { +#ifdef __VMS + PyObject *v; + + /* argv[0] is the script pathname if known */ + if (i == 0) { + char* fn = decc$translate_vms(argv[0]); + if ((fn == (char *)0) || fn == (char *)-1) + v = PyString_FromString(argv[0]); + else + v = PyString_FromString( + decc$translate_vms(argv[0])); + } else + v = PyString_FromString(argv[i]); +#else + PyObject *v = PyString_FromString(argv[i]); +#endif + if (v == NULL) { + Py_DECREF(av); + av = NULL; + break; + } + PyList_SetItem(av, i, v); + } + } + return av; +} + +void +PySys_SetArgvEx(int argc, char **argv, int updatepath) +{ +#if defined(HAVE_REALPATH) + char fullpath[MAXPATHLEN]; +#elif defined(MS_WINDOWS) && !defined(MS_WINCE) + char fullpath[MAX_PATH]; +#endif + PyObject *av = makeargvobject(argc, argv); + PyObject *path = PySys_GetObject("path"); + if (av == NULL) + Py_FatalError("no mem for sys.argv"); + if (PySys_SetObject("argv", av) != 0) + Py_FatalError("can't assign sys.argv"); + if (updatepath && path != NULL) { + char *argv0 = argv[0]; + char *p = NULL; + Py_ssize_t n = 0; + PyObject *a; +#ifdef HAVE_READLINK + char link[MAXPATHLEN+1]; + char argv0copy[2*MAXPATHLEN+1]; + int nr = 0; + if (argc > 0 && argv0 != NULL && strcmp(argv0, "-c") != 0) + nr = readlink(argv0, link, MAXPATHLEN); + if (nr > 0) { + /* It's a symlink */ + link[nr] = '\0'; + if (link[0] == SEP) + argv0 = link; /* Link to absolute path */ + else if (strchr(link, SEP) == NULL) + ; /* Link without path */ + else { + /* Must join(dirname(argv0), link) */ + char *q = strrchr(argv0, SEP); + if (q == NULL) + argv0 = link; /* argv0 without path */ + else { + /* Must make a copy */ + strcpy(argv0copy, argv0); + q = strrchr(argv0copy, SEP); + strcpy(q+1, link); + argv0 = argv0copy; + } + } + } +#endif /* HAVE_READLINK */ +#if SEP == '\\' /* Special case for MS filename syntax */ + if (argc > 0 && argv0 != NULL && strcmp(argv0, "-c") != 0) { + char *q; +#if defined(MS_WINDOWS) && !defined(MS_WINCE) + /* This code here replaces the first element in argv with the full + path that it represents. Under CE, there are no relative paths so + the argument must be the full path anyway. */ + char *ptemp; + if (GetFullPathName(argv0, + sizeof(fullpath), + fullpath, + &ptemp)) { + argv0 = fullpath; + } +#endif + p = strrchr(argv0, SEP); + /* Test for alternate separator */ + q = strrchr(p ? p : argv0, '/'); + if (q != NULL) + p = q; + if (p != NULL) { + n = p + 1 - argv0; + if (n > 1 && p[-1] != ':') + n--; /* Drop trailing separator */ + } + } +#else /* All other filename syntaxes */ + if (argc > 0 && argv0 != NULL && strcmp(argv0, "-c") != 0) { +#if defined(HAVE_REALPATH) + if (realpath(argv0, fullpath)) { + argv0 = fullpath; + } +#endif + p = strrchr(argv0, SEP); + } + if (p != NULL) { +#ifndef RISCOS + n = p + 1 - argv0; +#else /* don't include trailing separator */ + n = p - argv0; +#endif /* RISCOS */ +#if SEP == '/' /* Special case for Unix filename syntax */ + if (n > 1) + n--; /* Drop trailing separator */ +#endif /* Unix */ + } +#endif /* All others */ + a = PyString_FromStringAndSize(argv0, n); + if (a == NULL) + Py_FatalError("no mem for sys.path insertion"); + if (PyList_Insert(path, 0, a) < 0) + Py_FatalError("sys.path.insert(0) failed"); + Py_DECREF(a); + } + Py_DECREF(av); +} + +void +PySys_SetArgv(int argc, char **argv) +{ + PySys_SetArgvEx(argc, argv, 1); +} + + +/* APIs to write to sys.stdout or sys.stderr using a printf-like interface. + Adapted from code submitted by Just van Rossum. + + PySys_WriteStdout(format, ...) + PySys_WriteStderr(format, ...) + + The first function writes to sys.stdout; the second to sys.stderr. When + there is a problem, they write to the real (C level) stdout or stderr; + no exceptions are raised. + + Both take a printf-style format string as their first argument followed + by a variable length argument list determined by the format string. + + *** WARNING *** + + The format should limit the total size of the formatted output string to + 1000 bytes. In particular, this means that no unrestricted "%s" formats + should occur; these should be limited using "%.s where is a + decimal number calculated so that plus the maximum size of other + formatted text does not exceed 1000 bytes. Also watch out for "%f", + which can print hundreds of digits for very large numbers. + + */ + +static void +mywrite(char *name, FILE *fp, const char *format, va_list va) +{ + PyObject *file; + PyObject *error_type, *error_value, *error_traceback; + + PyErr_Fetch(&error_type, &error_value, &error_traceback); + file = PySys_GetObject(name); + if (file == NULL || PyFile_AsFile(file) == fp) + vfprintf(fp, format, va); + else { + char buffer[1001]; + const int written = PyOS_vsnprintf(buffer, sizeof(buffer), + format, va); + if (PyFile_WriteString(buffer, file) != 0) { + PyErr_Clear(); + fputs(buffer, fp); + } + if (written < 0 || (size_t)written >= sizeof(buffer)) { + const char *truncated = "... truncated"; + if (PyFile_WriteString(truncated, file) != 0) { + PyErr_Clear(); + fputs(truncated, fp); + } + } + } + PyErr_Restore(error_type, error_value, error_traceback); +} + +void +PySys_WriteStdout(const char *format, ...) +{ + va_list va; + + va_start(va, format); + mywrite("stdout", stdout, format, va); + va_end(va); +} + +void +PySys_WriteStderr(const char *format, ...) +{ + va_list va; + + va_start(va, format); + mywrite("stderr", stderr, format, va); + va_end(va); +} diff --git a/AppPkg/Applications/Python/Python-2.7.10/Python/traceback.c b/AppPkg/Applications/Python/Python-2.7.10/Python/traceback.c new file mode 100644 index 0000000000..85caa02869 --- /dev/null +++ b/AppPkg/Applications/Python/Python-2.7.10/Python/traceback.c @@ -0,0 +1,283 @@ + +/* Traceback implementation */ + +#include "Python.h" + +#include "code.h" +#include "frameobject.h" +#include "structmember.h" +#include "osdefs.h" +#include "traceback.h" + +#define OFF(x) offsetof(PyTracebackObject, x) + +static PyMemberDef tb_memberlist[] = { + {"tb_next", T_OBJECT, OFF(tb_next), READONLY}, + {"tb_frame", T_OBJECT, OFF(tb_frame), READONLY}, + {"tb_lasti", T_INT, OFF(tb_lasti), READONLY}, + {"tb_lineno", T_INT, OFF(tb_lineno), READONLY}, + {NULL} /* Sentinel */ +}; + +static void +tb_dealloc(PyTracebackObject *tb) +{ + PyObject_GC_UnTrack(tb); + Py_TRASHCAN_SAFE_BEGIN(tb) + Py_XDECREF(tb->tb_next); + Py_XDECREF(tb->tb_frame); + PyObject_GC_Del(tb); + Py_TRASHCAN_SAFE_END(tb) +} + +static int +tb_traverse(PyTracebackObject *tb, visitproc visit, void *arg) +{ + Py_VISIT(tb->tb_next); + Py_VISIT(tb->tb_frame); + return 0; +} + +static void +tb_clear(PyTracebackObject *tb) +{ + Py_CLEAR(tb->tb_next); + Py_CLEAR(tb->tb_frame); +} + +PyTypeObject PyTraceBack_Type = { + PyVarObject_HEAD_INIT(&PyType_Type, 0) + "traceback", + sizeof(PyTracebackObject), + 0, + (destructor)tb_dealloc, /*tp_dealloc*/ + 0, /*tp_print*/ + 0, /*tp_getattr*/ + 0, /*tp_setattr*/ + 0, /*tp_compare*/ + 0, /*tp_repr*/ + 0, /*tp_as_number*/ + 0, /*tp_as_sequence*/ + 0, /*tp_as_mapping*/ + 0, /* tp_hash */ + 0, /* tp_call */ + 0, /* tp_str */ + 0, /* tp_getattro */ + 0, /* tp_setattro */ + 0, /* tp_as_buffer */ + Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC,/* tp_flags */ + 0, /* tp_doc */ + (traverseproc)tb_traverse, /* tp_traverse */ + (inquiry)tb_clear, /* tp_clear */ + 0, /* tp_richcompare */ + 0, /* tp_weaklistoffset */ + 0, /* tp_iter */ + 0, /* tp_iternext */ + 0, /* tp_methods */ + tb_memberlist, /* tp_members */ + 0, /* tp_getset */ + 0, /* tp_base */ + 0, /* tp_dict */ +}; + +static PyTracebackObject * +newtracebackobject(PyTracebackObject *next, PyFrameObject *frame) +{ + PyTracebackObject *tb; + if ((next != NULL && !PyTraceBack_Check(next)) || + frame == NULL || !PyFrame_Check(frame)) { + PyErr_BadInternalCall(); + return NULL; + } + tb = PyObject_GC_New(PyTracebackObject, &PyTraceBack_Type); + if (tb != NULL) { + Py_XINCREF(next); + tb->tb_next = next; + Py_XINCREF(frame); + tb->tb_frame = frame; + tb->tb_lasti = frame->f_lasti; + tb->tb_lineno = PyFrame_GetLineNumber(frame); + PyObject_GC_Track(tb); + } + return tb; +} + +int +PyTraceBack_Here(PyFrameObject *frame) +{ + PyThreadState *tstate = PyThreadState_GET(); + PyTracebackObject *oldtb = (PyTracebackObject *) tstate->curexc_traceback; + PyTracebackObject *tb = newtracebackobject(oldtb, frame); + if (tb == NULL) + return -1; + tstate->curexc_traceback = (PyObject *)tb; + Py_XDECREF(oldtb); + return 0; +} + +int +_Py_DisplaySourceLine(PyObject *f, const char *filename, int lineno, int indent) +{ + int err = 0; + FILE *xfp = NULL; + char linebuf[2000]; + int i; + char namebuf[MAXPATHLEN+1]; + + if (filename == NULL) + return -1; + /* This is needed by Emacs' compile command */ +#define FMT " File \"%.500s\", line %d, in %.500s\n" + xfp = fopen(filename, "r" PY_STDIOTEXTMODE); + if (xfp == NULL) { + /* Search tail of filename in sys.path before giving up */ + PyObject *path; + const char *tail = strrchr(filename, SEP); + if (tail == NULL) + tail = filename; + else + tail++; + path = PySys_GetObject("path"); + if (path != NULL && PyList_Check(path)) { + Py_ssize_t _npath = PyList_Size(path); + int npath = Py_SAFE_DOWNCAST(_npath, Py_ssize_t, int); + size_t taillen = strlen(tail); + for (i = 0; i < npath; i++) { + PyObject *v = PyList_GetItem(path, i); + if (v == NULL) { + PyErr_Clear(); + break; + } + if (PyString_Check(v)) { + size_t len; + len = PyString_GET_SIZE(v); + if (len + 1 + taillen >= MAXPATHLEN) + continue; /* Too long */ + strcpy(namebuf, PyString_AsString(v)); + if (strlen(namebuf) != len) + continue; /* v contains '\0' */ + if (len > 0 && namebuf[len-1] != SEP) + namebuf[len++] = SEP; + strcpy(namebuf+len, tail); + xfp = fopen(namebuf, "r" PY_STDIOTEXTMODE); + if (xfp != NULL) { + break; + } + } + } + } + } + + if (xfp == NULL) + return err; + if (err != 0) { + fclose(xfp); + return err; + } + + for (i = 0; i < lineno; i++) { + char* pLastChar = &linebuf[sizeof(linebuf)-2]; + do { + *pLastChar = '\0'; + if (Py_UniversalNewlineFgets(linebuf, sizeof linebuf, xfp, NULL) == NULL) + break; + /* fgets read *something*; if it didn't get as + far as pLastChar, it must have found a newline + or hit the end of the file; if pLastChar is \n, + it obviously found a newline; else we haven't + yet seen a newline, so must continue */ + } while (*pLastChar != '\0' && *pLastChar != '\n'); + } + if (i == lineno) { + char buf[11]; + char *p = linebuf; + while (*p == ' ' || *p == '\t' || *p == '\014') + p++; + + /* Write some spaces before the line */ + strcpy(buf, " "); + assert (strlen(buf) == 10); + while (indent > 0) { + if(indent < 10) + buf[indent] = '\0'; + err = PyFile_WriteString(buf, f); + if (err != 0) + break; + indent -= 10; + } + + if (err == 0) + err = PyFile_WriteString(p, f); + if (err == 0 && strchr(p, '\n') == NULL) + err = PyFile_WriteString("\n", f); + } + fclose(xfp); + return err; +} + +static int +tb_displayline(PyObject *f, const char *filename, int lineno, const char *name) +{ + int err = 0; + char linebuf[2000]; + + if (filename == NULL || name == NULL) + return -1; + /* This is needed by Emacs' compile command */ +#define FMT " File \"%.500s\", line %d, in %.500s\n" + PyOS_snprintf(linebuf, sizeof(linebuf), FMT, filename, lineno, name); + err = PyFile_WriteString(linebuf, f); + if (err != 0) + return err; + return _Py_DisplaySourceLine(f, filename, lineno, 4); +} + +static int +tb_printinternal(PyTracebackObject *tb, PyObject *f, long limit) +{ + int err = 0; + long depth = 0; + PyTracebackObject *tb1 = tb; + while (tb1 != NULL) { + depth++; + tb1 = tb1->tb_next; + } + while (tb != NULL && err == 0) { + if (depth <= limit) { + err = tb_displayline(f, + PyString_AsString( + tb->tb_frame->f_code->co_filename), + tb->tb_lineno, + PyString_AsString(tb->tb_frame->f_code->co_name)); + } + depth--; + tb = tb->tb_next; + if (err == 0) + err = PyErr_CheckSignals(); + } + return err; +} + +int +PyTraceBack_Print(PyObject *v, PyObject *f) +{ + int err; + PyObject *limitv; + long limit = 1000; + if (v == NULL) + return 0; + if (!PyTraceBack_Check(v)) { + PyErr_BadInternalCall(); + return -1; + } + limitv = PySys_GetObject("tracebacklimit"); + if (limitv && PyInt_Check(limitv)) { + limit = PyInt_AsLong(limitv); + if (limit <= 0) + return 0; + } + err = PyFile_WriteString("Traceback (most recent call last):\n", f); + if (!err) + err = tb_printinternal((PyTracebackObject *)v, f, limit); + return err; +} -- 2.39.2