[ Web Proxy ]
URL:
Viewing: https://raw.githubusercontent.com/patstew/pythonnet/python3/src/runtime/interop.cs [Back]  [Original]

// ==========================================================================
// This software is subject to the provisions of the Zope Public License,
// Version 2.0 (ZPL).  A copy of the ZPL should accompany this distribution.
// THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
// WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
// WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
// FOR A PARTICULAR PURPOSE.
// ==========================================================================

using System;
using System.Collections;
using System.Collections.Specialized;
using System.Runtime.InteropServices;
using System.Reflection;
using System.Text;

namespace Python.Runtime {

    //=======================================================================
    // This file defines objects to support binary interop with the Python
    // runtime. Generally, the definitions here need to be kept up to date
    // when moving to new Python versions.
    //=======================================================================

    [Serializable()]
    [AttributeUsage(AttributeTargets.All)]
    public class DocStringAttribute : Attribute {
        public DocStringAttribute(string docStr) {
			DocString = docStr;
		}
		public string DocString {
			get { return docStr; }
			set { docStr = value; }
		}
		private string docStr;
    }
	
    [Serializable()]
    [AttributeUsage(AttributeTargets.Method | AttributeTargets.Delegate)]
    internal class PythonMethodAttribute : Attribute {
        public PythonMethodAttribute() {}
    }

    [Serializable()]
    [AttributeUsage(AttributeTargets.Method | AttributeTargets.Delegate)]
    internal class ModuleFunctionAttribute : Attribute {
        public ModuleFunctionAttribute() {}
    }

    [Serializable()]
    [AttributeUsage(AttributeTargets.Method | AttributeTargets.Delegate)]
    internal class ForbidPythonThreadsAttribute : Attribute {
        public ForbidPythonThreadsAttribute() { }
    }


    [Serializable()]
    [AttributeUsage(AttributeTargets.Property)]
    internal class ModulePropertyAttribute : Attribute {
        public ModulePropertyAttribute() {}
    }


    [StructLayout(LayoutKind.Sequential, CharSet=CharSet.Ansi)]
    internal class ObjectOffset {

        static ObjectOffset() {
            int size = IntPtr.Size;
            int n = 0; // Py_TRACE_REFS add two pointers to PyObject_HEAD 
#if (Py_DEBUG)
            _ob_next = 0;
            _ob_prev = 1 * size;
            n = 2;
#endif 
            ob_refcnt = (n+0) * size;
            ob_type = (n+1) * size;
            ob_dict = (n+2) * size;
            ob_data = (n+3) * size;
        }

        public static int magic(IntPtr ob) {
#if (PYTHON32 || PYTHON33 || PYTHON34)
            if ((Runtime.PyObject_TypeCheck(ob, Exceptions.BaseException) ||
                (Runtime.PyType_Check(ob) && Runtime.PyType_IsSubtype(ob, Exceptions.BaseException))))
            {
                return ExceptionOffset.ob_data;
            }
#endif
            return ob_data;
        }

        public static int DictOffset(IntPtr ob)
        {
#if (PYTHON32 || PYTHON33 || PYTHON34)
            if ((Runtime.PyObject_TypeCheck(ob, Exceptions.BaseException) ||
                (Runtime.PyType_Check(ob) && Runtime.PyType_IsSubtype(ob, Exceptions.BaseException))))
            {
                return ExceptionOffset.ob_dict;
            }
#endif
            return ob_dict;
        }

        public static int Size(IntPtr ob) {
#if (PYTHON32 || PYTHON33 || PYTHON34)
            if ((Runtime.PyObject_TypeCheck(ob, Exceptions.BaseException) ||
                (Runtime.PyType_Check(ob) && Runtime.PyType_IsSubtype(ob, Exceptions.BaseException))))
            {
                return ExceptionOffset.Size();
            }
#endif
#if (Py_DEBUG)
            return 6 * IntPtr.Size;
#else
            return 4 * IntPtr.Size;
#endif
        }

#if (Py_DEBUG)
        public static int _ob_next;
        public static int _ob_prev;
#endif
        public static int ob_refcnt;
        public static int ob_type;
        private static int ob_dict;
        private static int ob_data;
    }

#if (PYTHON32 || PYTHON33 || PYTHON34)
    [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)]
    internal class ExceptionOffset
    {
        static ExceptionOffset()
        {
            Type type = typeof(ExceptionOffset);
            FieldInfo[] fi = type.GetFields();
            int size = IntPtr.Size;
            for (int i = 0; i < fi.Length; i++)
            {
                fi[i].SetValue(null, (i * size) + ObjectOffset.ob_type + size);
            }
        }

        public static int Size()
        {
            return ob_data + IntPtr.Size;
        }

        // PyException_HEAD
        // (start after PyObject_HEAD)
        public static int dict = 0;
        public static int args = 0;
        public static int traceback = 0;
        public static int context = 0;
        public static int cause = 0;

        // extra c# data
        public static int ob_dict;
        public static int ob_data;
    }
