Revision: 547
          http://rpy.svn.sourceforge.net/rpy/?rev=547&view=rev
Author:   lgautier
Date:     2008-06-07 00:01:08 -0700 (Sat, 07 Jun 2008)

Log Message:
-----------
rinterface:
- replaced call to Rf_initEmbeddedR with its content (easier to tweak)
- dealloc for Sexp split into two functions: clear and dealloc
- PyObject_New and PyObject_Del are out (causing segfault when 
subclassing)
- init for Sexp moved around (and early type declaration with 
staticforward)
- trivial fixes in the init for VectorSexp, ClosureSexp, EnvironmentSexp
- restored --quiet as a default starting option

Modified Paths:
--------------
    branches/rpy_nextgen/rpy/rinterface/rinterface.c

Modified: branches/rpy_nextgen/rpy/rinterface/rinterface.c
===================================================================
--- branches/rpy_nextgen/rpy/rinterface/rinterface.c    2008-06-05 18:07:04 UTC 
(rev 546)
+++ branches/rpy_nextgen/rpy/rinterface/rinterface.c    2008-06-07 07:01:08 UTC 
(rev 547)
@@ -71,7 +71,7 @@
 #include "array.h"
 #include "r_utils.h"
 
-#define RPY_VERBOSE
+//#define RPY_VERBOSE
 
 /* Back-compatibility with Python 2.4 */
 #if (PY_VERSION_HEX < 0x02050000)
@@ -230,14 +230,11 @@
   }
 
 
-  int status = Rf_initEmbeddedR(n_args, options);
-  /* FIXME: setup_Rmainloop causes ipython to crash 
-   *(bug in ipython ?)
-   */
-/*   int status = 1; */
-/*   Rf_initialize_R(n_args, options); */
-/*   R_Interactive = TRUE;  Rf_initialize_R set this based on isatty */
-/*   setup_Rmainloop(); */
+  /* int status = Rf_initEmbeddedR(n_args, options);*/
+  int status = 1;
+  Rf_initialize_R(n_args, options);
+  R_Interactive = TRUE;
+  setup_Rmainloop();
 
   Py_XDECREF(embeddedR_isInitialized);
   embeddedR_isInitialized = Py_True;
@@ -326,18 +323,15 @@
  * Access to R objects through Python objects
  */
 
-
 static void
-Sexp_dealloc(PySexpObject *self)
+Sexp_clear(PySexpObject *self)
 {
   RPY_DECREF(self);
-  
 #ifdef RPY_VERBOSE
   printf("Python:%p / R:%p -- sexp count is %i\n", 
         self, RPY_SEXP(self), RPY_COUNT(self));
 #endif
 
-  printf("dealloc-count--->\n");
   if ((RPY_COUNT(self) == 0) && RPY_SEXP(self)) {
 #ifdef RPY_VERBOSE
     printf("freeing SEXP resources...\n");
@@ -352,12 +346,20 @@
     printf("done.\n");
 #endif 
   }
-  printf("dealloc-del--->\n");
-  PyObject_Del(self);
-  printf("dealloc-ok--->\n");
+
 }
 
 
+static void
+Sexp_dealloc(PySexpObject *self)
+{
+  Sexp_clear(self);
+  self->ob_type->tp_free((PyObject*)self);
+
+  //PyObject_Del(self);
+}
+
+
 static PyObject*
 Sexp_repr(PyObject *self)
 {
@@ -429,79 +431,9 @@
 };
 
 
+staticforward PyTypeObject Sexp_Type;
 
 static PyObject*
