Install safeguard against running PL/Python 2 and 3 in the same session
authorPeter Eisentraut <peter_e@gmx.net>
Thu, 8 Jul 2010 18:42:12 +0000 (18:42 +0000)
committerPeter Eisentraut <peter_e@gmx.net>
Thu, 8 Jul 2010 18:42:12 +0000 (18:42 +0000)
doc/src/sgml/plpython.sgml
src/pl/plpython/plpython.c

index 3f924e6cbf1af1f50b52ba24eeffca28aa44b933..c76012db402ef732490d7b37463ac4d611b4318f 100644 (file)
@@ -1,4 +1,4 @@
-<!-- $PostgreSQL: pgsql/doc/src/sgml/plpython.sgml,v 1.50 2010/07/06 21:37:31 petere Exp $ -->
+<!-- $PostgreSQL: pgsql/doc/src/sgml/plpython.sgml,v 1.51 2010/07/08 18:42:12 petere Exp $ -->
 
 <chapter id="plpython">
  <title>PL/Python - Python Procedural Language</title>
   </para>
 
   <para>
-   On most (possibly all) platforms, it is not possible to use
-   PL/Python based on Python 2 and PL/Python based on Python 3 in the
-   same session, because the symbols in the dynamic modules will
-   clash, which will result in crashes of the PostgreSQL server
-   process.  It is possible, however, to use both PL/Python variants
-   in the same database, from separate sessions.
+   It is not allowed to use PL/Python based on Python 2 and PL/Python
+   based on Python 3 in the same session, because the symbols in the
+   dynamic modules would clash, which could result in crashes of the
+   PostgreSQL server process.  There is a check that prevents mixing
+   Python major versions in a session, which will abort the session if
+   a mismatch is detected.  It is possible, however, to use both
+   PL/Python variants in the same database, from separate sessions.
   </para>
  </sect1>
 
index d63ba4a40cbd52172c5e37952e024dc00429f5b2..4a71b8bf5341c46aa1bf2413db04746413b36c9d 100644 (file)
@@ -1,7 +1,7 @@
 /**********************************************************************
  * plpython.c - python as a procedural language for PostgreSQL
  *
- *     $PostgreSQL: pgsql/src/pl/plpython/plpython.c,v 1.146 2010/07/06 19:19:01 momjian Exp $
+ *     $PostgreSQL: pgsql/src/pl/plpython/plpython.c,v 1.147 2010/07/08 18:42:12 petere Exp $
  *
  *********************************************************************
  */
@@ -3206,6 +3206,8 @@ PyInit_plpy(void)
 #endif
 
 
+static const int plpython_python_version = PY_MAJOR_VERSION;
+
 /*
  * _PG_init()                  - library load-time initialization
  *
@@ -3216,6 +3218,21 @@ _PG_init(void)
 {
        /* Be sure we do initialization only once (should be redundant now) */
        static bool inited = false;
+       const int **version_ptr;
+
+       /* Be sure we don't run Python 2 and 3 in the same session (might crash) */
+       version_ptr = (const int **) find_rendezvous_variable("plpython_python_version");
+       if (!(*version_ptr))
+               *version_ptr = &plpython_python_version;
+       else
+       {
+               if (**version_ptr != plpython_python_version)
+                       ereport(FATAL,
+                                       (errmsg("Python major version mismatch in session"),
+                                        errdetail("This session has previously used Python major version %d, and it is now attempting to use Python major version %d.",
+                                                          **version_ptr, plpython_python_version),
+                                        errhint("Start a new session to use a different Python major version.")));
+       }
 
        if (inited)
                return;