#endif

    [StructLayout(LayoutKind.Sequential, CharSet=CharSet.Ansi)]
    internal class TypeOffset {

        static TypeOffset() {
            Type type = typeof(TypeOffset);
            FieldInfo[] fi = type.GetFields();
            int size = IntPtr.Size;
            for (int i = 0; i < fi.Length; i++) {
                fi[i].SetValue(null, i * size);
            }
        }

        public static int magic() {
            return ob_size;
        }
        
/* The *real* layout of a type object when allocated on the heap */
//typedef struct _heaptypeobject {
#if (Py_DEBUG)  // #ifdef Py_TRACE_REFS
/* _PyObject_HEAD_EXTRA defines pointers to support a doubly-linked list of all live heap objects. */
        public static int _ob_next = 0;
        public static int _ob_prev = 0;
#endif
// PyObject_VAR_HEAD {
//     PyObject_HEAD {
        public static int ob_refcnt = 0;
        public static int ob_type = 0;
    // }
        public static int ob_size = 0;      /* Number of items in _VAR_iable part */
// }
        public static int tp_name = 0;      /* For printing, in format "." */
        public static int tp_basicsize = 0; /* For allocation */
        public static int tp_itemsize = 0;

        /* Methods to implement standard operations */
        public static int tp_dealloc = 0;
        public static int tp_print = 0;
        public static int tp_getattr = 0;
        public static int tp_setattr = 0;
        public static int tp_compare = 0; /* tp_reserved in Python 3 */
        public static int tp_repr = 0;

        /* Method suites for standard classes */
        public static int tp_as_number = 0;
        public static int tp_as_sequence = 0;
        public static int tp_as_mapping = 0;

        /* More standard operations (here for binary compatibility) */
        public static int tp_hash = 0;
        public static int tp_call = 0;
        public static int tp_str = 0;
        public static int tp_getattro = 0;
        public static int tp_setattro = 0;

        /* Functions to access object as input/output buffer */
        public static int tp_as_buffer = 0;

        /* Flags to define presence of optional/expanded features */
        public static int tp_flags = 0;

        public static int tp_doc = 0; /* Documentation string */

        /* Assigned meaning in release 2.0 */
        /* call function for all accessible objects */
        public static int tp_traverse = 0;
        /* delete references to contained objects */
        public static int tp_clear = 0;

        /* Assigned meaning in release 2.1 */
        /* rich comparisons */
        public static int tp_richcompare = 0;
        /* weak reference enabler */
        public static int tp_weaklistoffset = 0;

        /* Added in release 2.2 */
        /* Iterators */
        public static int tp_iter = 0;
        public static int tp_iternext = 0;
        /* Attribute descriptor and subclassing stuff */
        public static int tp_methods = 0;
        public static int tp_members = 0;
        public static int tp_getset = 0;
        public static int tp_base = 0;
        public static int tp_dict = 0;
        public static int tp_descr_get = 0;
        public static int tp_descr_set = 0;
        public static int tp_dictoffset = 0;
        public static int tp_init = 0;
        public static int tp_alloc = 0;
        public static int tp_new = 0;
        public static int tp_free = 0;      /* Low-level free-memory routine */
        public static int tp_is_gc = 0;     /* For PyObject_IS_GC */
        public static int tp_bases = 0;
        public static int tp_mro = 0;       /* method resolution order */
        public static int tp_cache = 0;
        public static int tp_subclasses = 0;
        public static int tp_weaklist = 0;
        public static int tp_del = 0;
#if (PYTHON26 || PYTHON27 || PYTHON32 || PYTHON33 || PYTHON34)
        /* Type attribute cache version tag. Added in version 2.6 */
	    public static int tp_version_tag;
#endif
#if (PYTHON34)
        public static int tp_finalize = 0;
#endif
        // COUNT_ALLOCS adds some more stuff to PyTypeObject 
#if (Py_COUNT_ALLOCS)
	/* these must be last and never explicitly initialized */
        public static int tp_allocs = 0;
        public static int tp_frees = 0;
        public static int tp_maxalloc = 0;
        public static int tp_prev = 0;
        public static int tp_next = 0;
#endif
//} PyTypeObject;

//typedef struct {
        public static int nb_add = 0;
        public static int nb_subtract = 0;
        public static int nb_multiply = 0;
#if !(PYTHON32 || PYTHON33 || PYTHON34)
        public static int nb_divide = 0;
#endif
        public static int nb_remainder = 0;
        public static int nb_divmod = 0;
        public static int nb_power = 0;
        public static int nb_negative = 0;
        public static int nb_positive = 0;
        public static int nb_absolute = 0;
        public static int nb_nonzero = 0;
        public static int nb_invert = 0;
        public static int nb_lshift = 0;
        public static int nb_rshift = 0;
        public static int nb_and = 0;
        public static int nb_xor = 0;
        public static int nb_or = 0;
#if !(PYTHON32 || PYTHON33 || PYTHON34)
        public static int nb_coerce = 0;
#endif
        public static int nb_int = 0;
        public static int nb_long = 0;
        public static int nb_float = 0;
#if !(PYTHON32 || PYTHON33 || PYTHON34)
        public static int nb_oct = 0;
        public static int nb_hex = 0;
#endif
        /* Added in release 2.0 */
        public static int nb_inplace_add = 0;
        public static int nb_inplace_subtract = 0;
        public static int nb_inplace_multiply = 0;
#if !(PYTHON32 || PYTHON33 || PYTHON34)
        public static int nb_inplace_divide = 0;
#endif
        public static int nb_inplace_remainder = 0;
        public static int nb_inplace_power = 0;
        public static int nb_inplace_lshift = 0;
        public static int nb_inplace_rshift = 0;
        public static int nb_inplace_and = 0;
        public static int nb_inplace_xor = 0;
        public static int nb_inplace_or = 0;
        /* Added in release 2.2 */
        /* The following require the Py_TPFLAGS_HAVE_CLASS flag */
        public static int nb_floor_divide = 0;
        public static int nb_true_divide = 0;
        public static int nb_inplace_floor_divide = 0;
        public static int nb_inplace_true_divide = 0;
#if (PYTHON25 || PYTHON26 || PYTHON27 || PYTHON32 || PYTHON33 || PYTHON34)
        /* Added in release 2.5 */
        public static int nb_index = 0;
#endif
        //} PyNumberMethods;
//typedef struct {
        public static int mp_length = 0;
        public static int mp_subscript = 0;
        public static int mp_ass_subscript = 0;
//} PyMappingMethods;
//typedef struct {
        public static int sq_length = 0;
        public static int sq_concat = 0;
        public static int sq_repeat = 0;
        public static int sq_item = 0;
        public static int sq_slice = 0;
        public static int sq_ass_item = 0;
        public static int sq_ass_slice = 0;
        public static int sq_contains = 0;
        /* Added in release 2.0 */
        public static int sq_inplace_concat = 0;
        public static int sq_inplace_repeat = 0;
//} PySequenceMethods;
//typedef struct {
#if !(PYTHON32 || PYTHON33 || PYTHON34)
        public static int bf_getreadbuffer = 0;
        public static int bf_getwritebuffer = 0;
        public static int bf_getsegcount = 0;
        public static int bf_getcharbuffer = 0;
#endif
#if (PYTHON26 || PYTHON27 || PYTHON32 || PYTHON33 || PYTHON34)
        // This addition is not actually noted in the 2.6.5 object.h
	    public static int bf_getbuffer = 0;
	    public static int bf_releasebuffer = 0;
//} PyBufferProcs;
#endif
        //PyObject *ht_name, *ht_slots;
        public static int name = 0;
        public static int slots = 0;

#if (PYTHON33 || PYTHON34)
        public static int qualname = 0;
        public static int cached_keys;
#endif

        /* here are optional user slots, followed by the members. */
        public static int members = 0;
    }