-Sexp_new(PyTypeObject *type, PyObject *args, PyObject *kwds);
-
-static int
-Sexp_init(PyObject *self, PyObject *args, PyObject *kwds);
-
-/*
- * Generic Sexp_Type. It represents SEXP objects at large.
- */
-static PyTypeObject Sexp_Type = {
-       /* The ob_type field must be initialized in the module init function
-        * to be portable to Windows without using C++. */
-       PyObject_HEAD_INIT(NULL)
-       0,                      /*ob_size*/
-       "rinterface.Sexp",      /*tp_name*/
-       sizeof(PySexpObject),   /*tp_basicsize*/
-       0,                      /*tp_itemsize*/
-       /* methods */
-       (destructor)Sexp_dealloc, /*tp_dealloc*/
-       0,                      /*tp_print*/
-       0,                      /*tp_getattr*/
-       0,                      /*tp_setattr*/
-       0,                      /*tp_compare*/
-       Sexp_repr,              /*tp_repr*/
-       0,                      /*tp_as_number*/
-       0,                      /*tp_as_sequence*/
-       0,                      /*tp_as_mapping*/
-       0,                      /*tp_hash*/
-       0,                      /*tp_call*/
-        0,//Sexp_str,               /*tp_str*/
-        0,                      /*tp_getattro*/
-        0,                      /*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*/
-        Sexp_methods,           /*tp_methods*/
-        0,                      /*tp_members*/
-        0,//Sexp_getset,            /*tp_getset*/
-        0,                      /*tp_base*/
-        0,                      /*tp_dict*/
-        0,                      /*tp_descr_get*/
-        0,                      /*tp_descr_set*/
-        0,                      /*tp_dictoffset*/
-        (initproc)Sexp_init,                      /*tp_init*/
-        0,                      /*tp_alloc*/
-        Sexp_new,               /*tp_new*/
-        0,                      /*tp_free*/
-        0,                      /*tp_is_gc*/
-};
-
-
-/* static PyObject* */
-/* Sexp_new(PyTypeObject *type, PyObject *args) */
-/* { */
-/*   PyObject object, res; */
-/*   if (!PyArg_ParseTuple(args, "O:new", */
-/*                     &object)) */
-/*     PyErr_Format(PyExc_ValueError, "Can only instanciate from 
PySexpObject"); */
-/*   return NULL; */
-/*   res = (PySexpObject *)_PyObject_New(&Sexp_Type); */
-/*   if (!res) */
-/*     PyErr_NoMemory(); */
-/*   res->sexp = sexp; */
-/*   return res; */
-/* } */
-static PyObject*
 Sexp_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
 {
 
@@ -509,21 +441,23 @@
   //unsigned short int rpy_only = 1;
 
   #ifdef RPY_VERBOSE
-  printf("new object @...\n");
+  printf("new '%s' object @...\n", type->tp_name);
   #endif 
 
-  //self = (PySexpObject *)_PyObject_New(&type);
+  //self = (PySexpObject *)PyObject_New(PySexpObject, type);
   self = (PySexpObject *)type->tp_alloc(type, 0);
   #ifdef RPY_VERBOSE
-  printf("  Python:%p / R:%p  ...\n", self, R_NilValue);
+  printf("  Python:%p / R:%p (R_NilValue) ...\n", self, R_NilValue);
   #endif 
 
   if (! self)
     PyErr_NoMemory();
 
   self->sObj = (SexpObject *)calloc(1, sizeof(SexpObject));
-  if (! self->sObj)
+  if (! self->sObj) {
+    Py_DECREF(self);
     PyErr_NoMemory();
+  }
 
   RPY_COUNT(self) = 1;
   RPY_SEXP(self) = R_NilValue;
@@ -537,7 +471,6 @@
 
 }
 
-
 static int
 Sexp_init(PyObject *self, PyObject *args, PyObject *kwds)
 {
@@ -547,8 +480,13 @@
 #endif 
 
   PyObject *sourceObject;
+
+  Py_INCREF(Py_True);
   PyObject *copy = Py_True;
-  Py_INCREF(Py_True);
+
+  SexpObject *tmpSexpObject;
+
+
   static char *kwlist[] = {"sexp", "copy", NULL};
   //FIXME: handle the copy argument
 
@@ -569,15 +507,13 @@
   }
 
   if (PyObject_IsTrue(copy)) {
-    //SEXP oldSexp;
-    //oldSexp = RPY_SEXP((PySexpObject *)sourceObject);
-    //RPY_SEXP(self) = oldSexp;
-    free(((PySexpObject *)self)->sObj);
+    tmpSexpObject = ((PySexpObject *)self)->sObj;
     ((PySexpObject *)self)->sObj = ((PySexpObject *)sourceObject)->sObj;
+    free(tmpSexpObject);
     RPY_INCREF((PySexpObject *)self);
 #ifdef RPY_VERBOSE
-    printf("%p: sexp count is increased to %i.\n", 
-          (PySexpObject *)self, RPY_COUNT((PySexpObject *)self));
+    printf("Python: %p / R: %p - sexp count is now %i.\n", 
+          (PySexpObject *)self, RPY_SEXP((PySexpObject *)self), 
RPY_COUNT((PySexpObject *)self));
 #endif 
 
   } else {
@@ -588,7 +524,7 @@
   Py_DECREF(Py_True);
 
 #ifdef RPY_VERBOSE
-  printf("done\n.");
+  printf("done.\n");
 #endif 
 
 
@@ -596,7 +532,75 @@
 }
 
 
+/*
+ * Generic Sexp_Type. It represents SEXP objects at large.
+ */
+static PyTypeObject Sexp_Type = {
+       /* The ob_type field must be initialized in the module init function
+        * to be portable to Windows without using C++. */
+       PyObject_HEAD_INIT(NULL)
+       0,                      /*ob_size*/
+       "rinterface.Sexp",      /*tp_name*/
+       sizeof(PySexpObject),   /*tp_basicsize*/
+       0,                      /*tp_itemsize*/
+       /* methods */
+       (destructor)Sexp_dealloc, /*tp_dealloc*/
+       0,                      /*tp_print*/
+       0,                      /*tp_getattr*/
+       0,                      /*tp_setattr*/
+       0,                      /*tp_compare*/
+       Sexp_repr,              /*tp_repr*/
+       0,                      /*tp_as_number*/
+       0,                      /*tp_as_sequence*/
+       0,                      /*tp_as_mapping*/
+       0,                      /*tp_hash*/
+       0,                      /*tp_call*/
+        0,//Sexp_str,               /*tp_str*/
+        0,                      /*tp_getattro*/
+        0,                      /*tp_setattro*/
+        0,                      /*tp_as_buffer*/
+        Py_TPFLAGS_DEFAULT|Py_TPFLAGS_BASETYPE,     /*tp_flags*/
+        0,                      /*tp_doc*/
+        0,                      /*tp_traverse*/
+        Sexp_clear,                      /*tp_clear*/
+        0,                      /*tp_richcompare*/
+        0,                      /*tp_weaklistoffset*/
+        0,                      /*tp_iter*/
+        0,                      /*tp_iternext*/
+        Sexp_methods,           /*tp_methods*/
+        0,                      /*tp_members*/
+        0,//Sexp_getset,            /*tp_getset*/
+        0,                      /*tp_base*/
+        0,                      /*tp_dict*/
+        0,                      /*tp_descr_get*/
+        0,                      /*tp_descr_set*/
+        0,                      /*tp_dictoffset*/
+        (initproc)Sexp_init,                      /*tp_init*/
+        0,                      /*tp_alloc*/
+        Sexp_new,               /*tp_new*/
+        0,                      /*tp_free*/
+        0,                      /*tp_is_gc*/
+};
 
+
+/* static PyObject* */
+/* Sexp_new(PyTypeObject *type, PyObject *args) */
+/* { */
+/*   PyObject object, res; */
+/*   if (!PyArg_ParseTuple(args, "O:new", */
+/*                     &object)) */
+/*     PyErr_Format(PyExc_ValueError, "Can only instanciate from 
PySexpObject"); */
+/*   return NULL; */
+/*   res = (PySexpObject *)_PyObject_New(&Sexp_Type); */
+/*   if (!res) */
+/*     PyErr_NoMemory(); */
+/*   res->sexp = sexp; */
+/*   return res; */
+/* } */
+
+
+
+
 /*
  * Closure-type Sexp.
  */
@@ -822,7 +826,7 @@
 ");
 
 static int