#if (PYTHON32 || PYTHON33 || PYTHON34)
    [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)]
    internal class BytesOffset
    {
        static BytesOffset()
        {
            Type type = typeof(BytesOffset);
            FieldInfo[] fi = type.GetFields();
            int size = IntPtr.Size;
            for (int i = 0; i < fi.Length; i++)
            {
                fi[i].SetValue(null, i * size);
            }
        }

        /* The *real* layout of a type object when allocated on the heap */
        //typedef struct _heaptypeobject {
#if (Py_DEBUG)  // #ifdef Py_TRACE_REFS
/* _PyObject_HEAD_EXTRA defines pointers to support a doubly-linked list of all live heap objects. */
        public static int _ob_next = 0;
        public static int _ob_prev = 0;
#endif
        // PyObject_VAR_HEAD {
        //     PyObject_HEAD {
        public static int ob_refcnt = 0;
        public static int ob_type = 0;
        // }
        public static int ob_size = 0;      /* Number of items in _VAR_iable part */
        // }
        public static int ob_shash = 0;
        public static int ob_sval = 0; /* start of data */

        /* 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.
         */
        //} PyBytesObject;
    }

    [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi)]
    internal class ModuleDefOffset
    {
        static ModuleDefOffset()
        {
            Type type = typeof(ModuleDefOffset);
            FieldInfo[] fi = type.GetFields();
            int size = IntPtr.Size;
            for (int i = 0; i < fi.Length; i++)
            {
                fi[i].SetValue(null, (i * size) + TypeOffset.ob_size);
            }
        }

        public static IntPtr AllocModuleDef(string modulename) {
            byte[] ascii = Encoding.ASCII.GetBytes(modulename);
            int size = name + ascii.Length + 1;
            IntPtr ptr = Marshal.AllocHGlobal(size);
            for (int i = 0; i 

Web Proxy Viewer  |  New URL  |  Original Page