-ClosureSexp_init(PySexpObject *self, PyObject *args, PyObject *kwds);
+ClosureSexp_init(PyObject *self, PyObject *args, PyObject *kwds);
 
 
 static PyTypeObject ClosureSexp_Type = {
@@ -874,7 +878,7 @@
 
 
 static int
-ClosureSexp_init(PySexpObject *self, PyObject *args, PyObject *kwds)
+ClosureSexp_init(PyObject *self, PyObject *args, PyObject *kwds)
 {
   PyObject *object;
   PyObject *copy;
@@ -889,7 +893,7 @@
   if (PyObject_IsInstance(object, 
                          (PyObject*)&ClosureSexp_Type)) {
     //call parent's constructor
-    if (Sexp_init(self, args, kwds) == -1) {
+    if (Sexp_init(self, args, NULL) == -1) {
       PyErr_Format(PyExc_RuntimeError, "Error initializing instance.");
       return -1;
     }
@@ -1093,7 +1097,7 @@
             " is done at zero.");
 
 static int
-VectorSexp_init(PySexpObject *self, PyObject *args, PyObject *kwds);
+VectorSexp_init(SexpObject *self, PyObject *args, PyObject *kwds);
 
 static PyTypeObject VectorSexp_Type = {
        /* The ob_type field must be initialized in the module init function
@@ -1144,7 +1148,7 @@
  
 
 static int
-VectorSexp_init(PySexpObject *self, PyObject *args, PyObject *kwds)
+VectorSexp_init(SexpObject *self, PyObject *args, PyObject *kwds)
 {
 #ifdef RPY_VERBOSE
   printf("%p: VectorSexp initializing...\n", self);
@@ -1165,31 +1169,30 @@
     return -1;
   }
 
-  if ((sexptype < 0) || (sexptype > maxValidSexpType) || 
-      (! validSexpType[sexptype])) {
-    PyErr_Format(PyExc_ValueError, "Invalid SEXP type.");
-    return -1;
-  }
   if (PyObject_IsInstance(object, 
                          (PyObject*)&VectorSexp_Type)) {
-
     //call parent's constructor
     if (Sexp_init(self, args, NULL) == -1) {
       //PyErr_Format(PyExc_RuntimeError, "Error initializing instance.");
       return -1;
     }
-  } else {
-    if (sexptype == -1) {
-      //FIXME: implemement automagic type
-      //(RPy has something).
-
-      PyErr_Format(PyExc_ValueError, "Missing type.");
+  } else if (PySequence_Check(object)) {
+    if ((sexptype < 0) || (sexptype > maxValidSexpType) || 
+       (! validSexpType[sexptype])) {
+      PyErr_Format(PyExc_ValueError, "Invalid SEXP type.");
       return -1;
     }
-    RPY_SEXP(self) = newSEXP(object, sexptype);
+    //FIXME: implemement automagic type ?
+    //(RPy has something)... or leave it to extensions ?
+
+    RPY_SEXP((PySexpObject *)self) = newSEXP(object, sexptype);
+  } else {
+    PyErr_Format(PyExc_ValueError, "Invalid sexpvector.");
+    return -1;
   }
+
 #ifdef RPY_VERBOSE
-  printf("done.\n");
+  printf("done (VectorSexp_init).\n");
 #endif 
   
   return 0;
@@ -1445,7 +1448,7 @@
   if (PyObject_IsInstance(object, 
                          (PyObject*)&EnvironmentSexp_Type)) {
     //call parent's constructor
-    if (Sexp_init(self, args, kwds) == -1) {
+    if (Sexp_init(self, args, NULL) == -1) {
       PyErr_Format(PyExc_RuntimeError, "Error initializing instance.");
       return -1;
     }
@@ -1578,9 +1581,15 @@
 {
   SEXP sexp;
   PyObject *seq_object, *item; 
+
+#ifdef RPY_VERBOSE
+  printf("  new SEXP for Python:%p.\n", object);
+#endif 
+
   seq_object = PySequence_Fast(object, 
                               "Cannot create R object from non-sequence Python 
object.");
   //FIXME: Isn't the call above supposed to fire an Exception ?
+
   if (! seq_object) {
     return NULL;
   }
@@ -1589,7 +1598,6 @@
   PROTECT(sexp = allocVector(rType, length));
 
   int i;
-  
   switch(rType) {
   case REALSXP:
     for (i = 0; i < length; ++i) {
@@ -1682,6 +1690,10 @@
     sexp = NULL;
   }
   UNPROTECT(1);
+#ifdef RPY_VERBOSE
+  printf("  new SEXP for Python:%p is %p.\n", object, sexp);
+#endif 
+
   return sexp;
 }
 
@@ -1904,7 +1916,7 @@
                );
   PYASSERT_ZERO(
                PyList_SetItem(initOptions, 1, 
-                              PyString_FromString("--verbose"))
+                              PyString_FromString("--quiet"))
                );
   PYASSERT_ZERO(
                PyList_SetItem(initOptions, 2, 


This was sent by the SourceForge.net collaborative development platform, the 
world's largest Open Source development site.

-------------------------------------------------------------------------
Check out the new SourceForge.net Marketplace.
It's the best place to buy or sell services for
just about anything Open Source.
http://sourceforge.net/services/buy/index.php
_______________________________________________
rpy-list mailing list
rpy-list@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/rpy-list

Reply via email to