PSARC 2014/151 Python 3.4
authorJohn Beck <John.Beck@Oracle.COM>
Mon, 19 May 2014 07:37:20 -0700
changeset 1907 446472de62e9
parent 1906 06b8097543cd
child 1908 702ae3973fcc
PSARC 2014/151 Python 3.4 15819724 SUNBT7202228 python 3.4 18756157 upgrade setuptools to 0.9.6
components/antlr/antlr.p5m
components/graphviz/graphviz-python-26.p5m
components/graphviz/graphviz-python-27.p5m
components/logilab-astng/Makefile
components/logilab-common/Makefile
components/meld/meld.p5m
components/mercurial/Makefile
components/mercurial/mercurial-GENFRAG.p5m
components/pylint/pylint-26.p5m
components/pylint/pylint-27.p5m
components/pylint/pylint-GENFRAG.p5m
components/pylint/pylint-PYVER.p5m
components/pylint/pylint.p5m
components/pylint/resolve.deps
components/python/alembic/alembic-PYVER.p5m
components/python/alembic/resolve.deps
components/python/amqp/resolve.deps
components/python/anyjson/resolve.deps
components/python/babel/resolve.deps
components/python/beautifulsoup4/resolve.deps
components/python/boto/Makefile
components/python/cffi/cffi-PYVER.p5m
components/python/cffi/resolve.deps
components/python/cheetah/Makefile
components/python/cherrypy/Makefile
components/python/cinderclient/resolve.deps
components/python/cliff/resolve.deps
components/python/cmd2/cmd2-PYVER.p5m
components/python/cmd2/resolve.deps
components/python/cov-core/Makefile
components/python/coverage/Makefile
components/python/cssutils/Makefile
components/python/d2to1/resolve.deps
components/python/decorator/resolve.deps
components/python/django-appconf/Makefile
components/python/django/Makefile
components/python/django_compressor/Makefile
components/python/django_openstack_auth/Makefile
components/python/eventlet/Makefile
components/python/filechunkio/patches/01-python3.patch
components/python/filechunkio/resolve.deps
components/python/formencode/Makefile
components/python/glanceclient/resolve.deps
components/python/greenlet/Makefile
components/python/httplib2/Makefile
components/python/imaging/Makefile
components/python/imaging/imaging-PYVER.p5m
components/python/ipython/Makefile
components/python/iso8601/resolve.deps
components/python/jsonpatch/Makefile
components/python/jsonpatch/resolve.deps
components/python/jsonpointer/Makefile
components/python/jsonpointer/resolve.deps
components/python/jsonrpclib/Makefile
components/python/jsonschema/resolve.deps
components/python/keystoneclient/resolve.deps
components/python/kombu/patches/01.python3-reqs.patch
components/python/kombu/resolve.deps
components/python/ldtp/Makefile
components/python/lesscpy/Makefile
components/python/lesscpy/resolve.deps
components/python/librabbitmq/Makefile
components/python/lockfile/resolve.deps
components/python/m2crypto/Makefile
components/python/mako/resolve.deps
components/python/markdown/resolve.deps
components/python/markupsafe/markupsafe-PYVER.p5m
components/python/markupsafe/resolve.deps
components/python/mock/Makefile
components/python/mysql/Makefile
components/python/netaddr/Makefile
components/python/netifaces/Makefile
components/python/neutronclient/Makefile
components/python/nose-cover3/resolve.deps
components/python/nose/nose-PYVER.p5m
components/python/nose/resolve.deps
components/python/novaclient/resolve.deps
components/python/oslo.config/resolve.deps
components/python/passlib/resolve.deps
components/python/paste.deploy/resolve.deps
components/python/paste/Makefile
components/python/pbr/resolve.deps
components/python/pep8/pep8-GENFRAG.p5m
components/python/pep8/pep8-PYVER.p5m
components/python/pep8/resolve.deps
components/python/pip/resolve.deps
components/python/ply/Makefile
components/python/prettytable/prettytable-PYVER.p5m
components/python/prettytable/resolve.deps
components/python/py/resolve.deps
components/python/pyasn1-modules/resolve.deps
components/python/pyasn1/resolve.deps
components/python/pybonjour/patches/pybonjour-python3.patch
components/python/pybonjour/resolve.deps
components/python/pycountry/resolve.deps
components/python/pycparser/resolve.deps
components/python/pycups/Makefile
components/python/pycurl/Makefile
components/python/pydns/Makefile
components/python/pyflakes/resolve.deps
components/python/pygments/resolve.deps
components/python/pylxml/pylxml-PYVER.p5m
components/python/pylxml/resolve.deps
components/python/pyopenssl/pyopenssl-PYVER.p5m
components/python/pyopenssl/resolve.deps
components/python/pyparsing/pyparsing-PYVER.p5m
components/python/pyparsing/resolve.deps
components/python/pyrabbit/Makefile
components/python/pytest-capturelog/resolve.deps
components/python/pytest-codecheckers/resolve.deps
components/python/pytest-cov/Makefile
components/python/pytest/pytest-PYVER.p5m
components/python/pytest/resolve.deps
components/python/python-ldap/Makefile
components/python/python26/python-26.p5m
components/python/python27/python-27.p5m
components/python/python34/Makefile
components/python/python34/patches/00-dtrace.patch
components/python/python34/patches/01-bits.patch
components/python/python34/patches/02-ext-stdio.patch
components/python/python34/patches/03-setup.patch
components/python/python34/patches/04-vendor-packages.patch
components/python/python34/patches/05-studio-profile.patch
components/python/python34/patches/06-solaris-64-bit.patch
components/python/python34/patches/07-ucred.patch
components/python/python34/patches/08-dlpi.patch
components/python/python34/patches/09-encoding-alias.patch
components/python/python34/patches/10-rbac.patch
components/python/python34/patches/11-closerange.patch
components/python/python34/patches/12-py_db.patch
components/python/python34/patches/13-get_wch.patch
components/python/python34/patches/14-ossaudiodev.patch
components/python/python34/patches/15-include.patch
components/python/python34/patches/16-pic-compile.patch
components/python/python34/python-34.p5m
components/python/python34/python34.license
components/python/python34/resolve.deps
components/python/python34/tkinter-34.p5m
components/python/pytz/pytz-PYVER.p5m
components/python/pytz/resolve.deps
components/python/quantumclient/resolve.deps
components/python/repoze.lru/resolve.deps
components/python/requests/patches/python3.patch
components/python/requests/patches/solaris-changes.patch
components/python/requests/resolve.deps
components/python/routes/resolve.deps
components/python/setuptools-git/resolve.deps
components/python/setuptools/Makefile
components/python/setuptools/resolve.deps
components/python/setuptools/setuptools-PYVER.p5m
components/python/simplejson/Makefile
components/python/six/resolve.deps
components/python/sqlalchemy-migrate/Makefile
components/python/sqlalchemy/Makefile
components/python/stevedore/resolve.deps
components/python/suds/Makefile
components/python/swiftclient/Makefile
components/python/tempita/resolve.deps
components/python/tox/resolve.deps
components/python/twisted-web2/Makefile
components/python/twisted/Makefile
components/python/virtualenv/Makefile
components/python/waitress/resolve.deps
components/python/warlock/resolve.deps
components/python/webob/resolve.deps
components/python/websockify/resolve.deps
components/python/websockify/websockify-PYVER.p5m
components/python/webtest/resolve.deps
components/python/xattr/resolve.deps
components/python/xattr/xattr-PYVER.p5m
components/python/zope-interface/Makefile
components/rdiff-backup/Makefile
doc/makefile-variables.txt
doc/packaging.txt
make-rules/ips.mk
make-rules/setup.py.mk
make-rules/shared-macros.mk
transforms/autopyc
transforms/mkgeneric
transforms/python-rename
transforms/standard-libraries-past-py2.6
--- a/components/antlr/antlr.p5m	Mon May 19 10:28:03 2014 +0100
+++ b/components/antlr/antlr.p5m	Mon May 19 07:37:20 2014 -0700
@@ -90,14 +90,13 @@
 file path=usr/include/antlr/TreeParserSharedInputState.hpp
 file path=usr/include/antlr/config.hpp
 file path=usr/lib/antlr.jar
-file path=usr/lib/antlr.py pkg.tmp.autopyc=false
+file path=usr/lib/antlr.py
 file path=usr/sbin/pyantlr.sh
-file path=usr/share/antlr-2.7.7/__init__.py pkg.tmp.autopyc=false
+file path=usr/share/antlr-2.7.7/__init__.py
 file path=usr/share/antlr-2.7.7/antlr-jedit.xml
 file path=usr/share/antlr-2.7.7/antlr-mode.el
 file path=usr/share/antlr-2.7.7/antlr.jar
-file path=usr/share/antlr-2.7.7/antlr.jar
-file path=usr/share/antlr-2.7.7/antlr.py pkg.tmp.autopyc=false
+file path=usr/share/antlr-2.7.7/antlr.py
 file path=usr/share/doc/antlr-2.7.7/closure.gif
 file path=usr/share/doc/antlr-2.7.7/cpp-runtime.html facet.doc.html=true
 file path=usr/share/doc/antlr-2.7.7/csharp-runtime.html facet.doc.html=true
--- a/components/graphviz/graphviz-python-26.p5m	Mon May 19 10:28:03 2014 +0100
+++ b/components/graphviz/graphviz-python-26.p5m	Mon May 19 07:37:20 2014 -0700
@@ -22,7 +22,8 @@
 #
 
 <transform file path=usr.*/man/.+ -> default mangler.man.stability volatile>
-
+<transform file hardlink path=usr/lib/.*\.py$ -> default pkg.tmp.pyversion 2.X>
+#
 set name=pkg.fmri \
     value=pkg:/image/graphviz/[email protected]$(IPS_COMPONENT_VERSION),$(BUILD_VERSION)
 set name=pkg.summary value="Python 2.6 bindings for Graphviz"
@@ -32,18 +33,17 @@
     value="org.opensolaris.category.2008:Applications/System Utilities"
 set name=info.source-url value=$(COMPONENT_ARCHIVE_URL)
 set name=info.upstream-url value=$(COMPONENT_PROJECT_URL)
+set name=org.opensolaris.arc-caseid value=PSARC/2011/269
 set name=org.opensolaris.consolidation value=$(CONSOLIDATION)
-set name=org.opensolaris.arc-caseid \
-    value=PSARC/2011/269
-
+link path=usr/lib/graphviz/python26/_gv.so target=libgv_python26.so
+#
 file path=usr/lib/graphviz/python26/gv.py
 file path=usr/lib/graphviz/python26/libgv_python26.so
-file usr/share/man/man3/gv.3python path=usr/share/man/man3/gv-python.3
-link path=usr/lib/graphviz/python26/_gv.so target=libgv_python26.so
 link path=usr/lib/python2.6/vendor-packages/_gv.so \
     target=../../graphviz/python26/libgv_python26.so
 link path=usr/lib/python2.6/vendor-packages/gv.py \
     target=../../graphviz/python26/gv.py
-
+file usr/share/man/man3/gv.3python path=usr/share/man/man3/gv-python.3
+#
 license COPYING license=EPL1.0
 license graphviz.license.extra license="Other Notices"
--- a/components/graphviz/graphviz-python-27.p5m	Mon May 19 10:28:03 2014 +0100
+++ b/components/graphviz/graphviz-python-27.p5m	Mon May 19 07:37:20 2014 -0700
@@ -22,7 +22,7 @@
 #
 
 <transform file path=usr.*/man/.+ -> default mangler.man.stability volatile>
-
+<transform file hardlink path=usr/lib/.*\.py$ -> default pkg.tmp.pyversion 2.X>
 set name=pkg.fmri \
     value=pkg:/image/graphviz/[email protected]$(IPS_COMPONENT_VERSION),$(BUILD_VERSION)
 set name=pkg.summary value="Python 2.7 bindings for Graphviz"
@@ -32,22 +32,20 @@
     value="org.opensolaris.category.2008:Applications/System Utilities"
 set name=info.source-url value=$(COMPONENT_ARCHIVE_URL)
 set name=info.upstream-url value=$(COMPONENT_PROJECT_URL)
+set name=org.opensolaris.arc-caseid value=PSARC/2011/269
 set name=org.opensolaris.consolidation value=$(CONSOLIDATION)
-set name=org.opensolaris.arc-caseid \
-    value=PSARC/2011/269
-
+#
+link path=usr/lib/graphviz/python27/_gv.so target=libgv_python27.so
 file path=usr/lib/graphviz/python27/gv.py
 file path=usr/lib/graphviz/python27/libgv_python27.so
-link path=usr/lib/graphviz/python27/_gv.so target=libgv_python27.so
 link path=usr/lib/python2.7/vendor-packages/_gv.so \
     target=../../graphviz/python27/libgv_python27.so
 link path=usr/lib/python2.7/vendor-packages/gv.py \
     target=../../graphviz/python27/gv.py
+#
+license COPYING license=EPL1.0
+license graphviz.license.extra license="Other Notices"
 
 # force a dependency on the graphviz package
-depend fmri=__TBD pkg.debug.depend.file=libgraph.so.5 \
-       pkg.debug.depend.path=usr/lib type=require
-
-
-license COPYING license=EPL1.0
-license graphviz.license.extra license="Other Notices"
+depend type=require fmri=__TBD pkg.debug.depend.file=libgraph.so.5 \
+    pkg.debug.depend.path=usr/lib
--- a/components/logilab-astng/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/logilab-astng/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -20,7 +20,7 @@
 #
 
 #
-# Copyright (c) 2011, 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2011, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 
 include ../../make-rules/shared-macros.mk
@@ -35,6 +35,10 @@
 COMPONENT_ARCHIVE_URL=	http://download.logilab.org/pub/astng/$(COMPONENT_ARCHIVE)
 COMPONENT_BUGDB=	python-mod/logilab-astng
 
+# logilab-astng depends on logilab-common, which is not Python 3 ready, so mark
+# this likewise.
+PYTHON_VERSIONS=	2.7 2.6
+
 include ../../make-rules/prep.mk
 include ../../make-rules/ips.mk
 include ../../make-rules/setup.py.mk
--- a/components/logilab-common/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/logilab-common/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -20,7 +20,7 @@
 #
 
 #
-# Copyright (c) 2011, 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2011, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 
 include ../../make-rules/shared-macros.mk
@@ -35,6 +35,9 @@
 COMPONENT_ARCHIVE_URL=	http://download.logilab.org/pub/common/$(COMPONENT_ARCHIVE)
 COMPONENT_BUGDB=	python-mod/logilab-common
 
+# Syntax issues: not Python 3 ready.
+PYTHON_VERSIONS=	2.7 2.6
+
 include ../../make-rules/prep.mk
 include ../../make-rules/ips.mk
 include ../../make-rules/setup.py.mk
--- a/components/meld/meld.p5m	Mon May 19 10:28:03 2014 +0100
+++ b/components/meld/meld.p5m	Mon May 19 07:37:20 2014 -0700
@@ -18,28 +18,30 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2011, 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2011, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 
 <transform file path=usr.*/man/.+ -> default mangler.man.stability uncommitted>
+<transform file hardlink path=usr/lib/.*\.py$ -> default pkg.tmp.pyversion 2.X>
+#
 set name=pkg.fmri \
     value=pkg:/developer/[email protected]$(IPS_COMPONENT_VERSION),$(BUILD_VERSION)
+set name=pkg.summary value="meld - graphical diff and merge tool"
 set name=pkg.description \
     value="Meld is a visual diff and merge tool. You can compare two or three files and edit them in place (diffs update dynamically). You can compare two or three folders and launch file comparisons. You can browse and view a working copy from popular version control systems such such as CVS, Subversion, Bazaar-ng and Mercurial."
-set name=pkg.summary value="meld - graphical diff and merge tool"
-set name=com.oracle.info.description value="the meld graphical diff and merge tool"
+set name=com.oracle.info.description \
+    value="the meld graphical diff and merge tool"
 set name=info.classification \
     value="org.opensolaris.category.2008:Applications/System Utilities"
 set name=info.source-url value=$(COMPONENT_ARCHIVE_URL)
 set name=info.upstream-url value=$(COMPONENT_PROJECT_URL)
-set name=org.opensolaris.arc-caseid \
-    value=PSARC/2008/189
+set name=org.opensolaris.arc-caseid value=PSARC/2008/189
 set name=org.opensolaris.consolidation value=$(CONSOLIDATION)
 file path=usr/bin/meld \
-	pkg.depend.runpath=/usr/lib/meld:/usr/lib/python2.6:/usr/lib/python2.6/vendor-packages/gtk-2.0 \
-	pkg.depend.bypass-generate=.*/checker.* \
-	pkg.depend.bypass-generate=.*/pychecker/__init__.* \
-	pkg.depend.bypass-generate=.*/pygtk.*
+    pkg.depend.runpath=/usr/lib/meld:/usr/lib/python2.6:/usr/lib/python2.6/vendor-packages/gtk-2.0 \
+    pkg.depend.bypass-generate=.*/checker.* \
+    pkg.depend.bypass-generate=.*/pychecker/__init__.* \
+    pkg.depend.bypass-generate=.*/pygtk.*
 file path=usr/lib/meld/meld/__init__.py
 file path=usr/lib/meld/meld/diffmap.py
 file path=usr/lib/meld/meld/diffutil.py
--- a/components/mercurial/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/mercurial/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -34,6 +34,9 @@
 COMPONENT_ARCHIVE_URL=	http://www.selenic.com/mercurial/release/$(COMPONENT_ARCHIVE)
 COMPONENT_BUGDB=	utility/hg
 
+# Fails to build: not Python 3 ready.
+PYTHON_VERSIONS = 2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/mercurial/mercurial-GENFRAG.p5m	Mon May 19 10:28:03 2014 +0100
+++ b/components/mercurial/mercurial-GENFRAG.p5m	Mon May 19 07:37:20 2014 -0700
@@ -25,15 +25,10 @@
 
 # These are not installed, but can be found in the source contrib directory.
 <transform file path=usr/demo/mercurial/(.+)$ -> set action.hash %<\1> >
- 
+
 # We also ignore all dependencies implied by the demos.
 <transform file path=usr/demo/mercurial/.+ -> set pkg.depend.bypass-generate .*>
 
-# And we don't create .pyc files for demo files.
-<transform file path=usr/demo/mercurial/.*\.py$ -> default pkg.tmp.autopyc false>
-
-license mercurial.copyright license='GPLv2+'
-
 
 file path=usr/demo/mercurial/bash_completion
 file path=usr/demo/mercurial/casesmash.py
@@ -72,7 +67,8 @@
 file path=usr/demo/mercurial/vim/patchreview.vim
 file path=usr/demo/mercurial/xml.rnc
 file path=usr/demo/mercurial/zsh_completion
-
+#
 file hg.1 path=usr/share/man/man1/hg.1
 file hgignore.5 path=usr/share/man/man5/hgignore.5
 file hgrc.5 path=usr/share/man/man5/hgrc.5
+license mercurial.copyright license=GPLv2+
--- a/components/pylint/pylint-26.p5m	Mon May 19 10:28:03 2014 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,110 +0,0 @@
-#
-# CDDL HEADER START
-#
-# The contents of this file are subject to the terms of the
-# Common Development and Distribution License (the "License").
-# You may not use this file except in compliance with the License.
-#
-# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
-# or http://www.opensolaris.org/os/licensing.
-# See the License for the specific language governing permissions
-# and limitations under the License.
-#
-# When distributing Covered Code, include this CDDL HEADER in each
-# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
-# If applicable, add the following below this CDDL HEADER, with the
-# fields enclosed by brackets "[]" replaced with your own identifying
-# information: Portions Copyright [yyyy] [name of copyright owner]
-#
-# CDDL HEADER END
-#
-# Copyright (c) 2011, 2013, Oracle and/or its affiliates. All rights reserved.
-#
-
-<transform file path=usr.*/man/.+ -> default mangler.man.stability uncommitted>
-
-set name=pkg.fmri value=pkg:/developer/python/[email protected]$(IPS_COMPONENT_VERSION),$(BUILD_VERSION)
-set name=pkg.summary value="pylint - python code static checker"
-set name=pkg.description value="pylint is a Python source code analyzer which looks for programming errors and helps enforce a coding standard"
-set name=com.oracle.info.description value="the pylint Python code static checker for Python 2.6"
-set name=com.oracle.info.tpno value=9026
-set name=info.classification value="org.opensolaris.category.2008:Development/Python"
-set name=info.upstream-url value=$(COMPONENT_PROJECT_URL)
-set name=info.source-url value=$(COMPONENT_ARCHIVE_URL)
-set name=org.opensolaris.consolidation value=$(CONSOLIDATION)
-set name=org.opensolaris.arc-caseid \
-    value=PSARC/2009/325
-
-file path=usr/bin/epylint-2.6
-file path=usr/bin/pylint-2.6
-file path=usr/bin/pylint-gui-2.6
-file path=usr/bin/pyreverse-2.6
-file path=usr/bin/symilar-2.6
-
-file \
-    path=usr/lib/python2.6/vendor-packages/pylint-$(COMPONENT_VERSION)-py2.6.egg-info/PKG-INFO
-file \
-    path=usr/lib/python2.6/vendor-packages/pylint-$(COMPONENT_VERSION)-py2.6.egg-info/SOURCES.txt
-file \
-    path=usr/lib/python2.6/vendor-packages/pylint-$(COMPONENT_VERSION)-py2.6.egg-info/dependency_links.txt
-file \
-    path=usr/lib/python2.6/vendor-packages/pylint-$(COMPONENT_VERSION)-py2.6.egg-info/requires.txt
-file \
-    path=usr/lib/python2.6/vendor-packages/pylint-$(COMPONENT_VERSION)-py2.6.egg-info/top_level.txt
-file path=usr/lib/python2.6/vendor-packages/pylint/__init__.py
-file path=usr/lib/python2.6/vendor-packages/pylint/__pkginfo__.py
-file path=usr/lib/python2.6/vendor-packages/pylint/checkers/__init__.py
-file path=usr/lib/python2.6/vendor-packages/pylint/checkers/base.py
-file path=usr/lib/python2.6/vendor-packages/pylint/checkers/classes.py
-file path=usr/lib/python2.6/vendor-packages/pylint/checkers/design_analysis.py
-file path=usr/lib/python2.6/vendor-packages/pylint/checkers/exceptions.py
-file path=usr/lib/python2.6/vendor-packages/pylint/checkers/format.py
-file path=usr/lib/python2.6/vendor-packages/pylint/checkers/imports.py
-file path=usr/lib/python2.6/vendor-packages/pylint/checkers/logging.py
-file path=usr/lib/python2.6/vendor-packages/pylint/checkers/misc.py
-file path=usr/lib/python2.6/vendor-packages/pylint/checkers/newstyle.py
-file path=usr/lib/python2.6/vendor-packages/pylint/checkers/raw_metrics.py
-file path=usr/lib/python2.6/vendor-packages/pylint/checkers/similar.py
-file path=usr/lib/python2.6/vendor-packages/pylint/checkers/string_format.py
-file path=usr/lib/python2.6/vendor-packages/pylint/checkers/typecheck.py
-file path=usr/lib/python2.6/vendor-packages/pylint/checkers/utils.py
-file path=usr/lib/python2.6/vendor-packages/pylint/checkers/variables.py
-file path=usr/lib/python2.6/vendor-packages/pylint/config.py
-file path=usr/lib/python2.6/vendor-packages/pylint/epylint.py
-file path=usr/lib/python2.6/vendor-packages/pylint/gui.py
-file path=usr/lib/python2.6/vendor-packages/pylint/interfaces.py
-file path=usr/lib/python2.6/vendor-packages/pylint/lint.py
-file path=usr/lib/python2.6/vendor-packages/pylint/pyreverse/__init__.py
-file path=usr/lib/python2.6/vendor-packages/pylint/pyreverse/diadefslib.py
-file path=usr/lib/python2.6/vendor-packages/pylint/pyreverse/diagrams.py
-file path=usr/lib/python2.6/vendor-packages/pylint/pyreverse/main.py
-file path=usr/lib/python2.6/vendor-packages/pylint/pyreverse/utils.py
-file path=usr/lib/python2.6/vendor-packages/pylint/pyreverse/writer.py
-file path=usr/lib/python2.6/vendor-packages/pylint/reporters/__init__.py
-file path=usr/lib/python2.6/vendor-packages/pylint/reporters/guireporter.py
-file path=usr/lib/python2.6/vendor-packages/pylint/reporters/html.py
-file path=usr/lib/python2.6/vendor-packages/pylint/reporters/text.py
-file path=usr/lib/python2.6/vendor-packages/pylint/testutils.py
-file path=usr/lib/python2.6/vendor-packages/pylint/utils.py
-
-link path=usr/bin/epylint target=epylint-2.6 mediator=python mediator-version=2.6
-link path=usr/bin/pylint target=pylint-2.6 mediator=python mediator-version=2.6
-link path=usr/bin/pylint-gui target=pylint-gui-2.6 mediator=python mediator-version=2.6
-link path=usr/bin/pyreverse target=pyreverse-2.6 mediator=python mediator-version=2.6
-link path=usr/bin/symilar target=symilar-2.6 mediator=python mediator-version=2.6
-
-license pylint.license license="GPLv2"
-
-# force a dependency on logilab-common-26 version 0.58.2
-depend fmri=library/python/[email protected] type=require
-
-# force a dependency on logilab-astng-26 version 0.24.0
-depend fmri=library/python/[email protected] type=require
-
-# force a dependency on the Python 2.6 runtime
-depend fmri=__TBD pkg.debug.depend.file=python2.6 \
-       pkg.debug.depend.path=usr/bin type=require
-
-# force a dependency on the pylint package
-depend fmri=developer/python/[email protected]$(IPS_COMPONENT_VERSION),$(BUILD_VERSION) \
-    type=require
--- a/components/pylint/pylint-27.p5m	Mon May 19 10:28:03 2014 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,110 +0,0 @@
-#
-# CDDL HEADER START
-#
-# The contents of this file are subject to the terms of the
-# Common Development and Distribution License (the "License").
-# You may not use this file except in compliance with the License.
-#
-# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
-# or http://www.opensolaris.org/os/licensing.
-# See the License for the specific language governing permissions
-# and limitations under the License.
-#
-# When distributing Covered Code, include this CDDL HEADER in each
-# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
-# If applicable, add the following below this CDDL HEADER, with the
-# fields enclosed by brackets "[]" replaced with your own identifying
-# information: Portions Copyright [yyyy] [name of copyright owner]
-#
-# CDDL HEADER END
-#
-# Copyright (c) 2011, 2013, Oracle and/or its affiliates. All rights reserved.
-#
-
-<transform file path=usr.*/man/.+ -> default mangler.man.stability uncommitted>
-
-set name=pkg.fmri value=pkg:/developer/python/[email protected]$(IPS_COMPONENT_VERSION),$(BUILD_VERSION)
-set name=pkg.summary value="pylint - python code static checker"
-set name=pkg.description value="pylint is a Python source code analyzer which looks for programming errors and helps enforce a coding standard"
-set name=com.oracle.info.description value="the pylint Python code static checker for Python 2.7"
-set name=com.oracle.info.tpno value=9026
-set name=info.classification value="org.opensolaris.category.2008:Development/Python"
-set name=info.upstream-url value=$(COMPONENT_PROJECT_URL)
-set name=info.source-url value=$(COMPONENT_ARCHIVE_URL)
-set name=org.opensolaris.consolidation value=$(CONSOLIDATION)
-set name=org.opensolaris.arc-caseid \
-    value=PSARC/2009/325
-
-
-file path=usr/bin/epylint-2.7 pkg.depend.bypass-generate=.*
-file path=usr/bin/pylint-2.7 pkg.depend.bypass-generate=.*
-file path=usr/bin/pylint-gui-2.7 pkg.depend.bypass-generate=.*
-file path=usr/bin/pyreverse-2.7 pkg.depend.bypass-generate=.*
-file path=usr/bin/symilar-2.7 pkg.depend.bypass-generate=.*
-file \
-    path=usr/lib/python2.7/vendor-packages/pylint-$(COMPONENT_VERSION)-py2.7.egg-info/PKG-INFO
-file \
-    path=usr/lib/python2.7/vendor-packages/pylint-$(COMPONENT_VERSION)-py2.7.egg-info/SOURCES.txt
-file \
-    path=usr/lib/python2.7/vendor-packages/pylint-$(COMPONENT_VERSION)-py2.7.egg-info/dependency_links.txt
-file \
-    path=usr/lib/python2.7/vendor-packages/pylint-$(COMPONENT_VERSION)-py2.7.egg-info/requires.txt
-file \
-    path=usr/lib/python2.7/vendor-packages/pylint-$(COMPONENT_VERSION)-py2.7.egg-info/top_level.txt
-file path=usr/lib/python2.7/vendor-packages/pylint/__init__.py
-file path=usr/lib/python2.7/vendor-packages/pylint/__pkginfo__.py
-file path=usr/lib/python2.7/vendor-packages/pylint/checkers/__init__.py
-file path=usr/lib/python2.7/vendor-packages/pylint/checkers/base.py
-file path=usr/lib/python2.7/vendor-packages/pylint/checkers/classes.py
-file path=usr/lib/python2.7/vendor-packages/pylint/checkers/design_analysis.py
-file path=usr/lib/python2.7/vendor-packages/pylint/checkers/exceptions.py
-file path=usr/lib/python2.7/vendor-packages/pylint/checkers/format.py
-file path=usr/lib/python2.7/vendor-packages/pylint/checkers/imports.py
-file path=usr/lib/python2.7/vendor-packages/pylint/checkers/logging.py
-file path=usr/lib/python2.7/vendor-packages/pylint/checkers/misc.py
-file path=usr/lib/python2.7/vendor-packages/pylint/checkers/newstyle.py
-file path=usr/lib/python2.7/vendor-packages/pylint/checkers/raw_metrics.py
-file path=usr/lib/python2.7/vendor-packages/pylint/checkers/similar.py
-file path=usr/lib/python2.7/vendor-packages/pylint/checkers/string_format.py
-file path=usr/lib/python2.7/vendor-packages/pylint/checkers/typecheck.py
-file path=usr/lib/python2.7/vendor-packages/pylint/checkers/utils.py
-file path=usr/lib/python2.7/vendor-packages/pylint/checkers/variables.py
-file path=usr/lib/python2.7/vendor-packages/pylint/config.py
-file path=usr/lib/python2.7/vendor-packages/pylint/epylint.py
-file path=usr/lib/python2.7/vendor-packages/pylint/gui.py
-file path=usr/lib/python2.7/vendor-packages/pylint/interfaces.py
-file path=usr/lib/python2.7/vendor-packages/pylint/lint.py
-file path=usr/lib/python2.7/vendor-packages/pylint/pyreverse/__init__.py
-file path=usr/lib/python2.7/vendor-packages/pylint/pyreverse/diadefslib.py
-file path=usr/lib/python2.7/vendor-packages/pylint/pyreverse/diagrams.py
-file path=usr/lib/python2.7/vendor-packages/pylint/pyreverse/main.py
-file path=usr/lib/python2.7/vendor-packages/pylint/pyreverse/utils.py
-file path=usr/lib/python2.7/vendor-packages/pylint/pyreverse/writer.py
-file path=usr/lib/python2.7/vendor-packages/pylint/reporters/__init__.py
-file path=usr/lib/python2.7/vendor-packages/pylint/reporters/guireporter.py
-file path=usr/lib/python2.7/vendor-packages/pylint/reporters/html.py
-file path=usr/lib/python2.7/vendor-packages/pylint/reporters/text.py
-file path=usr/lib/python2.7/vendor-packages/pylint/testutils.py
-file path=usr/lib/python2.7/vendor-packages/pylint/utils.py
-
-link path=usr/bin/epylint target=epylint-2.7 mediator=python mediator-version=2.7
-link path=usr/bin/pylint target=pylint-2.7 mediator=python mediator-version=2.7
-link path=usr/bin/pylint-gui target=pylint-gui-2.7 mediator=python mediator-version=2.7
-link path=usr/bin/pyreverse target=pyreverse-2.7 mediator=python mediator-version=2.7
-link path=usr/bin/symilar target=symilar-2.7 mediator=python mediator-version=2.7
-
-license pylint.license license="GPLv2"
-
-# force a dependency on logilab-common-27 version 0.58.2
-depend fmri=library/python/[email protected] type=require
-
-# force a dependency on logilab-astng-27 version 0.24.0
-depend fmri=library/python/[email protected] type=require
-
-# force a dependency on the Python 2.7 runtime
-depend fmri=__TBD pkg.debug.depend.file=python2.7 \
-       pkg.debug.depend.path=usr/bin type=require
-
-# force a dependency on the pylint package
-depend fmri=developer/python/[email protected]$(IPS_COMPONENT_VERSION),$(BUILD_VERSION) \
-    type=require
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/components/pylint/pylint-GENFRAG.p5m	Mon May 19 07:37:20 2014 -0700
@@ -0,0 +1,43 @@
+#
+# CDDL HEADER START
+#
+# The contents of this file are subject to the terms of the
+# Common Development and Distribution License (the "License").
+# You may not use this file except in compliance with the License.
+#
+# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
+# or http://www.opensolaris.org/os/licensing.
+# See the License for the specific language governing permissions
+# and limitations under the License.
+#
+# When distributing Covered Code, include this CDDL HEADER in each
+# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
+# If applicable, add the following below this CDDL HEADER, with the
+# fields enclosed by brackets "[]" replaced with your own identifying
+# information: Portions Copyright [yyyy] [name of copyright owner]
+#
+# CDDL HEADER END
+#
+# Copyright (c) 2011, 2014, Oracle and/or its affiliates. All rights reserved.
+#
+
+<transform file path=usr.*/man/.+ -> default mangler.man.stability uncommitted>
+#
+file path=usr/share/doc/pylint/FAQ.txt
+file path=usr/share/doc/pylint/README
+file path=usr/share/doc/pylint/beginner_pylint_tutorial.txt
+file path=usr/share/doc/pylint/examples/custom.py
+file path=usr/share/doc/pylint/examples/custom_raw.py
+file path=usr/share/doc/pylint/examples/pylint.el
+file path=usr/share/doc/pylint/examples/pylintrc
+file path=usr/share/doc/pylint/examples/pylintrc_camelcase
+file path=usr/share/doc/pylint/features.txt
+file path=usr/share/doc/pylint/manual.txt
+file path=usr/share/doc/pylint/quickstart.txt
+file manpages/epylint.1 path=usr/share/man/man1/epylint.1
+file manpages/pylint-gui.1 path=usr/share/man/man1/pylint-gui.1
+file man/pylint.1 path=usr/share/man/man1/pylint.1
+file man/pyreverse.1 path=usr/share/man/man1/pyreverse.1
+file manpages/symilar.1 path=usr/share/man/man1/symilar.1
+#
+license pylint.license license=GPLv2
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/components/pylint/pylint-PYVER.p5m	Mon May 19 07:37:20 2014 -0700
@@ -0,0 +1,115 @@
+#
+# CDDL HEADER START
+#
+# The contents of this file are subject to the terms of the
+# Common Development and Distribution License (the "License").
+# You may not use this file except in compliance with the License.
+#
+# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
+# or http://www.opensolaris.org/os/licensing.
+# See the License for the specific language governing permissions
+# and limitations under the License.
+#
+# When distributing Covered Code, include this CDDL HEADER in each
+# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
+# If applicable, add the following below this CDDL HEADER, with the
+# fields enclosed by brackets "[]" replaced with your own identifying
+# information: Portions Copyright [yyyy] [name of copyright owner]
+#
+# CDDL HEADER END
+#
+# Copyright (c) 2011, 2014, Oracle and/or its affiliates. All rights reserved.
+#
+
+<transform file path=usr.*/man/.+ -> default mangler.man.stability uncommitted>
+set name=pkg.fmri \
+    value=pkg:/developer/python/pylint-$(PYV)@$(IPS_COMPONENT_VERSION),$(BUILD_VERSION)
+set name=pkg.summary value="pylint - python code static checker"
+set name=pkg.description \
+    value="pylint is a Python source code analyzer which looks for programming errors and helps enforce a coding standard"
+set name=com.oracle.info.description \
+    value="the pylint Python code static checker for Python $(PYVER)"
+set name=com.oracle.info.tpno value=9026
+set name=info.classification \
+    value=org.opensolaris.category.2008:Development/Python
+set name=info.source-url value=$(COMPONENT_ARCHIVE_URL)
+set name=info.upstream-url value=$(COMPONENT_PROJECT_URL)
+set name=org.opensolaris.arc-caseid value=PSARC/2009/325
+set name=org.opensolaris.consolidation value=$(CONSOLIDATION)
+#
+link path=usr/bin/epylint target=epylint-$(PYVER) mediator=python \
+    mediator-version=$(PYVER)
+file path=usr/bin/epylint-$(PYVER)
+link path=usr/bin/pylint target=pylint-$(PYVER) mediator=python \
+    mediator-version=$(PYVER)
+file path=usr/bin/pylint-$(PYVER)
+link path=usr/bin/pylint-gui target=pylint-gui-$(PYVER) mediator=python \
+    mediator-version=$(PYVER)
+file path=usr/bin/pylint-gui-$(PYVER)
+link path=usr/bin/pyreverse target=pyreverse-$(PYVER) mediator=python \
+    mediator-version=$(PYVER)
+file path=usr/bin/pyreverse-$(PYVER)
+link path=usr/bin/symilar target=symilar-$(PYVER) mediator=python \
+    mediator-version=$(PYVER)
+#
+file path=usr/bin/symilar-$(PYVER)
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint-$(COMPONENT_VERSION)-py$(PYVER).egg-info/PKG-INFO
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint-$(COMPONENT_VERSION)-py$(PYVER).egg-info/SOURCES.txt
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint-$(COMPONENT_VERSION)-py$(PYVER).egg-info/dependency_links.txt
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint-$(COMPONENT_VERSION)-py$(PYVER).egg-info/requires.txt
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint-$(COMPONENT_VERSION)-py$(PYVER).egg-info/top_level.txt
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/__init__.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/__pkginfo__.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/checkers/__init__.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/checkers/base.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/checkers/classes.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/checkers/design_analysis.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/checkers/exceptions.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/checkers/format.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/checkers/imports.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/checkers/logging.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/checkers/misc.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/checkers/newstyle.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/checkers/raw_metrics.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/checkers/similar.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/checkers/string_format.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/checkers/typecheck.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/checkers/utils.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/checkers/variables.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/config.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/epylint.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/gui.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/interfaces.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/lint.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/pyreverse/__init__.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/pyreverse/diadefslib.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/pyreverse/diagrams.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/pyreverse/main.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/pyreverse/utils.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/pyreverse/writer.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/reporters/__init__.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/reporters/guireporter.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/reporters/html.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/reporters/text.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/testutils.py
+file path=usr/lib/python$(PYVER)/vendor-packages/pylint/utils.py
+#
+license pylint.license license=GPLv2
+
+# force a dependency on the Python $(PYVER) runtime
+depend type=require fmri=__TBD pkg.debug.depend.file=python$(PYVER) \
+    pkg.debug.depend.path=usr/bin
+
+# force a dependency on the pylint package
+depend type=require \
+    fmri=developer/python/[email protected]$(IPS_COMPONENT_VERSION),$(BUILD_VERSION)
+
+# force a dependency on the pylint package
+depend type=require \
+    fmri=developer/python/[email protected]$(IPS_COMPONENT_VERSION),$(BUILD_VERSION)
+
+# force a dependency on logilab-astng-$(PYV) version 0.24.0
+depend type=require fmri=library/python/logilab-astng-$(PYV)@0.24.0
+
+# force a dependency on logilab-common-$(PYV) version 0.58.2
+depend type=require fmri=library/python/logilab-common-$(PYV)@0.58.2
--- a/components/pylint/pylint.p5m	Mon May 19 10:28:03 2014 +0100
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,65 +0,0 @@
-#
-# CDDL HEADER START
-#
-# The contents of this file are subject to the terms of the
-# Common Development and Distribution License (the "License").
-# You may not use this file except in compliance with the License.
-#
-# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
-# or http://www.opensolaris.org/os/licensing.
-# See the License for the specific language governing permissions
-# and limitations under the License.
-#
-# When distributing Covered Code, include this CDDL HEADER in each
-# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
-# If applicable, add the following below this CDDL HEADER, with the
-# fields enclosed by brackets "[]" replaced with your own identifying
-# information: Portions Copyright [yyyy] [name of copyright owner]
-#
-# CDDL HEADER END
-#
-# Copyright (c) 2011, 2013, Oracle and/or its affiliates. All rights reserved.
-#
-
-<transform file path=usr.*/man/.+ -> default mangler.man.stability uncommitted>
-
-set name=pkg.fmri value=pkg:/developer/python/[email protected]$(IPS_COMPONENT_VERSION),$(BUILD_VERSION)
-set name=pkg.summary value="pylint - python code static checker"
-set name=pkg.description value="pylint is a Python source code analyzer which looks for programming errors and helps enforce a coding standard"
-set name=com.oracle.info.description value="the pylint code static checker for Python"
-set name=com.oracle.info.tpno value=9026
-set name=info.classification value="org.opensolaris.category.2008:Development/Python"
-set name=info.upstream-url value=$(COMPONENT_PROJECT_URL)
-set name=info.source-url value=$(COMPONENT_ARCHIVE_URL)
-set name=org.opensolaris.consolidation value=$(CONSOLIDATION)
-set name=org.opensolaris.arc-caseid \
-    value=PSARC/2009/325
-
-
-file path=usr/share/doc/pylint/beginner_pylint_tutorial.txt
-file path=usr/share/doc/pylint/examples/custom_raw.py pkg.tmp.autopyc=false
-file path=usr/share/doc/pylint/examples/custom.py pkg.tmp.autopyc=false
-file path=usr/share/doc/pylint/examples/pylint.el
-file path=usr/share/doc/pylint/examples/pylintrc
-file path=usr/share/doc/pylint/examples/pylintrc_camelcase
-file path=usr/share/doc/pylint/FAQ.txt
-file path=usr/share/doc/pylint/features.txt
-file path=usr/share/doc/pylint/manual.txt
-file path=usr/share/doc/pylint/quickstart.txt
-file path=usr/share/doc/pylint/README
-
-file manpages/epylint.1 path=usr/share/man/man1/epylint.1
-file man/pylint.1 path=usr/share/man/man1/pylint.1
-file manpages/pylint-gui.1 path=usr/share/man/man1/pylint-gui.1
-file man/pyreverse.1 path=usr/share/man/man1/pyreverse.1
-file manpages/symilar.1 path=usr/share/man/man1/symilar.1
-
-license pylint.license license="GPLv2"
-
-depend fmri=developer/python/[email protected]$(IPS_COMPONENT_VERSION),$(BUILD_VERSION) \
-    predicate=runtime/python-26 \
-    type=conditional
-
-depend fmri=developer/python/[email protected]$(IPS_COMPONENT_VERSION),$(BUILD_VERSION) \
-    predicate=runtime/python-27 \
-    type=conditional
--- a/components/pylint/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/pylint/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/alembic/alembic-PYVER.p5m	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/alembic/alembic-PYVER.p5m	Mon May 19 07:37:20 2014 -0700
@@ -83,7 +83,7 @@
 
 # force the rename with an optional dependency on the old name
 depend type=optional \
-    fmri=library/python/alembic-$(PYV)@0.6.0,5.12-5.12.0.0.0.41.0
+    fmri=library/python-2/alembic-$(PYV)@0.6.0,5.12-5.12.0.0.0.41.0
 
 # force a dependency on the Python runtime
 depend type=require fmri=__TBD pkg.debug.depend.file=python$(PYVER) \
--- a/components/python/alembic/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/alembic/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,4 +1,6 @@
 library/python/setuptools-26
 library/python/setuptools-27
+library/python/setuptools-34
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/amqp/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/amqp/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/anyjson/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/anyjson/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/babel/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/babel/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,6 +1,6 @@
-library/python-2/setuptools-26
-library/python-2/setuptools-27
 library/python/setuptools-26
 library/python/setuptools-27
+library/python/setuptools-34
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/beautifulsoup4/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/beautifulsoup4/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/boto/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/boto/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2012, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 include ../../../make-rules/shared-macros.mk
 
@@ -32,6 +32,9 @@
 COMPONENT_PROJECT_URL=	http://github.com/boto/boto/
 COMPONENT_BUGDB=	python-mod/boto
 
+# Syntax issues: not Python 3 ready.
+PYTHON_VERSIONS=	2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/cffi/cffi-PYVER.p5m	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/cffi/cffi-PYVER.p5m	Mon May 19 07:37:20 2014 -0700
@@ -23,6 +23,9 @@
 # Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
 #
 
+# Python 3.4 is 64-bit only, so no need for 32-bit shared object.
+<transform file path=usr/lib/python3.4/vendor-packages/_cffi_backend.so -> drop>
+#
 set name=pkg.fmri \
     value=pkg:/library/python/cffi-$(PYV)@$(IPS_COMPONENT_VERSION),$(BUILD_VERSION)
 set name=pkg.summary \
@@ -31,9 +34,8 @@
     value="CFFI provides a convenient and reliable way of calling C code from Python.  It does not require learning a new language or an extensive API, and tries to minimize the amount of C code you have to write.  It works at both an ABI level, allowing you to reference symbols in libraries as well as at an API level, allowing you to embed C code in your Python program."
 set name=com.oracle.info.description value="the cffi Python module"
 set name=com.oracle.info.tpno value=16913
-set name=info.classification \
-    value=org.opensolaris.category.2008:Development/Python \
-    value=org.opensolaris.category.2008:Development/C
+set name=info.classification value=org.opensolaris.category.2008:Development/C \
+    value=org.opensolaris.category.2008:Development/Python
 set name=info.source-url value=$(COMPONENT_ARCHIVE_URL)
 set name=info.upstream [email protected]
 set name=info.upstream-url value=$(COMPONENT_PROJECT_URL)
--- a/components/python/cffi/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/cffi/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,4 +1,5 @@
 library/libffi
 runtime/python-26
 runtime/python-27
+runtime/python-34
 system/library
--- a/components/python/cheetah/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/cheetah/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2012, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 include ../../../make-rules/shared-macros.mk
 
@@ -32,6 +32,9 @@
 COMPONENT_PROJECT_URL=	http://www.cheetahtemplate.org/
 COMPONENT_BUGDB=	python-mod/cheetah
 
+# Syntax issues: not Python 3 ready.
+PYTHON_VERSIONS=	2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/cherrypy/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/cherrypy/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2011, 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2011, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 include ../../../make-rules/shared-macros.mk
 
@@ -36,6 +36,9 @@
 
 PATCH_LEVEL=0
 
+# This module is not Python 3 ready: syntax issues.
+PYTHON_VERSIONS = 2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/cinderclient/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/cinderclient/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/cliff/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/cliff/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/cmd2/cmd2-PYVER.p5m	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/cmd2/cmd2-PYVER.p5m	Mon May 19 07:37:20 2014 -0700
@@ -44,7 +44,8 @@
 license cmd2.license license=MIT
 
 # force the rename with an optional dependency on the old name
-depend type=optional fmri=library/python-2/[email protected],5.12-5.12.0.0.0.41.0
+depend type=optional \
+    fmri=library/python-2/cmd2-$(PYV)@0.6.7.1,5.12-5.12.0.0.0.41.0
 
 # force a dependency on the Python runtime
 depend type=require fmri=__TBD pkg.debug.depend.file=python$(PYVER) \
--- a/components/python/cmd2/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/cmd2/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/cov-core/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/cov-core/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2013, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 include ../../../make-rules/shared-macros.mk
 
@@ -32,6 +32,9 @@
 COMPONENT_PROJECT_URL=	https://pypi.python.org/pypi/cov-core
 COMPONENT_BUGDB=	python-mod/cov-core
 
+# Depends on coverage, which is not Python 3 ready.
+PYTHON_VERSIONS=	2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/coverage/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/coverage/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -35,6 +35,11 @@
 COMPONENT_ARCHIVE_URL=	http://pypi.python.org/packages/source/c/coverage/$(COMPONENT_ARCHIVE)
 COMPONENT_BUGDB=	python-mod/coverage
 
+# Not Python 3 ready: weird build issues (tries to download & install
+# "distribute").  But coverage version 3.7.1 has fixed these issues; it
+# builds and publishes fine with Python 3.
+PYTHON_VERSIONS = 2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/cssutils/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/cssutils/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -20,21 +20,24 @@
 #
 
 #
-# Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2013, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 
 include ../../../make-rules/shared-macros.mk
 
 COMPONENT_NAME=		cssutils
 COMPONENT_VERSION=	0.9.6
-COMPONENT_PROJECT_URL=	http://code.google.com/p/cssutils/
+COMPONENT_PROJECT_URL=	https://pypi.python.org/pypi/cssutils/
 COMPONENT_SRC=		$(COMPONENT_NAME)-$(COMPONENT_VERSION)
 COMPONENT_ARCHIVE=	$(COMPONENT_SRC).zip
 COMPONENT_ARCHIVE_HASH= \
     sha256:18f3cffb2ff413e0796d0c9192db3a56f18fe57524cc54edc57d20239614eb87
-COMPONENT_ARCHIVE_URL=	http://cssutils.googlecode.com/files/$(COMPONENT_ARCHIVE)
+COMPONENT_ARCHIVE_URL=	https://pypi.python.org/packages/source/c/cssutils/$(COMPONENT_ARCHIVE)
 COMPONENT_BUGDB=	python-mod/cssutils
 
+# This module is not Python 3 ready: syntax issues.
+PYTHON_VERSIONS = 2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/d2to1/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/d2to1/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/decorator/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/decorator/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/django-appconf/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/django-appconf/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -32,6 +32,9 @@
 COMPONENT_PROJECT_URL=	http://django-appconf.readthedocs.org/
 COMPONENT_BUGDB=	python-mod/django-appconf
 
+# Depends on django, which is not Python 3 ready.
+PYTHON_VERSIONS=	2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/django/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/django/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -32,6 +32,9 @@
 COMPONENT_PROJECT_URL=	http://www.djangoproject.com/
 COMPONENT_BUGDB=	python-mod/django
 
+# Syntax issues: not Python 3 ready.
+PYTHON_VERSIONS=	2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/django_compressor/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/django_compressor/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -32,6 +32,9 @@
 COMPONENT_PROJECT_URL=	http://django-compressor.readthedocs.org
 COMPONENT_BUGDB=	python-mod/django_compressor
 
+# Depends on django, which is not Python 3 ready.
+PYTHON_VERSIONS=	2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/django_openstack_auth/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/django_openstack_auth/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -32,6 +32,9 @@
 COMPONENT_PROJECT_URL=	http://www.openstack.org/
 COMPONENT_BUGDB=	python-mod/django_openstack_auth
 
+# Depends on django, which is not Python 3 ready.
+PYTHON_VERSIONS=	2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/eventlet/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/eventlet/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2012, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 include ../../../make-rules/shared-macros.mk
 
@@ -32,6 +32,9 @@
 COMPONENT_PROJECT_URL=	http://eventlet.net/
 COMPONENT_BUGDB=	python-mod/eventlet
 
+# Depends on greenlet, which is not Python 3 ready.
+PYTHON_VERSIONS=	2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/components/python/filechunkio/patches/01-python3.patch	Mon May 19 07:37:20 2014 -0700
@@ -0,0 +1,19 @@
+This patch is for Python 3 compatibility.  It has not been submitted upstream,
+as the community appears to have gone dormant.
+
+--- filechunkio-1.5/setup.py~	2011-04-27 06:12:34.000000000 -0700
++++ filechunkio-1.5/setup.py	2014-04-16 11:32:41.158068141 -0700
[email protected]@ -1,12 +1,11 @@
+ #!/usr/bin/env python
+ from distutils.core import setup
+ 
+-from filechunkio import __version__
+ 
+ 
+ setup(
+     name="filechunkio",
+-    version=unicode(__version__),
++    version="1.5",
+     description="FileChunkIO represents a chunk of an OS-level file "\
+         "containing bytes data",
+     long_description=open("README", 'r').read(),
--- a/components/python/filechunkio/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/filechunkio/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/formencode/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/formencode/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2013, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 include ../../../make-rules/shared-macros.mk
 
@@ -32,6 +32,9 @@
 COMPONENT_PROJECT_URL=	http://www.formencode.org/en/latest/
 COMPONENT_BUGDB=	python-mod/formencode
 
+# Code explicitly checks for sys.version < '3.0'
+PYTHON_VERSIONS=	2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/glanceclient/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/glanceclient/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/greenlet/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/greenlet/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -32,6 +32,10 @@
 COMPONENT_PROJECT_URL=	https://github.com/python-greenlet/greenlet
 COMPONENT_BUGDB=	python-mod/greenlet
 
+# This module is not Python 3 ready: strange build failures that need more
+# investigation.
+PYTHON_VERSIONS = 2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/httplib2/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/httplib2/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2012, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 include ../../../make-rules/shared-macros.mk
 
@@ -32,6 +32,11 @@
 COMPONENT_PROJECT_URL=	http://code.google.com/p/httplib2/
 COMPONENT_BUGDB=	python-mod/httplib2
 
+# Depends on SocksiPy; for Python 2.x, the module is part of httplib2, but
+# for Python 3.x, it is separate.  Once we add this module, httplib2 will
+# most likely work with Python 3.
+PYTHON_VERSIONS=	2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/imaging/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/imaging/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -35,6 +35,9 @@
 COMPONENT_ARCHIVE_URL=	http://effbot.org/downloads/$(COMPONENT_ARCHIVE)
 COMPONENT_BUGDB=	python-mod/pil
 
+# Syntax issues: not Python 3 ready.
+PYTHON_VERSIONS = 2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/imaging/imaging-PYVER.p5m	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/imaging/imaging-PYVER.p5m	Mon May 19 07:37:20 2014 -0700
@@ -37,24 +37,25 @@
 set name=info.upstream-url value=$(COMPONENT_PROJECT_URL)
 set name=org.opensolaris.arc-caseid value=PSARC/2008/102
 set name=org.opensolaris.consolidation value=$(CONSOLIDATION)
+#
 file build/$(MACH32)-$(PYVER)/scripts-$(PYVER)/pilconvert.py \
-    path=usr/bin/pilconvert-$(PYVER).py pkg.tmp.autopyc=false
+    path=usr/bin/pilconvert-$(PYVER).py
 link path=usr/bin/pilconvert.py target=pilconvert-$(PYVER).py mediator=python \
     mediator-version=$(PYVER)
 file build/$(MACH32)-$(PYVER)/scripts-$(PYVER)/pildriver.py \
-    path=usr/bin/pildriver-$(PYVER).py pkg.tmp.autopyc=false
+    path=usr/bin/pildriver-$(PYVER).py
 link path=usr/bin/pildriver.py target=pildriver-$(PYVER).py mediator=python \
     mediator-version=$(PYVER)
 file build/$(MACH32)-$(PYVER)/scripts-$(PYVER)/pilfile.py \
-    path=usr/bin/pilfile-$(PYVER).py pkg.tmp.autopyc=false
+    path=usr/bin/pilfile-$(PYVER).py
 link path=usr/bin/pilfile.py target=pilfile-$(PYVER).py mediator=python \
     mediator-version=$(PYVER)
 file build/$(MACH32)-$(PYVER)/scripts-$(PYVER)/pilfont.py \
-    path=usr/bin/pilfont-$(PYVER).py pkg.tmp.autopyc=false
+    path=usr/bin/pilfont-$(PYVER).py
 link path=usr/bin/pilfont.py target=pilfont-$(PYVER).py mediator=python \
     mediator-version=$(PYVER)
 file build/$(MACH32)-$(PYVER)/scripts-$(PYVER)/pilprint.py \
-    path=usr/bin/pilprint-$(PYVER).py pkg.tmp.autopyc=false
+    path=usr/bin/pilprint-$(PYVER).py
 link path=usr/bin/pilprint.py target=pilprint-$(PYVER).py mediator=python \
     mediator-version=$(PYVER)
 file path=usr/lib/python$(PYVER)/vendor-packages/PIL.pth
@@ -146,6 +147,7 @@
 file path=usr/lib/python$(PYVER)/vendor-packages/PIL/_imaging.so
 file path=usr/lib/python$(PYVER)/vendor-packages/PIL/_imagingft.so
 file path=usr/lib/python$(PYVER)/vendor-packages/PIL/_imagingmath.so
+#
 license imaging.license license="Historical Permission Notice and Disclaimer"
 
 # python-imaging was previously in the 'desktop' consolidation. This optional
--- a/components/python/ipython/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/ipython/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -20,7 +20,7 @@
 #
 
 #
-# Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2013, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 
 include ../../../make-rules/shared-macros.mk
@@ -35,6 +35,9 @@
 COMPONENT_ARCHIVE_URL=	http://archive.ipython.org/release/$(COMPONENT_VERSION)/$(COMPONENT_ARCHIVE)
 COMPONENT_BUGDB=	python-mod/ipython
 
+# Syntax issues: not Python 3 ready.
+PYTHON_VERSIONS = 2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/iso8601/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/iso8601/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/jsonpatch/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/jsonpatch/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2013, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 include ../../../make-rules/shared-macros.mk
 
@@ -38,6 +38,10 @@
 
 ASLR_MODE = $(ASLR_NOT_APPLICABLE)
 
+# Author's name uses non-ASCII characters.
+COMPONENT_BUILD_ENV	+=	LC_ALL=en_US.UTF-8
+COMPONENT_INSTALL_ENV	+=	LC_ALL=en_US.UTF-8
+
 # common targets
 build:		$(BUILD_NO_ARCH)
 
--- a/components/python/jsonpatch/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/jsonpatch/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/jsonpointer/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/jsonpointer/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2013, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 include ../../../make-rules/shared-macros.mk
 
@@ -38,6 +38,10 @@
 
 ASLR_MODE = $(ASLR_NOT_APPLICABLE)
 
+# Author's name uses non-ASCII characters.
+COMPONENT_BUILD_ENV	+=	LC_ALL=en_US.UTF-8
+COMPONENT_INSTALL_ENV	+=	LC_ALL=en_US.UTF-8
+
 # common targets
 build:		$(BUILD_NO_ARCH)
 
--- a/components/python/jsonpointer/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/jsonpointer/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/jsonrpclib/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/jsonrpclib/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -36,6 +36,10 @@
 COMPONENT_ARCHIVE_URL=https://github.com/joshmarshall/jsonrpclib/tarball/$(COMPONENT_HASH)
 COMPONENT_BUGDB=	python-mod/jsonrpclib
 
+# This module builds with Python 3, but depends on simplejson.  The following
+# line can be removed when simplejson supports Python 3.
+PYTHON_VERSIONS=	2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/jsonschema/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/jsonschema/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/keystoneclient/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/keystoneclient/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/components/python/kombu/patches/01.python3-reqs.patch	Mon May 19 07:37:20 2014 -0700
@@ -0,0 +1,17 @@
+This patch comes from upstream; it is the essential change between 2.5.15
+and 2.5.16; once we upgrade to 2.5.16 or later, the patch can be removed.
+The patch is needed to get kombu to install properly with Python 3.
+
+--- kombu-2.5.12/setup.py	2013-06-28 07:11:26.000000000 -0700
++++ kombu-2.5.12/setup.py	2013-10-23 10:53:25.000000000 -0700
[email protected]@ -108,8 +108,8 @@
+ 
+ 
+ def reqs(f):
+-    return filter(None, [strip_comments(l) for l in open(
+-        os.path.join(os.getcwd(), 'requirements', f)).readlines()])
++    return list(filter(None, [strip_comments(l) for l in open(
++        os.path.join(os.getcwd(), 'requirements', f)).readlines()]))
+ 
+ install_requires = reqs('default.txt')
+ if py_version[0:2] == (2, 6):
--- a/components/python/kombu/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/kombu/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/ldtp/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/ldtp/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2011, 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2011, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 include ../../../make-rules/shared-macros.mk
 
@@ -36,6 +36,9 @@
 COMPONENT_ARCHIVE_URL=  http://download.freedesktop.org/ldtp/$(COMPONENT_MAJOR_VERSION)/$(COMPONENT_MINOR_VERSION)/$(COMPONENT_ARCHIVE)
 COMPONENT_BUGDB=	python-mod/ldtp
 
+# Syntax issues: not Python 3 ready.
+PYTHON_VERSIONS = 2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/lesscpy/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/lesscpy/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2013, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 include ../../../make-rules/shared-macros.mk
 
@@ -41,6 +41,10 @@
 
 ASLR_MODE = $(ASLR_NOT_APPLICABLE)
 
+# Author's name has non-ASCII characters.
+COMPONENT_BUILD_ENV	+=	LC_ALL=en_US.UTF-8
+COMPONENT_INSTALL_ENV	+=	LC_ALL=en_US.UTF-8
+
 COMPONENT_POST_INSTALL_ACTION = \
          (cd $(PROTO_DIR)/usr/bin ; $(MV) -f lesscpy lesscpy-$(PYTHON_VERSION))
 
--- a/components/python/lesscpy/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/lesscpy/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/librabbitmq/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/librabbitmq/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2012, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 include ../../../make-rules/shared-macros.mk
 
@@ -32,6 +32,9 @@
 COMPONENT_PROJECT_URL=	http://github.com/celery/librabbitmq
 COMPONENT_BUGDB=	python-mod/librabbitmq
 
+# This module is not Python 3 ready: syntax work needed.
+PYTHON_VERSIONS=	2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/lockfile/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/lockfile/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/m2crypto/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/m2crypto/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -35,6 +35,9 @@
 COMPONENT_ARCHIVE_URL=	http://pypi.python.org/packages/source/M/M2Crypto/$(COMPONENT_ARCHIVE)
 COMPONENT_BUGDB=	python-mod/m2crypto
 
+# Syntax issues: not Python 3 ready.
+PYTHON_VERSIONS = 2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/mako/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/mako/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/markdown/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/markdown/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/markupsafe/markupsafe-PYVER.p5m	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/markupsafe/markupsafe-PYVER.p5m	Mon May 19 07:37:20 2014 -0700
@@ -21,6 +21,9 @@
 # Copyright (c) 2013, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 
+# Python 3 is 64-bit only, so 32-bit shared objects do not belong.
+<transform file path=usr/lib/python3.4/vendor-packages/markupsafe/_speedups.so -> drop>
+#
 set name=pkg.fmri \
     value=pkg:/library/python/markupsafe-$(PYV)@$(IPS_COMPONENT_VERSION),$(BUILD_VERSION)
 set name=pkg.summary value="Python HTML string module."
@@ -48,6 +51,10 @@
 file path=usr/lib/python$(PYVER)/vendor-packages/markupsafe/_speedups.so
 license markupsafe.license license=BSD
 
+# force the rename with an optional dependency on the old name
+depend type=optional \
+    fmri=library/python-2/markupsafe-$(PYV)@0.18,5.12-5.12.0.0.0.41.0
+
 # force a dependency on the Python runtime
 depend type=require fmri=__TBD pkg.debug.depend.file=python$(PYVER) \
     pkg.debug.depend.path=usr/bin
@@ -55,7 +62,3 @@
 # force a dependency on the markupsafe package
 depend type=require \
     fmri=library/python/[email protected]$(IPS_COMPONENT_VERSION),$(BUILD_VERSION)
-
-# force the rename with an optional dependency on the old name
-depend type=optional \
-    fmri=library/python-2/markupsafe-$(PYV)@0.18,5.12-5.12.0.0.0.41.0
--- a/components/python/markupsafe/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/markupsafe/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,3 +1,4 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
 system/library
--- a/components/python/mock/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/mock/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2013, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 include ../../../make-rules/shared-macros.mk
 
@@ -32,6 +32,10 @@
 COMPONENT_ARCHIVE_URL=	http://pypi.python.org/packages/source/m/mock/$(COMPONENT_ARCHIVE)
 COMPONENT_BUGDB=	python-mod/mock
 
+# mock has been subsumed into Python starting with 3.3, so no need to build
+# it for Python 3.
+PYTHON_VERSIONS=	2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/mysql/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/mysql/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -40,6 +40,9 @@
 COMPONENT_ARCHIVE_URL=	http://downloads.sourceforge.net/mysql-python/$(COMPONENT_ARCHIVE)
 COMPONENT_BUGDB=	python-mod/mysql
 
+# Syntax issues: not Python 3 ready.
+PYTHON_VERSIONS = 2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/netaddr/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/netaddr/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -32,6 +32,11 @@
 COMPONENT_ARCHIVE_URL=	http://github.com/downloads/drkjam/$(COMPONENT_NAME)/$(COMPONENT_ARCHIVE)
 COMPONENT_BUGDB=	python-mod/netaddr
 
+# This module depends on iPython and cannot support Python 3.3 until iPython
+# is also migrated.
+#
+PYTHON_VERSIONS = 2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/netifaces/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/netifaces/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -32,6 +32,9 @@
 COMPONENT_ARCHIVE_URL=	$(COMPONENT_PROJECT_URL)/$(COMPONENT_ARCHIVE)
 COMPONENT_BUGDB=	python-mod/netifaces
 
+# Syntax issues: not Python 3 ready.
+PYTHON_VERSIONS = 2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/neutronclient/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/neutronclient/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -34,6 +34,9 @@
 COMPONENT_PROJECT_URL=	http://launchpad.net/python-neutronclient
 COMPONENT_BUGDB=	service/neutron
 
+# Syntax issues: not Python 3 ready.
+PYTHON_VERSIONS=	2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/nose-cover3/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/nose-cover3/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/nose/nose-PYVER.p5m	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/nose/nose-PYVER.p5m	Mon May 19 07:37:20 2014 -0700
@@ -23,6 +23,8 @@
 # Copyright (c) 2013, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 
+<transform file path=usr.*/man/.+ -> default mangler.man.stability uncommitted>
+#
 set name=pkg.fmri \
     value=pkg:/library/python/nose-$(PYV)@$(IPS_COMPONENT_VERSION),$(BUILD_VERSION)
 set name=pkg.summary value="Nicer testing for Python"
@@ -36,6 +38,7 @@
 set name=info.upstream-url value=$(COMPONENT_PROJECT_URL)
 set name=org.opensolaris.arc-caseid value=PSARC/2011/198
 set name=org.opensolaris.consolidation value=$(CONSOLIDATION)
+#
 link path=usr/bin/nosetests target=nosetests-$(PYVER) mediator=python \
     mediator-version=$(PYVER)
 file path=usr/bin/nosetests-$(PYVER)
@@ -92,6 +95,10 @@
 file path=usr/lib/python$(PYVER)/vendor-packages/nose/twistedtools.py
 file path=usr/lib/python$(PYVER)/vendor-packages/nose/usage.txt
 file path=usr/lib/python$(PYVER)/vendor-packages/nose/util.py
+file nosetests.1 path=usr/share/man/nosetests-$(PYVER).1
+link path=usr/share/man/nosetests.1 target=nosetests-$(PYVER).1 \
+    mediator=python mediator-version=$(PYVER)
+#
 license nose.license license=LGPLv2.1
 
 # force a group dependency on the optional coverage; pkgdepend work is needed to
--- a/components/python/nose/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/nose/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,4 +1,6 @@
 library/python/setuptools-26
 library/python/setuptools-27
+library/python/setuptools-34
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/novaclient/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/novaclient/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/oslo.config/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/oslo.config/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/passlib/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/passlib/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/paste.deploy/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/paste.deploy/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/paste/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/paste/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2012, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 include ../../../make-rules/shared-macros.mk
 
@@ -32,6 +32,9 @@
 COMPONENT_PROJECT_URL=	http://pythonpaste.org/
 COMPONENT_BUGDB=	python-mod/paste
 
+# Syntax issues: not Python 3 ready.
+PYTHON_VERSIONS=	2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/pbr/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pbr/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/pep8/pep8-GENFRAG.p5m	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pep8/pep8-GENFRAG.p5m	Mon May 19 07:37:20 2014 -0700
@@ -21,8 +21,6 @@
 # Copyright (c) 2013, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 
-<transform file path=usr.*/man/.+ -> default mangler.man.stability uncommitted>
-file path=usr/share/man/man1/pep8.1
 license Oracle.copyright license="Oracle copyright"
 
 # force the rename with an optional dependency on the old name
--- a/components/python/pep8/pep8-PYVER.p5m	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pep8/pep8-PYVER.p5m	Mon May 19 07:37:20 2014 -0700
@@ -21,6 +21,8 @@
 # Copyright (c) 2013, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 
+<transform file path=usr.*/man/.+ -> default mangler.man.stability uncommitted>
+#
 set name=pkg.fmri \
     value=pkg:/library/python/pep8-$(PYV)@$(IPS_COMPONENT_VERSION),$(BUILD_VERSION)
 set name=pkg.summary value="pep8 - Python style guide checker"
@@ -34,6 +36,7 @@
 set name=info.upstream-url value=$(COMPONENT_PROJECT_URL)
 set name=org.opensolaris.arc-caseid value=PSARC/2012/301
 set name=org.opensolaris.consolidation value=$(CONSOLIDATION)
+#
 link path=usr/bin/pep8 target=pep8-$(PYVER) mediator=python \
     mediator-version=$(PYVER)
 file path=usr/bin/pep8-$(PYVER)
@@ -46,14 +49,18 @@
 file path=usr/lib/python$(PYVER)/vendor-packages/pep8-$(COMPONENT_VERSION)-py$(PYVER).egg-info/requires.txt
 file path=usr/lib/python$(PYVER)/vendor-packages/pep8-$(COMPONENT_VERSION)-py$(PYVER).egg-info/top_level.txt
 file path=usr/lib/python$(PYVER)/vendor-packages/pep8.py \
-    pkg.depend.bypass-generate=.*/configparser.* \
+    pkg.depend.bypass-generate=.*/[Cc]onfig[Pp]arser.* \
     pkg.depend.bypass-generate=.*/test_pep8.*
+file usr/share/man/man1/pep8.1 path=usr/share/man/man1/pep8-$(PYVER).1
+link path=usr/share/man/man1/pep8.1 target=pep8-$(PYVER).1 mediator=python \
+    mediator-version=$(PYVER)
+#
 license pep8.license license="expat license"
 
+# force the rename with an optional dependency on the old name
+depend type=optional \
+    fmri=library/python-2/pep8-$(PYV)@1.4.4,5.12-5.12.0.0.0.41.0
+
 # force a dependency on the pep8 package
 depend type=require \
     fmri=library/python/[email protected]$(IPS_COMPONENT_VERSION),$(BUILD_VERSION)
-
-# force the rename with an optional dependency on the old name
-depend type=optional \
-    fmri=library/python-2/pep8-$(PYV)@1.4.4,5.12-5.12.0.0.0.41.0
--- a/components/python/pep8/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pep8/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,6 +1,6 @@
-library/python-2/setuptools-26
-library/python-2/setuptools-27
 library/python/setuptools-26
 library/python/setuptools-27
+library/python/setuptools-34
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/pip/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pip/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,4 +1,6 @@
 library/python/setuptools-26
 library/python/setuptools-27
+library/python/setuptools-34
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/ply/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/ply/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2011, 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2011, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 include ../../../make-rules/shared-macros.mk
 
@@ -34,6 +34,9 @@
 COMPONENT_PROJECT_URL=  http://www.dabeaz.com/ply/
 COMPONENT_BUGDB=	python-mod/ply
 
+# Syntax issues: not Python 3 ready.
+PYTHON_VERSIONS=	2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/prettytable/prettytable-PYVER.p5m	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/prettytable/prettytable-PYVER.p5m	Mon May 19 07:37:20 2014 -0700
@@ -40,9 +40,10 @@
 file path=usr/lib/python$(PYVER)/vendor-packages/prettytable-$(COMPONENT_VERSION)-py$(PYVER).egg-info/SOURCES.txt
 file path=usr/lib/python$(PYVER)/vendor-packages/prettytable-$(COMPONENT_VERSION)-py$(PYVER).egg-info/dependency_links.txt
 file path=usr/lib/python$(PYVER)/vendor-packages/prettytable-$(COMPONENT_VERSION)-py$(PYVER).egg-info/top_level.txt
-# When and only when running under Python 3.x, PrettyTable imports "html".
+# Python 2.x & 3.x, import "html" modules with slightly different syntax:
+# 2.x uses lower-case; 3.x uses upper-case; hence the expression below.
 file path=usr/lib/python$(PYVER)/vendor-packages/prettytable.py \
-    pkg.depend.bypass-generate=.*html.*
+    pkg.depend.bypass-generate=.*[Hh][Tt][Mm][Ll].*
 license prettytable.license license=BSD
 
 # force the rename with an optional dependency on the old name
--- a/components/python/prettytable/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/prettytable/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/py/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/py/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/pyasn1-modules/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pyasn1-modules/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/pyasn1/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pyasn1/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/components/python/pybonjour/patches/pybonjour-python3.patch	Mon May 19 07:37:20 2014 -0700
@@ -0,0 +1,14 @@
+This patch is for Python 3 compatibility.  It has not been submitted upstream,
+as the community appears to have gone dormant.
+
+--- pybonjour-1.1.1/pybonjour.py-orig	2013-02-13 04:39:03.391680773 -0600
++++ pybonjour-1.1.1/pybonjour.py	2013-02-13 04:39:15.452208372 -0600
[email protected]@ -804,7 +804,7 @@ def _create_function_bindings():
+         }
+ 
+ 
+-    for name, (restype, errcheck, outparam, argtypes) in specs.iteritems():
++    for name, (restype, errcheck, outparam, argtypes) in specs.items():
+         prototype = _CFunc(restype, *argtypes)
+ 
+         paramflags = [1] * len(argtypes)
--- a/components/python/pybonjour/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pybonjour/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/pycountry/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pycountry/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/pycparser/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pycparser/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/pycups/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pycups/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -35,6 +35,9 @@
 COMPONENT_ARCHIVE_URL=	http://cyberelk.net/tim/data/pycups/$(COMPONENT_ARCHIVE)
 COMPONENT_BUGDB=	python-mod/pycups
 
+# Fails to compile: not Python 3 ready.
+PYTHON_VERSIONS = 2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/pycurl/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pycurl/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -39,6 +39,9 @@
 
 PATCH_LEVEL = 0
 
+# Syntax issues: not Python 3 ready.
+PYTHON_VERSIONS = 2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/pydns/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pydns/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2013, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 include ../../../make-rules/shared-macros.mk
 
@@ -32,6 +32,9 @@
 COMPONENT_PROJECT_URL=	https://pypi.python.org/pypi/pydns
 COMPONENT_BUGDB=	python-mod/pydns
 
+# Import/syntax issues: not Python 3 ready.
+PYTHON_VERSIONS=	2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/pyflakes/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pyflakes/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,6 +1,6 @@
-library/python-2/setuptools-26
-library/python-2/setuptools-27
 library/python/setuptools-26
 library/python/setuptools-27
+library/python/setuptools-34
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/pygments/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pygments/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,4 +1,6 @@
 library/python/setuptools-26
 library/python/setuptools-27
+library/python/setuptools-34
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/pylxml/pylxml-PYVER.p5m	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pylxml/pylxml-PYVER.p5m	Mon May 19 07:37:20 2014 -0700
@@ -23,6 +23,9 @@
 # Copyright (c) 2011, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 
+# We build Python 3 64-bit only: no need for 32-bit shared objects.
+<transform file path=usr/lib/python3.4/vendor-packages/lxml/[^/]*.so -> drop>
+#
 set name=pkg.fmri \
     value=pkg:/library/python/lxml-$(PYV)@$(IPS_COMPONENT_VERSION),$(BUILD_VERSION)
 set name=pkg.summary \
--- a/components/python/pylxml/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pylxml/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -2,5 +2,6 @@
 library/libxslt
 runtime/python-26
 runtime/python-27
+runtime/python-34
 system/library
 system/library/math
--- a/components/python/pyopenssl/pyopenssl-PYVER.p5m	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pyopenssl/pyopenssl-PYVER.p5m	Mon May 19 07:37:20 2014 -0700
@@ -23,6 +23,9 @@
 # Copyright (c) 2011, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 
+# Python 3 is 64-bit only, so 32-bit shared objects do not belong.
+<transform file path=usr/lib/python3.4/vendor-packages/OpenSSL/[^/]*.so -> drop>
+#
 set name=pkg.fmri \
     value=pkg:/library/python/pyopenssl-$(PYV)@$(IPS_COMPONENT_VERSION),$(BUILD_VERSION)
 set name=pkg.summary value="Python interface to the OpenSSL library"
--- a/components/python/pyopenssl/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pyopenssl/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,4 +1,5 @@
 library/security/openssl
 runtime/python-26
 runtime/python-27
+runtime/python-34
 system/library
--- a/components/python/pyparsing/pyparsing-PYVER.p5m	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pyparsing/pyparsing-PYVER.p5m	Mon May 19 07:37:20 2014 -0700
@@ -40,7 +40,8 @@
 license pyparsing.license license="MIT, GPLv3, BSD"
 
 # force the rename with an optional dependency on the old name
-depend type=optional fmri=library/python-2/[email protected],5.12-5.12.0.0.0.41.0
+depend type=optional \
+    fmri=library/python-2/pyparsing-$(PYV)@2.0.1,5.12-5.12.0.0.0.41.0
 
 # force a dependency on the Python runtime
 depend type=require fmri=__TBD pkg.debug.depend.file=python$(PYVER) \
--- a/components/python/pyparsing/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pyparsing/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/pyrabbit/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pyrabbit/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2012, 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2012, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 include ../../../make-rules/shared-macros.mk
 
@@ -32,6 +32,11 @@
 COMPONENT_PROJECT_URL=	https://github.com/bkjones/pyrabbit
 COMPONENT_BUGDB=	python-mod/pyrabbit
 
+# pyrabbit itself is Python 3 ready: builds & publishes cleanly.  But it
+# depends on httplib2 which has its own dependency issues (see its Makefile
+# for details).  So don't build for Python 3 until dependencies resolved.
+PYTHON_VERSIONS=	2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/pytest-capturelog/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pytest-capturelog/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/pytest-codecheckers/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pytest-codecheckers/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,2 +1,3 @@
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/pytest-cov/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pytest-cov/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2013, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 include ../../../make-rules/shared-macros.mk
 
@@ -32,6 +32,11 @@
 COMPONENT_PROJECT_URL=	https://pypi.python.org/pypi/pytest-cov
 COMPONENT_BUGDB=	python-mod/pytest-plugins
 
+# pytest-cov itself is Python 3 ready (builds & publishes cleanly with usual
+# changes applied) but it depends on cov-core which depends on coverage which
+# needs to be upgraded.  Thus, skip Python 3 until then.
+PYTHON_VERSIONS=	2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/pytest/pytest-PYVER.p5m	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pytest/pytest-PYVER.p5m	Mon May 19 07:37:20 2014 -0700
@@ -66,7 +66,10 @@
 file path=usr/lib/python$(PYVER)/vendor-packages/_pytest/resultlog.py
 file path=usr/lib/python$(PYVER)/vendor-packages/_pytest/runner.py
 file path=usr/lib/python$(PYVER)/vendor-packages/_pytest/skipping.py
-file path=usr/lib/python$(PYVER)/vendor-packages/_pytest/standalonetemplate.py
+# Python 3 has pickle instead of cPickle. The code is written properly, but
+# pkgdepend is not (yet) smart enough to grok the difference; see 18697587.
+file path=usr/lib/python$(PYVER)/vendor-packages/_pytest/standalonetemplate.py \
+    pkg.depend.bypass-generate=.*cPickle.*
 file path=usr/lib/python$(PYVER)/vendor-packages/_pytest/terminal.py
 file path=usr/lib/python$(PYVER)/vendor-packages/_pytest/tmpdir.py
 file path=usr/lib/python$(PYVER)/vendor-packages/_pytest/unittest.py
--- a/components/python/pytest/resolve.deps	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/pytest/resolve.deps	Mon May 19 07:37:20 2014 -0700
@@ -1,4 +1,6 @@
 library/python/setuptools-26
 library/python/setuptools-27
+library/python/setuptools-34
 runtime/python-26
 runtime/python-27
+runtime/python-34
--- a/components/python/python-ldap/Makefile	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/python-ldap/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2013, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 include ../../../make-rules/shared-macros.mk
 
@@ -32,6 +32,9 @@
 COMPONENT_PROJECT_URL=	http://www.python-ldap.org/
 COMPONENT_BUGDB=	python-mod/python-ldap
 
+# This module has syntax issues and this is not Python 3 ready.
+PYTHON_VERSIONS = 2.7 2.6
+
 include $(WS_TOP)/make-rules/prep.mk
 include $(WS_TOP)/make-rules/setup.py.mk
 include $(WS_TOP)/make-rules/ips.mk
--- a/components/python/python26/python-26.p5m	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/python26/python-26.p5m	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2011, 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2011, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 
 <transform file path=usr.*/man/.+ -> default mangler.man.stability uncommitted>
@@ -31,21 +31,34 @@
     value=org.opensolaris.category.2008:Development/Python
 set name=info.source-url value=$(COMPONENT_ARCHIVE_URL)
 set name=info.upstream-url value=$(COMPONENT_PROJECT_URL)
-set name=org.opensolaris.arc-caseid \
-    value=PSARC/2009/043
+set name=org.opensolaris.arc-caseid value=PSARC/2009/043
 set name=org.opensolaris.consolidation value=$(CONSOLIDATION)
 
 # isapython2.6
 file usr/bin/python2.6 path=usr/bin/$(MACH32)/isapython2.6
 file usr/bin/$(MACH64)/python2.6 path=usr/bin/$(MACH64)/isapython2.6
+link path=usr/bin/$(MACH64)/python target=python2.6 mediator=python \
+    mediator-version=2.6
+link path=usr/bin/$(MACH64)/python-config target=python2.6-config \
+    mediator=python mediator-version=2.6
+link path=usr/bin/$(MACH64)/python2.6 target=isapython2.6
 file path=usr/bin/$(MACH64)/python2.6-config pkg.depend.bypass-generate=.*
-
+link path=usr/bin/2to3 target=2to3-2.6 mediator=python mediator-version=2.6
 file usr/bin/2to3 path=usr/bin/2to3-2.6
+link path=usr/bin/idle target=idle-2.6 mediator=python mediator-version=2.6
 file usr/bin/idle path=usr/bin/idle-2.6
+hardlink path=usr/bin/isapython2.6 target=../lib/isaexec
+link path=usr/bin/pydoc target=pydoc-2.6 mediator=python mediator-version=2.6
 file usr/bin/pydoc path=usr/bin/pydoc-2.6
+link path=usr/bin/python target=python2.6 mediator=python mediator-version=2.6
+link path=usr/bin/python-config target=python2.6-config mediator=python \
+    mediator-version=2.6
+
+# python2.6
+link path=usr/bin/python2.6 target=$(MACH32)/isapython2.6
 file path=usr/bin/python2.6-config
-#file path=usr/bin/smtpd.py pkg.tmp.autopyc=false
-#file path=usr/bin/$(MACH64)/smtpd.py pkg.tmp.autopyc=false
+#file path=usr/bin/smtpd.py
+#file path=usr/bin/$(MACH64)/smtpd.py
 
 file path=usr/include/python2.6/Python-ast.h
 file path=usr/include/python2.6/Python.h
@@ -103,9 +116,9 @@
 file path=usr/include/python2.6/pgenheaders.h
 file path=usr/include/python2.6/py_curses.h
 file path=usr/include/python2.6/pyarena.h
-file files/pyconfig.h path=usr/include/python2.6/pyconfig.h
 file path=usr/include/python2.6/pyconfig-32.h
 file path=usr/include/python2.6/pyconfig-64.h
+file files/pyconfig.h path=usr/include/python2.6/pyconfig.h
 file path=usr/include/python2.6/pydebug.h
 file path=usr/include/python2.6/pyerrors.h
 file path=usr/include/python2.6/pyexpat.h
@@ -137,10 +150,14 @@
 file path=usr/include/python2.6/unicodeobject.h
 file path=usr/include/python2.6/warnings.h
 file path=usr/include/python2.6/weakrefobject.h
+link path=usr/lib/$(MACH64)/libpython2.6.so target=libpython2.6.so.1.0
 file path=usr/lib/$(MACH64)/libpython2.6.so.1.0
+link path=usr/lib/$(MACH64)/libpython2.6_db.so target=libpython2.6_db.so.1.0
 file path=usr/lib/$(MACH64)/libpython2.6_db.so.1.0
 file $(MACH64)/llib-lpython26.ln path=usr/lib/$(MACH64)/llib-lpython2.6.ln
+link path=usr/lib/libpython2.6.so target=libpython2.6.so.1.0
 file path=usr/lib/libpython2.6.so.1.0
+link path=usr/lib/libpython2.6_db.so target=libpython2.6_db.so.1.0
 file path=usr/lib/libpython2.6_db.so.1.0
 file llib-lpython26 path=usr/lib/llib-lpython2.6
 file $(MACH32)/llib-lpython26.ln path=usr/lib/llib-lpython2.6.ln
@@ -701,10 +718,10 @@
 file path=usr/lib/python2.6/lib-dynload/ucred.so
 file path=usr/lib/python2.6/lib-dynload/unicodedata.so
 file path=usr/lib/python2.6/lib-dynload/zlib.so
+file path=usr/lib/python2.6/lib2to3/Grammar$(COMPONENT_VERSION).final.0.pickle
 file path=usr/lib/python2.6/lib2to3/Grammar.txt
-file path=usr/lib/python2.6/lib2to3/Grammar$(COMPONENT_VERSION).final.0.pickle
+file path=usr/lib/python2.6/lib2to3/PatternGrammar$(COMPONENT_VERSION).final.0.pickle
 file path=usr/lib/python2.6/lib2to3/PatternGrammar.txt
-file path=usr/lib/python2.6/lib2to3/PatternGrammar$(COMPONENT_VERSION).final.0.pickle
 file path=usr/lib/python2.6/lib2to3/__init__.py
 file path=usr/lib/python2.6/lib2to3/fixer_base.py
 file path=usr/lib/python2.6/lib2to3/fixer_util.py
@@ -839,6 +856,7 @@
 file path=usr/lib/python2.6/profile.py pkg.depend.bypass-generate=.*
 file path=usr/lib/python2.6/pstats.py
 file path=usr/lib/python2.6/pty.py
+link path=usr/lib/python2.6/pyCC target=pycc
 file path=usr/lib/python2.6/py_compile.py
 file path=usr/lib/python2.6/pycc mode=0555
 file path=usr/lib/python2.6/pyclbr.py
@@ -946,37 +964,11 @@
 file path=usr/lib/python2.6/xmllib.py
 file path=usr/lib/python2.6/xmlrpclib.py
 file path=usr/lib/python2.6/zipfile.py
+link path=usr/share/man/man1/python.1 target=python2.6.1 mediator=python \
+    mediator-version=2.6
 file usr/share/man/man1/python.1 path=usr/share/man/man1/python2.6.1
-hardlink path=usr/bin/isapython2.6 target=../lib/isaexec
+#
 license python26.license license=PSFv2
 
-link path=usr/bin/$(MACH64)/python2.6 target=isapython2.6
-
-# python2.6
-link path=usr/bin/python2.6 target=$(MACH32)/isapython2.6
-link path=usr/lib/$(MACH64)/libpython2.6.so target=libpython2.6.so.1.0
-link path=usr/lib/$(MACH64)/libpython2.6_db.so target=libpython2.6_db.so.1.0
-link path=usr/lib/libpython2.6.so target=libpython2.6.so.1.0
-link path=usr/lib/libpython2.6_db.so target=libpython2.6_db.so.1.0
-link path=usr/lib/python2.6/pyCC target=pycc
-
-link path=usr/bin/2to3 target=2to3-2.6 \
-    mediator=python mediator-version=2.6
-link path=usr/bin/idle target=idle-2.6 \
-    mediator=python mediator-version=2.6
-link path=usr/bin/pydoc target=pydoc-2.6 \
-    mediator=python mediator-version=2.6
-link path=usr/bin/python target=python2.6 \
-    mediator=python mediator-version=2.6
-link path=usr/bin/python-config target=python2.6-config \
-    mediator=python mediator-version=2.6
-link path=usr/bin/$(MACH64)/python target=python2.6 \
-    mediator=python mediator-version=2.6
-link path=usr/bin/$(MACH64)/python-config target=python2.6-config \
-    mediator=python mediator-version=2.6
-link path=usr/share/man/man1/python.1 target=python2.6.1 \
-    mediator=python mediator-version=2.6
-
-
 # This optionally brings in the python tk support if tk is installed
 depend type=conditional fmri=library/python/tkinter-26 predicate=runtime/tk-8
--- a/components/python/python27/python-27.p5m	Mon May 19 10:28:03 2014 +0100
+++ b/components/python/python27/python-27.p5m	Mon May 19 07:37:20 2014 -0700
@@ -18,7 +18,7 @@
 #
 # CDDL HEADER END
 #
-# Copyright (c) 2011, 2013, Oracle and/or its affiliates. All rights reserved.
+# Copyright (c) 2011, 2014, Oracle and/or its affiliates. All rights reserved.
 #
 
 <transform file path=usr.*/man/.+ -> default mangler.man.stability uncommitted>
@@ -31,30 +31,39 @@
     value=org.opensolaris.category.2008:Development/Python
 set name=info.source-url value=$(COMPONENT_ARCHIVE_URL)
 set name=info.upstream-url value=$(COMPONENT_PROJECT_URL)
-set name=org.opensolaris.arc-caseid \
-    value=PSARC/2008/514 \
-    value=PSARC/2009/529 \
-    value=PSARC/2011/XXX
+set name=org.opensolaris.arc-caseid value=PSARC/2008/514 value=PSARC/2009/529
 # PSARC 2008/514 Python interface to dlpi(7P)
 # PSARC 2009/529 Python interface to privileges(5) & rbac(5)
 
 set name=org.opensolaris.consolidation value=$(CONSOLIDATION)
-
-license python27.license license=PSFv2
-
+#file path=usr/bin/smtpd.py
+#file path=usr/bin/$(MACH64)/smtpd.py
+#
+file usr/bin/python2.7 path=usr/bin/$(MACH32)/isapython2.7
+link path=usr/bin/$(MACH32)/python2.7 target=isapython2.7
+file usr/bin/$(MACH64)/python2.7 path=usr/bin/$(MACH64)/isapython2.7
+link path=usr/bin/$(MACH64)/python target=python2.7 mediator=python \
+    mediator-version=2.7
+link path=usr/bin/$(MACH64)/python-config target=python2.7-config \
+    mediator=python mediator-version=2.7
+link path=usr/bin/$(MACH64)/python2.7 target=isapython2.7
+#
+file path=usr/bin/$(MACH64)/python2.7-config
+link path=usr/bin/2to3 target=2to3-2.7 mediator=python mediator-version=2.7
+#
 #dir path=usr/lib/$(MACH64)/python2.7
 #dir path=usr/lib/$(MACH64)/python2.7/config
-
+#
 file usr/bin/2to3 path=usr/bin/2to3-2.7
+link path=usr/bin/idle target=idle-2.7 mediator=python mediator-version=2.7
 file usr/bin/idle path=usr/bin/idle-2.7
+hardlink path=usr/bin/isapython2.7 target=../lib/isaexec
+link path=usr/bin/pydoc target=pydoc-2.7 mediator=python mediator-version=2.7
 file usr/bin/pydoc path=usr/bin/pydoc-2.7
-#file path=usr/bin/smtpd.py pkg.tmp.autopyc=false
-#file path=usr/bin/$(MACH64)/smtpd.py pkg.tmp.autopyc=false
-
-file usr/bin/python2.7           path=usr/bin/$(MACH32)/isapython2.7
-file usr/bin/$(MACH64)/python2.7 path=usr/bin/$(MACH64)/isapython2.7
-
-file path=usr/bin/$(MACH64)/python2.7-config
+link path=usr/bin/python target=python2.7 mediator=python mediator-version=2.7
+link path=usr/bin/python-config target=python2.7-config mediator=python \
+    mediator-version=2.7
+link path=usr/bin/python2.7 target=$(MACH32)/isapython2.7
 file path=usr/bin/python2.7-config
 file path=usr/include/python2.7/Python-ast.h
 file path=usr/include/python2.7/Python.h
@@ -115,9 +124,9 @@
 file path=usr/include/python2.7/py_curses.h
 file path=usr/include/python2.7/pyarena.h
 file path=usr/include/python2.7/pycapsule.h
-file files/pyconfig.h path=usr/include/python2.7/pyconfig.h
 file path=usr/include/python2.7/pyconfig-32.h
 file path=usr/include/python2.7/pyconfig-64.h
+file files/pyconfig.h path=usr/include/python2.7/pyconfig.h
 file path=usr/include/python2.7/pyctype.h
 file path=usr/include/python2.7/pydebug.h
 file path=usr/include/python2.7/pyerrors.h
@@ -150,10 +159,15 @@
 file path=usr/include/python2.7/unicodeobject.h
 file path=usr/include/python2.7/warnings.h
 file path=usr/include/python2.7/weakrefobject.h
+link path=usr/lib/$(MACH64)/libpython2.7.so target=libpython2.7.so.1.0
 file path=usr/lib/$(MACH64)/libpython2.7.so.1.0
+link path=usr/lib/$(MACH64)/libpython2.7_db.so target=libpython2.7_db.so.1.0
 file path=usr/lib/$(MACH64)/libpython2.7_db.so.1.0
 file $(MACH64)/llib-lpython27.ln path=usr/lib/$(MACH64)/llib-lpython2.7.ln
 file path=usr/lib/$(MACH64)/pkgconfig/python-2.7.pc
+link path=usr/lib/$(MACH64)/pkgconfig/python.pc target=python-2.7.pc \
+    mediator=python mediator-version=2.7
+link path=usr/lib/libpython2.7.so target=libpython2.7.so.1.0
 #file path=usr/lib/$(MACH64)/python2.7/config/Makefile
 #file path=usr/lib/$(MACH64)/python2.7/config/Setup
 #file path=usr/lib/$(MACH64)/python2.7/config/Setup.config
@@ -164,10 +178,13 @@
 #file path=usr/lib/$(MACH64)/python2.7/config/makesetup mode=0555
 #file path=usr/lib/$(MACH64)/python2.7/config/python.o
 file path=usr/lib/libpython2.7.so.1.0
+link path=usr/lib/libpython2.7_db.so target=libpython2.7_db.so.1.0
 file path=usr/lib/libpython2.7_db.so.1.0
 file llib-lpython27 path=usr/lib/llib-lpython2.7
 file $(MACH32)/llib-lpython27.ln path=usr/lib/llib-lpython2.7.ln
 file path=usr/lib/pkgconfig/python-2.7.pc
+link path=usr/lib/pkgconfig/python.pc target=python-2.7.pc mediator=python \
+    mediator-version=2.7
 file path=usr/lib/python2.7/BaseHTTPServer.py
 file path=usr/lib/python2.7/Bastion.py
 file path=usr/lib/python2.7/CGIHTTPServer.py
@@ -596,7 +613,6 @@
 file path=usr/lib/python2.7/json/scanner.py
 file path=usr/lib/python2.7/json/tool.py
 file path=usr/lib/python2.7/keyword.py
-file path=usr/lib/python2.7/lib-dynload/Python-$(COMPONENT_VERSION)-py2.7.egg-info
 file path=usr/lib/python2.7/lib-dynload/64/_bisect.so
 file path=usr/lib/python2.7/lib-dynload/64/_codecs_cn.so
 file path=usr/lib/python2.7/lib-dynload/64/_codecs_hk.so
@@ -662,6 +678,7 @@
 file path=usr/lib/python2.7/lib-dynload/64/ucred.so
 file path=usr/lib/python2.7/lib-dynload/64/unicodedata.so
 file path=usr/lib/python2.7/lib-dynload/64/zlib.so
+file path=usr/lib/python2.7/lib-dynload/Python-$(COMPONENT_VERSION)-py2.7.egg-info
 file path=usr/lib/python2.7/lib-dynload/_bisect.so
 file path=usr/lib/python2.7/lib-dynload/_codecs_cn.so
 file path=usr/lib/python2.7/lib-dynload/_codecs_hk.so
@@ -729,10 +746,10 @@
 file path=usr/lib/python2.7/lib-dynload/ucred.so
 file path=usr/lib/python2.7/lib-dynload/unicodedata.so
 file path=usr/lib/python2.7/lib-dynload/zlib.so
+file path=usr/lib/python2.7/lib2to3/Grammar$(COMPONENT_VERSION).final.0.pickle
 file path=usr/lib/python2.7/lib2to3/Grammar.txt
-file path=usr/lib/python2.7/lib2to3/Grammar$(COMPONENT_VERSION).final.0.pickle
+file path=usr/lib/python2.7/lib2to3/PatternGrammar$(COMPONENT_VERSION).final.0.pickle
 file path=usr/lib/python2.7/lib2to3/PatternGrammar.txt
-file path=usr/lib/python2.7/lib2to3/PatternGrammar$(COMPONENT_VERSION).final.0.pickle
 file path=usr/lib/python2.7/lib2to3/__init__.py
 file path=usr/lib/python2.7/lib2to3/__main__.py
 file path=usr/lib/python2.7/lib2to3/btm_matcher.py
@@ -1002,28 +1019,11 @@
 file path=usr/lib/python2.7/xmllib.py
 file path=usr/lib/python2.7/xmlrpclib.py
 file path=usr/lib/python2.7/zipfile.py
+link path=usr/share/man/man1/python.1 target=python2.7.1 mediator=python \
+    mediator-version=2.7
 file path=usr/share/man/man1/python2.7.1
-
-hardlink path=usr/bin/isapython2.7 target=../lib/isaexec
-
-link path=usr/bin/$(MACH32)/python2.7 target=isapython2.7
-link path=usr/bin/$(MACH64)/python2.7 target=isapython2.7
-link path=usr/bin/python2.7 target=$(MACH32)/isapython2.7
-link path=usr/lib/$(MACH64)/libpython2.7.so target=libpython2.7.so.1.0
-link path=usr/lib/$(MACH64)/libpython2.7_db.so target=libpython2.7_db.so.1.0
-link path=usr/lib/libpython2.7.so target=libpython2.7.so.1.0
-link path=usr/lib/libpython2.7_db.so target=libpython2.7_db.so.1.0
-
-link path=usr/bin/2to3 target=2to3-2.7 mediator=python mediator-version=2.7
-link path=usr/bin/idle target=idle-2.7 mediator=python mediator-version=2.7
-link path=usr/bin/pydoc target=pydoc-2.7 mediator=python mediator-version=2.7
-link path=usr/bin/python target=python2.7 mediator=python mediator-version=2.7
-link path=usr/bin/python-config target=python2.7-config mediator=python mediator-version=2.7
-link path=usr/bin/$(MACH64)/python target=python2.7 mediator=python mediator-version=2.7
-link path=usr/bin/$(MACH64)/python-config target=python2.7-config mediator=python mediator-version=2.7
-link path=usr/lib/pkgconfig/python.pc target=python-2.7.pc mediator=python mediator-version=2.7
-link path=usr/lib/$(MACH64)/pkgconfig/python.pc target=python-2.7.pc mediator=python mediator-version=2.7
-link path=usr/share/man/man1/python.1 target=python2.7.1 mediator=python mediator-version=2.7
+#
+license python27.license license=PSFv2
 
 # This optionally brings in the python tk support if tk is installed
 depend type=conditional fmri=library/python/tkinter-27 predicate=runtime/tk-8
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/components/python/python34/Makefile	Mon May 19 07:37:20 2014 -0700
@@ -0,0 +1,146 @@
+#
+# CDDL HEADER START
+#
+# The contents of this file are subject to the terms of the
+# Common Development and Distribution License (the "License").
+# You may not use this file except in compliance with the License.
+#
+# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
+# or http://www.opensolaris.org/os/licensing.
+# See the License for the specific language governing permissions
+# and limitations under the License.
+#
+# When distributing Covered Code, include this CDDL HEADER in each
+# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
+# If applicable, add the following below this CDDL HEADER, with the
+# fields enclosed by brackets "[]" replaced with your own identifying
+# information: Portions Copyright [yyyy] [name of copyright owner]
+#
+# CDDL HEADER END
+#
+
+#
+# Copyright (c) 2011, 2014, Oracle and/or its affiliates. All rights reserved.
+#
+
+include ../../../make-rules/shared-macros.mk
+
+COMPONENT_NAME=		Python
+COMPONENT_VERSION=	3.4.0
+COMPONENT_PROJECT_URL=	http://python.org/
+COMPONENT_SRC=		$(COMPONENT_NAME)-$(COMPONENT_VERSION)
+COMPONENT_ARCHIVE=	$(COMPONENT_SRC).tar.xz
+COMPONENT_ARCHIVE_HASH=	\
+    sha256:f13686c0a2d45e7146759e9d5d1cbd8097a0606483c0cf7730e1e13f58b14cbe
+COMPONENT_ARCHIVE_URL=	$(COMPONENT_PROJECT_URL)ftp/python/$(COMPONENT_VERSION)/$(COMPONENT_ARCHIVE)
+COMPONENT_BUGDB=	utility/python
+
+include $(WS_TOP)/make-rules/prep.mk
+include $(WS_TOP)/make-rules/configure.mk
+include $(WS_TOP)/make-rules/ips.mk
+include $(WS_TOP)/make-rules/lint-libraries.mk
+
+# Need to preserve timestamp for Grammar files.  If the pickle files are older,
+# Python will try to rebuild them.
+PKGSEND_PUBLISH_OPTIONS += -T \*Grammar\*.txt
+PKGSEND_PUBLISH_OPTIONS += -T \*Grammar\*.pickle
+
+# We patch auto* files, so regenerate headers and configure
+COMPONENT_PREP_ACTION = \
+	(cd $(@D) ; autoheader ; autoconf)
+
+# The DTrace patch needs this file to be mode 0755.
+COMPONENT_PRE_BUILD_ACTION=($(CHMOD) +x \
+    $(SOURCE_DIR)/Include/pydtrace_offsets.sh)
+
+# we don't want to leak $(CC_BITS) into BASECFLAGS as it causes problems with
+# python-config
+CC +=	$(CFLAGS)
+
+C99MODE=
+CPPFLAGS +=	-IPython
+
+# to find the ncurses headers
+CPPFLAGS +=	-I/usr/include/ncurses
+# enable large files how they did in JDS
+CPPFLAGS +=	-D_LARGEFILE64_SOURCE
+
+# libffi for _ctypes
+CPPFLAGS +=	$(shell pkg-config --cflags-only-I libffi)
+
+# because python links with $(CC) ... $(LDFLAGS) ...
+LDFLAGS =	$(CC_BITS) $(CC_PIC)
+
+# build pic
+CFLAGS +=	$(CC_PIC)
+
+# The python build is profile-guided for studio; to see the benefits of that,
+# Python must be compiled with -xO5 and a different build target must be used.
+# Use of xprofile requires that the same options be used during compilation and
+# linking.  The targets chosen are based on Solaris 11 minimum supported system
+# requirements.
+COMPONENT_BUILD_TARGETS = profile-opt
+XPROFILE_DIR = $(BUILD_DIR_$(BITS))/.profile
+PYFLAGS.i386 = -xtarget=opteron -xarch=sse2 -xcache=generic
+PYFLAGS.sparc =
+CFLAGS += -xO5 $(PYFLAGS.$(MACH))
+LDFLAGS += -xO5 $(PYFLAGS.$(MACH))
+
+# add /usr/gnu/lib to the library search/run path
+LDFLAGS.64 = -R/usr/gnu/lib/$(MACH64) -L/usr/gnu/lib/$(MACH64)
+LDFLAGS += $(LDFLAGS.$(BITS))
+
+# Python puts its header files in a special place.
+LINT_FLAGS +=	-I$(SOURCE_DIR)/Include
+
+CONFIGURE_OPTIONS  +=		--infodir=$(CONFIGURE_INFODIR)
+CONFIGURE_OPTIONS  +=		--enable-shared
+CONFIGURE_OPTIONS  +=		--with-dtrace
+CONFIGURE_OPTIONS  +=		--with-system-expat
+CONFIGURE_OPTIONS  +=		--with-system-ffi
+CONFIGURE_OPTIONS  +=		--without-gcc
+# Building with pymalloc is the default, but that causes core dumps;
+# see http://bugs.python.org/issue21412 for details.
+CONFIGURE_OPTIONS  +=		--without-pymalloc
+CONFIGURE_OPTIONS  +=		--without-ensurepip
+CONFIGURE_OPTIONS  +=		--enable-ipv6
+CONFIGURE_OPTIONS  +=		CPPFLAGS="$(CPPFLAGS)"
+CONFIGURE_OPTIONS  +=		LDFLAGS="$(LDFLAGS)"
+CONFIGURE_OPTIONS  +=		CFLAGS="$(CFLAGS)"
+CONFIGURE_OPTIONS  +=		DFLAGS="-$(BITS)"
+CONFIGURE_OPTIONS  +=		XPROFILE_DIR="$(XPROFILE_DIR)"
+
+COMPONENT_BUILD_ENV  +=		DFLAGS="-$(BITS)"
+COMPONENT_BUILD_ENV  +=		XPROFILE_DIR="$(XPROFILE_DIR)"
+
+# Some tests have non-ASCII characters encoded for international domain names;
+# the publish step will fail in 'pkgdepend generate' without this:
+COMPONENT_PUBLISH_ENV  +=	LC_ALL=en_US.UTF-8
+
+# 64 bit shared objects need to go in a 64-bit directory
+COMPONENT_INSTALL_ARGS.64 += DESTSHARED=$(CONFIGURE_PREFIX)/lib/python3.4/lib-dynload
+
+ASLR_MODE = $(ASLR_ENABLE)
+
+# common targets
+build:		$(BUILD_64)
+install:	$(INSTALL_64)
+
+# Using "-uall,-network" ensures all tests are run except the network tests.
+# The network tests contain many expected failures when run behind a firewall.
+# The "-v" ensures verbose mode.  You can set TESTOPTS_PYTHON_TEST to a
+# particular test if you want to run just one test.  For example,
+# $ TESTOPTS_PYTHON_TEST=test_sys gmake -k test
+# Note that when a test succeeds, the builds/*/.tested file gets created.  You
+# may need to remove these files, or run "gmake clobber" or "gmake clean"
+# between tests.
+#
+COMPONENT_TEST_ENV = EXTRATESTOPTS="-v -uall,-network $(TESTOPTS_PYTHON_TEST)"
+# Prevent the tests from getting stuck waiting for input.
+COMPONENT_TEST_TARGETS = test < /dev/null
+
+test:				$(TEST_64)
+
+BUILD_PKG_DEPENDENCIES =	$(BUILD_TOOLS)
+
+include $(WS_TOP)/make-rules/depend.mk
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/components/python/python34/patches/00-dtrace.patch	Mon May 19 07:37:20 2014 -0700
@@ -0,0 +1,2036 @@
+This patch comes from upstream:
+http://www.jcea.es/artic/python_dtrace-3_4_0_0de6441eedb7.txt
+http://www.jcea.es/artic/python_dtrace.htm
+Follow http://bugs.python.org/issue13405 for plans to get it
+integrated into the main tree.
+
+--- Python-3.4.0/Doc/library/debug.rst
++++ Python-3.4.0/Doc/library/debug.rst
[email protected]@ -15,4 +15,5 @@
+    profile.rst
+    timeit.rst
+    trace.rst
++   dtrace.rst
+    tracemalloc.rst
+--- /dev/null
++++ Python-3.4.0/Doc/library/dtrace.rst
[email protected]@ -0,0 +1,183 @@
++:mod:`dtrace` --- DTrace probes for Python
++===============================================
++
++.. module:: dtrace
++   :synopsis: DTrace probes for Python.
++
++**Source code:** :source:`Lib/dtrace.py`
++
++--------------
++
++The :mod:`dtrace` module indicates if the CPython executable currently
++running has been compiled with DTrace probes support.
++
++.. impl-detail::
++
++   DTrace probes are implementation details of the CPython interpreter!
++   No garantees are made about probe compatibility between versions of
++   CPython. DTrace scripts can stop working or work incorrectly without
++   warning when changing CPython versions.
++
++The :mod:`dtrace` module defines the following variable:
++
++
++.. data:: available
++
++   The variable will be ``True`` if the current CPython interpreter was
++   compiled with DTrace probe support. ``False`` if not.
++   
++
++DTrace probes
++-------------
++
++DTrace scripts are run externally to CPython. DTrace probes export
++selected events inside CPython interpreter in order to make them
++accessible to external scripts.
++
++The probes are exported through the "python" provider. The available
++probes are defined in the file :file:`Include/pydtrace.d`.
++
++To learn how to use DTrace, read `DTrace User Guide
++<http://docs.oracle.com/cd/E19253-01/819-5488/>`_.
++
++.. opcode:: function-entry (arg0, arg1, arg2)
++
++   Fires when python code enters a new function. *arg0* is sourcecode
++   file path, *arg1* is the name of the funcion called, and *arg2* is
++   line number.
++
++   The probe is not fired if Python code calls C functions.
++
++.. opcode:: function-return (arg0, arg1, arg2)
++
++   Fires when Python code finishes execution of a function. Parameters
++   are the same as in ``function-entry``.
++
++   The probe is not fired if the finishing function is written in C.
++
++.. opcode:: line (arg0, arg1, arg2)
++
++   Fires when Python code changes the execution line. Parameters are the
++   same as in ``function-entry``.
++
++   The probe is not fired in C functions.
++
++.. opcode:: gc-start (arg0)
++
++   Fires when the Python interpreter starts a garbage collection cycle.
++   *arg0* is the generation to scan, like :func:`gc.collect()`.
++
++.. opcode:: gc-done (arg0)
++
++   Fires when the Python interpreter finishes a garbage collection
++   cycle. *arg0* is the number of collected objects.
++
++.. opcode:: instance-new-start (arg0, arg1)
++
++   Fires when an object instanciation starts. *arg0* is the class name,
++   *arg1* is the filename where the class is defined.
++
++   The probe is not fired for most C code object creations.
++
++.. opcode:: instance-new-done (arg0, arg1)
++
++   Fires when an object instanciation finishes. Parameters are the same
++   as in ``instance-new-done``.
++
++   The probe is not fired for most C code object creations.
++
++.. opcode:: instance-delete-start (arg0, arg1)
++
++   Fires when an object instance is going to be destroyed. Parameters
++   are the same as in ``instance-new-done``.
++
++   The probe is not fired for most C code object destructions.
++
++.. opcode:: instance-delete-done (arg0, arg1)
++
++   Fires when an object instance has been destroyed. parameters are the
++   same as in ``instance-new-done``.
++
++   Between an ``instance-delete-start`` and corresponding
++   ``instance-delete-done`` others probes can fire if, for instance,
++   deletion of an instance creates a deletion cascade.
++
++   The probe is not fired for most C code object destructions.
++
++
++Python stack
++------------
++
++When a DTrace probe is fired, the DTrace script can examine the stack.
++Since CPython is a Python interpreter coded in C, the stack will show C
++functions, with no direct relation to the Python code currently being
++executed.
++
++Using the special "jstack()" DTrace function, the user will be given
++hints about the python program stack, if possible. In particular, the
++augmented stack will show python function calls, filename, name
++of the function or method, and the line number.
++
++DTrace scripts examples
++-----------------------
++
++DTrace python provider is suffixed by the pid of the process to monitor.
++In the examples, the pid will be 9876.
++
++Show the time spent doing garbage collection (in nanoseconds)::
++
++  python9876:::gc-start
++  {
++      self->t = timestamp;
++  }
++
++  python9876:::gc-done
++  /self->t/
++  {
++      printf("%d", timestamp-self->t);
++      self->t = 0;
++  }
++
++Count how many instances are created of each class::
++
++  python9876:::instance-new-start
++  {
++      @v[copyinstr(arg1), copyinstr(arg0)] = count();
++  }
++
++Observe time spent in object destruction, useful if datastructures are
++complicated and deletion of an object can create a cascade effect::
++
++  python9876:::instance-delete-start
++  /self->t==0/
++  {
++      self->t = timestamp;
++      self->level = 0;
++  }
++
++  python9876:::instance-delete-start
++  /self->t/
++  {
++      self->level += 1;
++  }
++
++  python9876:::instance-delete-done
++  /(self->level) && (self->t)/
++  {
++      self->level -= 1;
++  }
++
++  python9876:::instance-delete-done
++  /(self->level==0) && (self->t)/
++  {
++      @time = quantize(timestamp-self->t);
++      self->t = 0;
++  }
++
++To know which python source code lines create new TCP/IP connections::
++
++  pid9876::sock_connect:entry
++  {
++      @conn[jstack()] = count();
++  }
++
+--- Python-3.4.0/Include/code.h
++++ Python-3.4.0/Include/code.h
[email protected]@ -7,6 +7,8 @@
+ extern "C" {
+ #endif
+ 
++#include "pyconfig.h"
++
+ /* Bytecode object */
+ typedef struct {
+     PyObject_HEAD
[email protected]@ -28,6 +30,9 @@
+     int co_firstlineno;		/* first source line number */
+     PyObject *co_lnotab;	/* string (encoding addr<->lineno mapping) See
+ 				   Objects/lnotab_notes.txt for details. */
++#ifdef WITH_DTRACE
++    unsigned short *co_linenos; /* dtrace stack helper */
++#endif
+     void *co_zombieframe;     /* for optimization only (see frameobject.c) */
+     PyObject *co_weakreflist;   /* to support weakrefs to code objects */
+ } PyCodeObject;
+--- /dev/null
++++ Python-3.4.0/Include/pydtrace.d
[email protected]@ -0,0 +1,177 @@
++provider python {
++    probe function__entry(const char *, const char *, int);
++    probe function__return(const char *, const char *, int);
++    probe instance__new__start(const char *, const char *);
++    probe instance__new__done(const char *, const char *);
++    probe instance__delete__start(const char *, const char *);
++    probe instance__delete__done(const char *, const char *);
++    probe line(const char *, const char *, int);
++    probe gc__start(int);
++    probe gc__done(long);
++};
++
++#pragma D attributes Evolving/Evolving/Common provider python provider
++#pragma D attributes Private/Private/Common provider python module
++#pragma D attributes Private/Private/Common provider python function
++#pragma D attributes Evolving/Evolving/Common provider python name
++#pragma D attributes Evolving/Evolving/Common provider python args
++
++
++
++#ifdef PYDTRACE_STACK_HELPER
++/*
++ * Python ustack helper.  This relies on the first argument (PyFrame *) being
++ * on the stack; see Python/ceval.c for the contortions we go through to ensure
++ * this is the case.
++ *
++ * On x86, the PyFrame * is two slots up from the frame pointer; on SPARC, it's
++ * eight.
++ *
++ * Some details about this in "Python and DTrace in build 65":
++ * http://blogs.oracle.com/levon/entry/python_and_dtrace_in_build
++ */
++
++/*
++ * Yes, this is as gross as it looks. DTrace cannot handle static functions,
++ * and our stat_impl.h has them in ILP32.
++ */
++#define _SYS_STAT_H
++
++/*
++** When compiling in 32 bits:
++** - Early inclusion to avoid problems with
++**   _FILE_OFFSET_BITS redefined.
++** - Also, we must "undef" _POSIX_PTHREAD_SEMANTICS
++**   to avoid error compiling this source.
++*/
++#include "pyconfig.h"
++#undef _POSIX_PTHREAD_SEMANTICS
++
++#include <stdio.h>
++#include <sys/types.h>
++
++#include "pyport.h"
++#include "pyatomic.h"
++/* "string" type is used in dtrace */
++#define string	stringDTRACE
++#include "object.h"
++#include "pystate.h"
++#include "pyarena.h"
++#include "pythonrun.h"
++#include "compile.h"
++#include "frameobject.h"
++/* Avoid a compile error because a symbol (equivalent) redefinition */
++#undef __STDC__
++/* "self" has an special meaning for dtrace */
++#define self	selfDTRACE
++#include "unicodeobject.h"
++#undef string
++#undef self
++
++#include "pydtrace_offsets.h"
++
++#if defined(__i386)
++#define	startframe PyEval_EvalFrameEx
++#define	endframe AFTER_PyEval_EvalFrameEx
++#elif defined(__amd64)
++#define	startframe PyEval_EvalFrameExReal
++#define	endframe AFTER_PyEval_EvalFrameExReal
++#elif defined(__sparc)
++#define	startframe PyEval_EvalFrameExReal
++#define	endframe AFTER_PyEval_EvalFrameExReal
++#endif
++
++#ifdef __sparcv9
++#define	STACK_BIAS (2048-1)
++#else
++#define	STACK_BIAS 0
++#endif
++
++#define	at_evalframe(addr) \
++    ((uintptr_t)addr >= ((uintptr_t)&``startframe) && \
++     (uintptr_t)addr < ((uintptr_t)&``endframe))
++#define	probe dtrace:helper:ustack:
++#define	print_result(r) (r)
++
++#if defined(__i386) || defined(__amd64)
++#define	frame_ptr_addr ((uintptr_t)arg1 + sizeof(uintptr_t) * 2)
++#elif defined(__sparc)
++#define	frame_ptr_addr ((uintptr_t)arg1 + STACK_BIAS + sizeof(uintptr_t) * 8)
++#else
++#error unknown architecture
++#endif
++
++/* startframe and endframe are macro-expansions */
++extern uintptr_t startframe;
++extern uintptr_t endframe;
++
++
++#define	copyin_obj(addr, obj) ((obj *)copyin((uintptr_t)(addr), sizeof(obj)))
++
++/*
++** Check if the string is ASCII. Don't use bitfields, because the
++** packing in GCC and D are different. BEWARE!!!.
++** The size of the structures are also different!. That is the reason for
++** the negative offset. BEWARE!!!
++*/
++#define pystr_len(addr) ((*(((char *)addr)+PYDTRACE_ASCII_OFFSET)) & PYDTRACE_ASCII_MASK ? \
++		(addr)->_base.length : \
++		*(Py_ssize_t *)(((char *)(addr)) + PYDTRACE_UTF8_LENGTH_OFFSET))
++#define pystr_addr(addr, addr2) ((*(((char *)addr)+PYDTRACE_ASCII_OFFSET)) & PYDTRACE_ASCII_MASK ? \
++		(char *)(((char *)(addr2)) + PYDTRACE_PyASCIIObject_SIZE) : \
++		(char *)*(uintptr_t *)(((char *)(addr)) + PYDTRACE_UTF8_OFFSET))
++
++#define	add_digit(nr, div) (((nr) / div) ? \
++    (this->result[this->pos++] = '0' + (((nr) / div) % 10)) : \
++    (this->result[this->pos] = '\0'))
++#define	add_char(c) (this->result[this->pos++] = c)
++
++probe /at_evalframe(arg0)/
++{
++	this->framep = *(uintptr_t *)copyin(frame_ptr_addr, sizeof(uintptr_t));
++	this->frameo = copyin_obj(this->framep, PyFrameObject);
++	this->codep = this->frameo->f_code;
++	this->codeo = copyin_obj(this->codep, PyCodeObject);
++	/* If we just enter a function, show the definition line */
++	this->lineno = this->codeo->co_firstlineno +
++		(this->frameo->f_lasti == -1 ? 0 :
++		*copyin_obj(this->codeo->co_linenos + this->frameo->f_lasti,
++			unsigned short));
++	this->filenameo = copyin_obj(this->codeo->co_filename, PyCompactUnicodeObject);
++	this->len_filename = pystr_len(this->filenameo);
++	this->nameo = copyin_obj(this->codeo->co_name, PyCompactUnicodeObject);
++	this->len_name = pystr_len(this->nameo);
++	this->len = 1 + (this->len_filename) + 1 + 5 + 2 +
++	    (this->len_name) + 1 + 1;
++
++	this->result = (char *)alloca(this->len);
++	this->pos = 0;
++	add_char('@');
++
++	copyinto((uintptr_t)pystr_addr(this->filenameo, this->codeo->co_filename), this->len_filename, this->result+this->pos);
++	this->pos += this->len_filename;
++
++	add_char(':');
++	add_digit(this->lineno, 10000);
++	add_digit(this->lineno, 1000);
++	add_digit(this->lineno, 100);
++	add_digit(this->lineno, 10);
++	add_digit(this->lineno, 1);
++	add_char(' ');
++	add_char('(');
++	
++	copyinto((uintptr_t)pystr_addr(this->nameo, this->codeo->co_name), this->len_name, this->result+this->pos);
++	this->pos += this->len_name;
++
++	add_char(')');
++	this->result[this->pos] = '\0';
++	print_result(stringof(this->result));
++}
++
++probe /!at_evalframe(arg0)/
++{
++	NULL;
++}
++
++#endif  /* PYDTRACE_STACK_HELPER */
++
+--- /dev/null
++++ Python-3.4.0/Include/pydtrace_offsets.c
[email protected]@ -0,0 +1,40 @@
++#include "Python.h"
++#include "unicodeobject.h"
++#include <stdlib.h>
++#include <stdio.h>
++
++int main(int argc, const char* argv[]) {
++    PyCompactUnicodeObject o;
++    unsigned char *p = (unsigned char *)(&o);
++
++    if (argc != 3) {
++        printf("Parameter number incorrect\n");
++        exit(1);
++    }
++
++    memset(&o, 0, sizeof(o));
++    o._base.state.ascii = 1;
++    while (!*p) p++;
++
++    printf("/* File autogenerated. DO NOT MODIFY MANUALLY */\n");
++    printf("\n");
++    printf("#ifndef PYDTRACE_OFFSETS_H\n");
++    printf("#define PYDTRACE_OFFSETS_H\n");
++    printf("\n");
++    printf("#define PYDTRACE_ASCII_OFFSET %d\n",
++            p-(unsigned char *)(&o));
++    printf("#define PYDTRACE_ASCII_MASK %d\n", *p);
++    printf("#define PYDTRACE_PyASCIIObject_SIZE %d\n",
++            sizeof(PyASCIIObject));
++    printf("#define PYDTRACE_UTF8_LENGTH_OFFSET %d\n",
++            offsetof(PyCompactUnicodeObject, utf8_length));
++    printf("#define PYDTRACE_UTF8_OFFSET %d\n",
++            offsetof(PyCompactUnicodeObject, utf8));
++    printf("\n");
++    printf("#define AFTER_PyEval_EvalFrameEx      %s\n", argv[1]);
++    printf("#define AFTER_PyEval_EvalFrameExReal  %s\n", argv[2]);
++    printf("\n");
++    printf("#endif\n");
++    return 0;
++}
++
+new file mode 100755
+--- /dev/null
++++ Python-3.4.0/Include/pydtrace_offsets.sh
[email protected]@ -0,0 +1,32 @@
++#!/bin/sh
++
++DTRACE_NM=$1
++CEVAL_O=$2
++PYDTRACE_OFFSETS=$3
++if test "$DTRACE_NM" = "OTHER" ; then
++    $PYDTRACE_OFFSETS \
++		"`nm -n $CEVAL_O | grep \" T \" | \
++		sed -n \"/ T PyEval_EvalFrameEx$/{n;p;}\" | \
++		sed \"s/.* T \(.*\)$/\1/\"`" \
++		"`nm -n $CEVAL_O | grep \" T \" | \
++		sed -n \"/ T PyEval_EvalFrameExReal$/{n;p;}\" | \
++		sed \"s/.* T \(.*\)$/\1/\"`"
++fi
++if test "$DTRACE_NM" = "SOLARIS" ; then 
++    $PYDTRACE_OFFSETS \
++		"`/usr/ccs/bin/nm -n $CEVAL_O | \
++		/usr/bin/grep \"\\|FUNC \\|\" | \
++		/usr/bin/grep -v \"\\|IGNORE \\|\" | \
++		/usr/bin/grep -v \"\\|UNDEF  \\|\" | \
++		/usr/bin/tr -d \"\\[\\]\\|\" | sort -n | \
++		sed -n \"/ PyEval_EvalFrameEx$/{n;p;}\" | \
++		sed \"s/.* \([a-zA-Z0-9_]*\)$/\1/\"`" \
++		"`/usr/ccs/bin/nm -n $CEVAL_O | \
++		/usr/bin/grep \"\\|FUNC \\|\" | \
++		/usr/bin/grep -v \"\\|UNDEF  \\|\" | \
++		/usr/bin/grep -v \"\\|IGNORE \\|\" | \
++	       	/usr/bin/tr -d \"\\[\\]\\|\" | sort -n | \
++		sed -n \"/ PyEval_EvalFrameExReal$/{n;p;}\" | \
++		sed \"s/.* \([a-zA-Z0-9_]*\)$/\1/\"`"
++fi
++
+--- /dev/null
++++ Python-3.4.0/Lib/test/dtrace_sample.py
[email protected]@ -0,0 +1,80 @@
++# Sample script for use by test_dtrace.py
++# DO NOT MODIFY THIS FILE IN ANY WAY WITHOUT UPDATING test_dtrace.py!!!!!
++
++import gc
++
++def function_1() :
++    pass
++
++# Check stacktrace
++def function_2() :
++    function_1()
++
++# CALL_FUNCTION_VAR
++def function_3(dummy, dummy2) :
++    pass
++
++# CALL_FUNCTION_KW
++def function_4(**dummy) :
++    pass
++
++# CALL_FUNCTION_VAR_KW
++def function_5(dummy, dummy2, **dummy3) :
++    pass
++
++def test_entry_return_and_stack() :
++    function_1()
++    function_2()
++    function_3(*(1,2))
++    function_4(**{"test":42})
++    function_5(*(1,2), **{"test":42})
++
++def test_line() :
++    a = 1  # Preamble
++    for i in range(2) :
++        a = i
++        b = i+2
++        c = i+3
++        d = a + b +c
++    a = 1  # Epilogue
++
++def test_unicode_entry_return_and_stack() :
++    def únícódé() :
++        pass
++    únícódé()
++
++def test_instance_creation_destruction() :
++    class old_style_class() :
++        pass
++    class new_style_class(object) :
++        pass
++
++    a = old_style_class()
++    del a
++    gc.collect()
++    b = new_style_class()
++    del b
++    gc.collect()
++
++    a = old_style_class()
++    del old_style_class
++    gc.collect()
++    b = new_style_class()
++    del new_style_class
++    gc.collect()
++    del a
++    gc.collect()
++    del b
++    gc.collect()
++
++def test_garbage_collection() :
++    gc.collect()
++
++
++if __name__ == "__main__":
++    test_entry_return_and_stack()
++    test_line()
++    test_unicode_entry_return_and_stack()
++    test_instance_creation_destruction()
++    test_garbage_collection()
++
+--- /dev/null
++++ Python-3.4.0/Lib/test/test_dtrace.py
[email protected]@ -0,0 +1,447 @@
++import sys, unittest, subprocess, os.path, dis, types, re
++import dtrace
++from test.support import TESTFN, run_unittest, findfile
++
++sample = os.path.abspath(findfile("dtrace_sample.py"))
++if not dtrace.available :
++    raise unittest.SkipTest("dtrace support not compiled in")
++
++def normalize(data) :
++    # DTRACE keeps a per-CPU buffer, and when showing the fired probes,
++    # buffers are concatenated. So if the operating system moves our
++    # thread around, the straight result can be "non causal".
++    # So we add timestamps to the probe firing, and sort by that field.
++
++    result = data if isinstance(data, str) else data.decode("ascii")
++    # When compiling with '--with-pydebug'
++    result = "".join(re.split("\[[0-9]+ refs\]", result))
++
++    try :
++        result = [i.split("\t") \
++                for i in result.replace("\r", "").split("\n") if len(i)]
++        result.sort(key = lambda i: int(i[0]))
++        result = "".join((i[1] for i in result))
++        result = result.replace(" ", "")
++    except :
++        # If something goes wrong, rebuild the value so we can see the
++        # real result when the assert fails.
++        result = data if isinstance(data, str) else data.decode("ascii")
++        result = result.replace("\r", "").replace("\n", "")
++    return result
++
++dscript = """
++pid$target::PyEval_EvalCode:entry
++"""
++dscript = dscript.replace("\r", "").replace("\n", "")
++result, _ = subprocess.Popen(["dtrace", "-q", "-l", "-n", dscript,
++    "-c", "%s %s" %(sys.executable, sample)], stdout=subprocess.PIPE,
++    stderr=subprocess.STDOUT).communicate()
++if result.decode("ascii").split("\n")[1].split()[-2:] != \
++        ["PyEval_EvalCode", "entry"] :
++    result2 = repr(result)
++    raise unittest.SkipTest("dtrace seems not to be working. " + \
++        "Please, check your privileges. " +
++        "Result: " +result2)
++
++class DTraceTestsNormal(unittest.TestCase) :
++    def setUp(self) :
++        self.optimize = False
++
++    def test_function_entry_return(self) :
++        dscript = """
++python$target:::function-entry
++/(copyinstr(arg0)=="%(path)s") &&
++(copyinstr(arg1)=="test_entry_return_and_stack")/
++{
++    self->trace = 1;
++}
++python$target:::function-entry,python$target:::function-return
++/(copyinstr(arg0)=="%(path)s") && (self->trace)/
++{
++    printf("%%d\t**%%s*%%s*%%s*%%d\\n", timestamp,
++        probename, copyinstr(arg0),
++        copyinstr(arg1), arg2);
++}
++python$target:::function-return
++/(copyinstr(arg0)=="%(path)s") &&
++(copyinstr(arg1)=="test_entry_return_and_stack")/
++{
++    self->trace = 0;
++}
++""" %{"path":sample}
++
++        dscript = dscript.replace("\r", "").replace("\n", "")
++        expected_result = """
++        **function-entry*%(path)s*test_entry_return_and_stack*25
++        **function-entry*%(path)s*function_1*6
++        **function-return*%(path)s*function_1*7
++        **function-entry*%(path)s*function_2*10
++        **function-entry*%(path)s*function_1*6
++        **function-return*%(path)s*function_1*7
++        **function-return*%(path)s*function_2*11
++        **function-entry*%(path)s*function_3*14
++        **function-return*%(path)s*function_3*15
++        **function-entry*%(path)s*function_4*18
++        **function-return*%(path)s*function_4*19
++        **function-entry*%(path)s*function_5*22
++        **function-return*%(path)s*function_5*23
++        **function-return*%(path)s*test_entry_return_and_stack*30
++        """ %{"path":sample}
++
++        command = "%s %s" %(sys.executable, sample)
++        if self.optimize :
++            command = "%s -OO %s" %(sys.executable, sample)
++        actual_result, _ = subprocess.Popen(["dtrace", "-q", "-n",
++            dscript,
++            "-c", command],
++                stdout=subprocess.PIPE, stderr=subprocess.STDOUT).communicate()
++
++        actual_result = normalize(actual_result)
++        expected_result = expected_result.replace("\r", "").replace("\n",
++                "").replace(" ", "")
++        self.assertEqual(actual_result, expected_result)
++
++    @unittest.skipIf(sys.platform == 'darwin',
++        "MacOS X doesn't support jstack()")
++    def test_stack(self) :
++        dscript = """
++python$target:::function-entry
++/(copyinstr(arg0)=="%(path)s") &&
++(copyinstr(arg1)=="test_entry_return_and_stack")/
++{
++    self->trace = 1;
++}
++python$target:::function-entry
++/(copyinstr(arg0)=="%(path)s") && (self->trace)/
++{
++    printf("[x]");
++    jstack();
++}
++python$target:::function-return
++/(copyinstr(arg0)=="%(path)s") &&
++(copyinstr(arg1)=="test_entry_return_and_stack")/
++{
++    self->trace = 0;
++}
++""" %{"path":sample}
++
++        dscript = dscript.replace("\r", "").replace("\n", "")
++        expected_result = """
++        [x]
++        [%(path)s:25(test_entry_return_and_stack)]
++        [x]
++        [%(path)s:6(function_1)]
++        [%(path)s:26(test_entry_return_and_stack)]
++        [x]
++        [%(path)s:10(function_2)]
++        [%(path)s:27(test_entry_return_and_stack)]
++        [x]
++        [%(path)s:6(function_1)]
++        [%(path)s:11(function_2)]
++        [%(path)s:27(test_entry_return_and_stack)]
++        [x]
++        [%(path)s:14(function_3)]
++        [%(path)s:28(test_entry_return_and_stack)]
++        [x]
++        [%(path)s:18(function_4)]
++        [%(path)s:29(test_entry_return_and_stack)]
++        [x]
++        [%(path)s:22(function_5)]
++        [%(path)s:30(test_entry_return_and_stack)]
++        """ %{"path":sample}
++
++        command = "%s %s" %(sys.executable, sample)
++        if self.optimize :
++            command = "%s -OO %s" %(sys.executable, sample)
++        actual_result, _ = subprocess.Popen(["dtrace", "-q", "-n",
++            dscript,
++            "-c", command],
++                stdout=subprocess.PIPE, stderr=subprocess.STDOUT).communicate()
++
++        actual_result = actual_result.decode("ascii")
++        # When compiling with '--with-pydebug'
++        actual_result = "".join(re.split("\[[0-9]+ refs\]", actual_result))
++
++        actual_result = [i for i in actual_result.split("\n") \
++                if (("[" in i) and not i.endswith(" (<module>) ]"))]
++        actual_result = "".join(actual_result)
++        actual_result = actual_result.replace("\r", "").replace("\n",
++                "").replace(" ", "")
++        expected_result = expected_result.replace("\r", "").replace("\n",
++                "").replace(" ", "")
++        self.assertEqual(actual_result, expected_result)
++
++    def test_garbage_collection(self) :
++        dscript = """
++python$target:::gc-start,python$target:::gc-done
++{
++    printf("%d\t**%s(%ld)\\n", timestamp, probename, arg0);
++}
++"""
++
++        dscript = dscript.replace("\r", "").replace("\n", "")
++        command = "%s %s" %(sys.executable, sample)
++        if self.optimize :
++            command = "%s -OO %s" %(sys.executable, sample)
++        actual_result, _ = subprocess.Popen(["dtrace", "-q", "-n",
++            dscript,
++            "-c", command],
++                stdout=subprocess.PIPE, stderr=subprocess.STDOUT).communicate()
++
++        actual_result = normalize(actual_result)
++        for i in range(10) :
++            actual_result = actual_result.replace(str(i), "")
++        expected_result = "**gc-start()**gc-done()" * \
++            actual_result.count("**gc-start()**")
++
++        self.assertEqual(actual_result, expected_result)
++
++    def test_verify_opcodes(self) :
++        # Verify that we are checking:
++        opcodes = set(["CALL_FUNCTION", "CALL_FUNCTION_VAR",
++            "CALL_FUNCTION_KW", "CALL_FUNCTION_VAR_KW"])
++        with open(sample, encoding="utf-8") as f :
++            obj = compile(f.read(), "sample", "exec")
++        class dump() :
++            def __init__(self) :
++                self.buf = []
++            def write(self, v) :
++                self.buf.append(v)
++
++        dump = dump()
++        stdout = sys.stdout
++        sys.stdout = dump
++        for i in obj.co_consts :
++            if isinstance(i, types.CodeType) and \
++                (i.co_name == 'test_entry_return_and_stack') :
++                dis.dis(i)
++        sys.stdout = stdout
++        dump = "\n".join(dump.buf)
++        dump = dump.replace("\r", "").replace("\n", "").split()
++        for i in dump :
++            opcodes.discard(i)
++        # Are we verifying all the relevant opcodes?
++        self.assertEqual(set(), opcodes)  # Are we verifying all opcodes?
++
++    def test_line(self) :
++        dscript = """
++python$target:::line
++/(copyinstr(arg0)=="%(path)s") &&
++(copyinstr(arg1)=="test_line")/
++{
++    printf("%%d\t**%%s*%%s*%%s*%%d\\n", timestamp,
++        probename, copyinstr(arg0),
++        copyinstr(arg1), arg2);
++}
++""" %{"path":sample}
++
++        dscript = dscript.replace("\r", "").replace("\n", "")
++        expected_result = """
++        **line*%(path)s*test_line*33
++        **line*%(path)s*test_line*34
++        **line*%(path)s*test_line*35
++        **line*%(path)s*test_line*36
++        **line*%(path)s*test_line*37
++        **line*%(path)s*test_line*38
++        **line*%(path)s*test_line*34
++        **line*%(path)s*test_line*35
++        **line*%(path)s*test_line*36
++        **line*%(path)s*test_line*37
++        **line*%(path)s*test_line*38
++        **line*%(path)s*test_line*34
++        **line*%(path)s*test_line*39
++        """ %{"path":sample}
++
++        command = "%s %s" %(sys.executable, sample)
++        if self.optimize :
++            command = "%s -OO %s" %(sys.executable, sample)
++        actual_result, _ = subprocess.Popen(["dtrace", "-q", "-n",
++            dscript,
++            "-c", command],
++                stdout=subprocess.PIPE, stderr=subprocess.STDOUT).communicate()
++
++        actual_result = normalize(actual_result)
++        expected_result = expected_result.replace("\r", "").replace("\n",
++                "").replace(" ", "")
++        self.assertEqual(actual_result, expected_result)
++
++    def test_instance_creation_destruction(self) :
++        dscript = """
++python$target:::function-entry
++/(copyinstr(arg0)=="%(path)s") &&
++(copyinstr(arg1)=="test_instance_creation_destruction")/
++{
++    self->trace = 1;
++}
++
++python$target:::instance-new-start,
++python$target:::instance-new-done,
++python$target:::instance-delete-start,
++python$target:::instance-delete-done
++/self->trace/
++{
++    printf("%%d\t**%%s* (%%s.%%s)\\n", timestamp,
++        probename, copyinstr(arg1), copyinstr(arg0));
++}
++
++python$target:::function-return
++/(copyinstr(arg0)=="%(path)s") &&
++(copyinstr(arg1)=="test_instance_creation_destruction")/
++{
++    self->trace = 0;
++}
++""" %{"path":sample}
++
++        dscript = dscript.replace("\r", "").replace("\n", "")
++        expected_result = """
++        **instance-new-start*(__main__.old_style_class)
++        **instance-new-done*(__main__.old_style_class)
++        **instance-delete-start*(__main__.old_style_class)
++        **instance-delete-done*(__main__.old_style_class)
++        **instance-new-start*(__main__.new_style_class)
++        **instance-new-done*(__main__.new_style_class)
++        **instance-delete-start*(__main__.new_style_class)
++        **instance-delete-done*(__main__.new_style_class)
++        **instance-new-start*(__main__.old_style_class)
++        **instance-new-done*(__main__.old_style_class)
++        **instance-new-start*(__main__.new_style_class)
++        **instance-new-done*(__main__.new_style_class)
++        **instance-delete-start*(__main__.old_style_class)
++        **instance-delete-done*(__main__.old_style_class)
++        **instance-delete-start*(__main__.new_style_class)
++        **instance-delete-done*(__main__.new_style_class)
++        """
++
++        command = "%s %s" %(sys.executable, sample)
++        if self.optimize :
++            command = "%s -OO %s" %(sys.executable, sample)
++        actual_result, _ = subprocess.Popen(["dtrace", "-q", "-n",
++            dscript,
++            "-c", command],
++                stdout=subprocess.PIPE, stderr=subprocess.STDOUT).communicate()
++
++        actual_result = normalize(actual_result)
++        expected_result = expected_result.replace("\r", "").replace("\n",
++                "").replace(" ", "")
++        self.assertEqual(actual_result, expected_result)
++
++    def test_unicode_function_entry_return(self) :
++        dscript = """
++python$target:::function-entry
++/(copyinstr(arg0)=="%(path)s") &&
++(copyinstr(arg1)=="test_unicode_entry_return_and_stack")/
++{
++    self->trace = 1;
++}
++python$target:::function-entry,python$target:::function-return
++/(copyinstr(arg0)=="%(path)s") && (self->trace)/
++{
++    printf("%%d\t**%%s*%%s*%%s*%%d\\n", timestamp,
++        probename, copyinstr(arg0),
++        copyinstr(arg1), arg2);
++}
++python$target:::function-return
++/(copyinstr(arg0)=="%(path)s") &&
++(copyinstr(arg1)=="test_unicode_entry_return_and_stack")/
++{
++    self->trace = 0;
++}
++""" %{"path":sample}
++
++        dscript = dscript.replace("\r", "").replace("\n", "")
++        expected_result = """
++        **function-entry*%(path)s*test_unicode_entry_return_and_stack*41
++        **function-entry*%(path)s*únícódé*42
++        **function-return*%(path)s*únícódé*43
++        **function-return*%(path)s*test_unicode_entry_return_and_stack*44
++        """ %{"path":sample}
++
++        command = "%s %s" %(sys.executable, sample)
++        if self.optimize :
++            command = "%s -OO %s" %(sys.executable, sample)
++        actual_result, _ = subprocess.Popen(["dtrace", "-q", "-n",
++            dscript,
++            "-c", command],
++                stdout=subprocess.PIPE, stderr=subprocess.STDOUT).communicate()
++
++        actual_result = actual_result.decode("utf8")
++        actual_result = normalize(actual_result)
++        expected_result = expected_result.replace("\r", "").replace("\n",
++                "").replace(" ", "")
++        self.assertEqual(actual_result, expected_result)
++
++    @unittest.skipIf(sys.platform == 'darwin',
++        "MacOS X doesn't support jstack()")
++    def test_unicode_stack(self) :
++        dscript = """
++python$target:::function-entry
++/(copyinstr(arg0)=="%(path)s") &&
++(copyinstr(arg1)=="test_unicode_entry_return_and_stack")/
++{
++    self->trace = 1;
++}
++python$target:::function-entry
++/(copyinstr(arg0)=="%(path)s") && (self->trace)/
++{
++    printf("[x]");
++    jstack();
++}
++python$target:::function-return
++/(copyinstr(arg0)=="%(path)s") &&
++(copyinstr(arg1)=="test_unicode_entry_return_and_stack")/
++{
++    self->trace = 0;
++}
++""" %{"path":sample}
++
++        dscript = dscript.replace("\r", "").replace("\n", "")
++        expected_result = """
++        [x]
++        [%(path)s:41(test_unicode_entry_return_and_stack)]
++        [x]
++        [%(path)s:42(únícódé)]
++        [%(path)s:44(test_unicode_entry_return_and_stack)]
++        """ %{"path":sample}
++
++        command = "%s %s" %(sys.executable, sample)
++        if self.optimize :
++            command = "%s -OO %s" %(sys.executable, sample)
++        actual_result, _ = subprocess.Popen(["dtrace", "-q", "-n",
++            dscript,
++            "-c", command],
++                stdout=subprocess.PIPE, stderr=subprocess.STDOUT).communicate()
++
++        actual_result = actual_result.decode("utf8")
++        # When compiling with '--with-pydebug'
++        actual_result = "".join(re.split("\[[0-9]+ refs\]", actual_result))
++
++        actual_result = [i for i in actual_result.split("\n") \
++                if (("[" in i) and not i.endswith(" (<module>) ]"))]
++        actual_result = "".join(actual_result)
++        actual_result = actual_result.replace("\r", "").replace("\n",
++                "").replace(" ", "")
++        expected_result = expected_result.replace("\r", "").replace("\n",
++                "").replace(" ", "")
++        self.assertEqual(actual_result, expected_result)
++
++
++
++# This class try to verify that dtrace probes
++# are still working with optimizations enabled in the bytecode.
++#
++# Some tests will not actually verify it. For instance,
++# source code compilation follows optimization status of
++# current working Python. So, you should run the test
++# both with an optimizing and a non optimizing Python.
++class DTraceTestsOptimize(DTraceTestsNormal) :
++    def setUp(self) :
++        self.optimize = True
++
++
++def test_main():
++    run_unittest(DTraceTestsNormal)
++    run_unittest(DTraceTestsOptimize)
++
++if __name__ == '__main__':
++    test_main()
++
+--- Python-3.4.0/Lib/test/test_sys.py
++++ Python-3.4.0/Lib/test/test_sys.py
[email protected]@ -729,6 +729,7 @@
+         self.assertEqual(sys.getsizeof(True, -1), size('') + self.longdigit)
+ 
+     def test_objecttypes(self):
++        import dtrace
+         # check all types defined in Objects/
+         size = test.support.calcobjsize
+         vsize = test.support.calcvobjsize
[email protected]@ -754,13 +755,17 @@
+             return inner
+         check(get_cell().__closure__[0], size('P'))
+         # code
+-        check(get_cell().__code__, size('5i9Pi3P'))
+-        check(get_cell.__code__, size('5i9Pi3P'))
++        if dtrace.available :
++            code = '5i9PiPH2P'
++        else :
++            code = '5i9Pi3P'
++        check(get_cell().__code__, size(code))
++        check(get_cell.__code__, size(code))
+         def get_cell2(x):
+             def inner():
+                 return x
+             return inner
+-        check(get_cell2.__code__, size('5i9Pi3P') + 1)
++        check(get_cell2.__code__, size(code) + 1)
+         # complex
+         check(complex(0,1), size('2d'))
+         # method_descriptor (descriptor object)
+--- Python-3.4.0/Makefile.pre.in
++++ Python-3.4.0/Makefile.pre.in
[email protected]@ -52,6 +52,13 @@
+ # Use this to make a link between python$(VERSION) and python in $(BINDIR)
+ LN=		@[email protected]
+ 
++DTRACE=         @[email protected]
++DFLAGS=         @[email protected]
++DTRACEOBJS=     @[email protected]
++DTRACE_NM=      @[email protected]
++DTRACE_LINKER=  @[email protected]
++
++
+ # Portable install script (configure doesn't always guess right)
+ INSTALL=	@[email protected]
+ [email protected][email protected]
[email protected]@ -569,7 +576,7 @@
+ 	$(AR) $(ARFLAGS) [email protected] $(MODOBJS)
+ 	$(RANLIB) [email protected]
+ 
+-libpython$(LDVERSION).so: $(LIBRARY_OBJS)
++libpython$(LDVERSION).so: $(LIBRARY_OBJS) $(DTRACEOBJS)
+ 	if test $(INSTSONAME) != $(LDLIBRARY); then \
+ 		$(BLDSHARED) -Wl,-h$(INSTSONAME) -o $(INSTSONAME) $(LIBRARY_OBJS) $(MODLIBS) $(SHLIBS) $(LIBC) $(LIBM) $(LDLAST); \
+ 		$(LN) -f $(INSTSONAME) [email protected]; \
[email protected]@ -580,9 +587,8 @@
+ libpython3.so:	libpython$(LDVERSION).so
+ 	$(BLDSHARED) $(NO_AS_NEEDED) -o [email protected] -Wl,[email protected] $^
+ 
+-libpython$(LDVERSION).dylib: $(LIBRARY_OBJS)
+-	 $(CC) -dynamiclib -Wl,-single_module $(PY_LDFLAGS) -undefined dynamic_lookup -Wl,-install_name,$(prefix)/lib/libpython$(LDVERSION).dylib -Wl,-compatibility_version,$(VERSION) -Wl,-current_version,$(VERSION) -o [email protected] $(LIBRARY_OBJS) $(SHLIBS) $(LIBC) $(LIBM) $(LDLAST); \
+-
++libpython$(LDVERSION).dylib: $(LIBRARY_OBJS) $(DTRACEOBJS)
++	 $(CC) -dynamiclib -Wl,-single_module $(PY_LDFLAGS) -undefined dynamic_lookup -Wl,-install_name,$(prefix)/lib/libpython$(LDVERSION).dylib -Wl,-compatibility_version,$(VERSION) -Wl,-current_version,$(VERSION) -o [email protected] $(LIBRARY_OBJS) $(DTRACEOBJS) $(SHLIBS) $(LIBC) $(LIBM) $(LDLAST)
+ 
+ libpython$(VERSION).sl: $(LIBRARY_OBJS)
+ 	$(LDSHARED) -o [email protected] $(LIBRARY_OBJS) $(MODLIBS) $(SHLIBS) $(LIBC) $(LIBM) $(LDLAST)
[email protected]@ -682,12 +688,18 @@
+ 		$(MODULE_OBJS) \
+ 		$(SIGNAL_OBJS) \
+ 		$(MODOBJS) \
++		$(DTRACEOBJS) \
+ 		$(srcdir)/Modules/getbuildinfo.c
+ 	$(CC) -c $(PY_CORE_CFLAGS) \
+ 	      -DHGVERSION="\"`LC_ALL=C $(HGVERSION)`\"" \
+ 	      -DHGTAG="\"`LC_ALL=C $(HGTAG)`\"" \
+ 	      -DHGBRANCH="\"`LC_ALL=C $(HGBRANCH)`\"" \
+ 	      -o [email protected] $(srcdir)/Modules/getbuildinfo.c
++	if test "$(DTRACEOBJS)" != "" ; then \
++		$(DTRACE_LINKER) --relocatable \
++	          [email protected] $(DTRACEOBJS) -o [email protected] ; \
++		mv [email protected] [email protected] ; \
++	fi;
+ 
+ Modules/getpath.o: $(srcdir)/Modules/getpath.c Makefile
+ 	$(CC) -c $(PY_CORE_CFLAGS) -DPYTHONPATH='"$(PYTHONPATH)"' \
[email protected]@ -820,6 +832,46 @@
+ Objects/typeslots.inc: $(srcdir)/Include/typeslots.h $(srcdir)/Objects/typeslots.py
+ 	$(PYTHON) $(srcdir)/Objects/typeslots.py < $(srcdir)/Include/typeslots.h > Objects/typeslots.inc
+ 
++$(srcdir)/Include/pydtrace.h: $(srcdir)/Include/pydtrace.d
++	if test "$(DTRACE)" != "" ; then \
++		$(DTRACE) -o [email protected] $(DFLAGS) \
++			-C -h -s $(srcdir)/Include/pydtrace.d ; \
++	else	touch [email protected] ; \
++	fi;
++
++$(srcdir)/Include/pydtrace_offsets.h: $(srcdir)/Include/pydtrace_offsets.c Python/ceval.o
++	$(CC) $(PY_CORE_CFLAGS) -o $(srcdir)/Include/pydtrace_offsets \
++	       	$(srcdir)/Include/pydtrace_offsets.c
++	$(srcdir)/Include/pydtrace_offsets.sh $(DTRACE_NM) \
++		Python/ceval.o $(srcdir)/Include/pydtrace_offsets > \
++		$(srcdir)/Include/pydtrace_offsets.h
++
++Python/ceval.o: Include/pydtrace.h
++Modules/gcmodule.o: Include/pydtrace.h
++Objects/typeobject.o: Include/pydtrace.h
++
++Python/pydtrace.o: $(srcdir)/Include/pydtrace.d $(srcdir)/Include/pydtrace_offsets.h \
++			Python/ceval.o Modules/gcmodule.o Objects/typeobject.o
++	# We do the "touch" game to break a circular dependency between
++	# "Python/ceval.o" and "Include/pydtrace_offsets.h".
++	if test "$(DTRACE)" != "" ; then \
++		touch -r Python/ceval.o Python/ceval.o.ts_dtrace ; \
++		touch -r Modules/gcmodule.o Modules/gcmodule.o.ts_dtrace ; \
++		touch -r Objects/typeobject.o Objects/typeobject.o.ts_dtrace ; \
++		$(DTRACE) -o [email protected] -DPYDTRACE_STACK_HELPER \
++			$(DFLAGS) $(PY_CPPFLAGS) \
++			-C -G -s $(srcdir)/Include/pydtrace.d \
++				Python/ceval.o Modules/gcmodule.o \
++				Objects/typeobject.o; \
++		touch -r Python/ceval.o.ts_dtrace Python/ceval.o ; \
++		touch -r Modules/gcmodule.o.ts_dtrace Modules/gcmodule.o ; \
++		touch -r Objects/typeobject.o.ts_dtrace Objects/typeobject.o ; \
++		rm Python/ceval.o.ts_dtrace ; \
++		rm Modules/gcmodule.o.ts_dtrace ; \
++		rm Objects/typeobject.o.ts_dtrace ; \
++	else    touch [email protected] ; \
++	fi;
++
+ ############################################################################
+ # Header files
+ 
[email protected]@ -1515,6 +1567,11 @@
+ 	find build -name '*.py[co]' -exec rm -f {} ';' || true
+ 	-rm -f pybuilddir.txt
+ 	-rm -f Lib/lib2to3/*Grammar*.pickle
++	rm -f Include/pydtrace.h
++	rm -f Include/pydtrace_offsets Include/pydtrace_offsets.h
++	rm -f Python/ceval.o.ts_dtrace
++	rm -f Modules/gcmodule.o.ts_dtrace
++	rm -f Objects/typeobject.o.ts_dtrace
+ 	-rm -f Modules/_testembed Modules/_freeze_importlib
+ 
+ profile-removal:
[email protected]@ -1546,6 +1603,11 @@
+ 				     -o -name '*.orig' -o -name '*.rej' \
+ 				     -o -name '*.bak' ')' \
+ 				     -exec rm -f {} ';'
++	rm -f Include/pydtrace.h
++	rm -f Include/pydtrace_offsets Include/pydtrace_offsets.h
++	rm -f Python/ceval.o.ts_dtrace
++	rm -f Modules/gcmodule.o.ts_dtrace
++	rm -f Objects/typeobject.o.ts_dtrace
+ 
+ # Check for smelly exported symbols (not starting with Py/_Py)
+ smelly: all
+--- Python-3.4.0/Modules/Setup.dist
++++ Python-3.4.0/Modules/Setup.dist
[email protected]@ -390,3 +390,5 @@
+ 
+ # Another example -- the 'xxsubtype' module shows C-level subtyping in action
+ xxsubtype xxsubtype.c
++
++dtrace dtracemodule.c
+--- /dev/null
++++ Python-3.4.0/Modules/dtracemodule.c
[email protected]@ -0,0 +1,39 @@
++#include "Python.h"
++
++static PyMethodDef dtrace_methods[] = {
++    {NULL,  NULL}   /* sentinel */
++};
++
++
++static struct PyModuleDef dtracemodule = {
++    PyModuleDef_HEAD_INIT,
++    "dtrace",
++    NULL,
++    -1,
++    dtrace_methods,
++    NULL,
++    NULL,
++    NULL,
++    NULL
++};
++
++PyMODINIT_FUNC
++PyInit_dtrace(void)
++{
++    PyObject *m, *v;
++
++    m = PyModule_Create(&dtracemodule);
++    if (m) {
++#ifdef WITH_DTRACE
++        v = Py_True;
++#else
++        v = Py_False;
++#endif
++        Py_INCREF(v);
++        if (PyModule_AddObject(m, "available", v) < 0) {
++            Py_DECREF(m);
++            return NULL;
++        }
++    }
++    return m;
++}
+--- Python-3.4.0/Modules/gcmodule.c
++++ Python-3.4.0/Modules/gcmodule.c
[email protected]@ -26,6 +26,10 @@
+ #include "Python.h"
+ #include "frameobject.h"        /* for PyFrame_ClearFreeList */
+ 
++#ifdef WITH_DTRACE
++#include "pydtrace.h"
++#endif
++
+ /* Get an object's GC head */
+ #define AS_GC(o) ((PyGC_Head *)(o)-1)
+ 
[email protected]@ -905,7 +909,12 @@
+ /* This is the main function.  Read this to understand how the
+  * collection process works. */
+ static Py_ssize_t
+-collect(int generation, Py_ssize_t *n_collected, Py_ssize_t *n_uncollectable,
++#ifdef WITH_DTRACE
++collect2
++#else
++collect
++#endif
++(int generation, Py_ssize_t *n_collected, Py_ssize_t *n_uncollectable,
+         int nofail)
+ {
+     int i;
[email protected]@ -1080,6 +1089,50 @@
+     return n+m;
+ }
+ 
++#ifdef WITH_DTRACE
++static void
++dtrace_gc_start(int collection)
++{
++    PYTHON_GC_START(collection);
++
++    /*
++     * Currently a USDT tail-call will not receive the correct arguments.
++     * Disable the tail call here.
++     */
++#if defined(__sparc)
++    asm("nop");
++#endif
++}
++
++static void
++dtrace_gc_done(Py_ssize_t value)
++{
++    PYTHON_GC_DONE((long) value);
++
++    /*
++     * Currently a USDT tail-call will not receive the correct arguments.
++     * Disable the tail call here.
++     */
++#if defined(__sparc)
++    asm("nop");
++#endif
++}
++
++static Py_ssize_t
++collect(int collection, Py_ssize_t *n_collected, Py_ssize_t *n_uncollectable,
++	int nofail)
++{
++    Py_ssize_t value;
++
++    if (PYTHON_GC_START_ENABLED())
++        dtrace_gc_start(collection);
++    value = collect2(collection, n_collected, n_uncollectable, nofail);
++    if (PYTHON_GC_DONE_ENABLED())
++        dtrace_gc_done(value);
++    return value;
++}
++#endif /* WITH_DTRACE */
++
+ /* Invoke progress callbacks to notify clients that garbage collection
+  * is starting or stopping
+  */
+--- Python-3.4.0/Objects/codeobject.c
++++ Python-3.4.0/Objects/codeobject.c
[email protected]@ -152,6 +152,37 @@
+     co->co_lnotab = lnotab;
+     co->co_zombieframe = NULL;
+     co->co_weakreflist = NULL;
++
++#ifdef WITH_DTRACE
++    /*
++    ** Cache UTF8 internally, available
++    ** for the pythonframe stack walker.
++    */
++    PyUnicode_AsUTF8(filename);
++    PyUnicode_AsUTF8(name);
++
++    i = PyBytes_Size(co->co_code);
++    co->co_linenos = PyMem_Malloc(sizeof(unsigned short) * i);
++    if (co->co_linenos) {
++        unsigned short *p = (unsigned short *)(co->co_linenos);
++        unsigned char *p2 = (unsigned char*)PyBytes_AsString(co->co_lnotab);
++        int size = PyBytes_Size(co->co_lnotab) / 2;
++        int i2;
++        unsigned short offset = 0;
++
++        while (size) {
++            size -= 1;
++            i2 = *p2++;
++            i-=i2;
++            while (i2--)
++                *p++ = offset;
++            offset += *p2++;
++        }
++        while(i--)
++            *p++ = offset;
++    }
++#endif
++
+     return co;
+ }
+ 
+--- Python-3.4.0/Objects/frameobject.c
++++ Python-3.4.0/Objects/frameobject.c
[email protected]@ -733,6 +733,15 @@
+     f->f_executing = 0;
+     f->f_gen = NULL;
+ 
++#ifdef WITH_DTRACE
++    /*
++    ** Cache UTF8 internally, available
++    ** for the pythonframe stack walker.
++    */
++    PyUnicode_AsUTF8(f->f_code->co_filename);
++    PyUnicode_AsUTF8(f->f_code->co_name);
++#endif
++
+     _PyObject_GC_TRACK(f);
+     return f;
+ }
+--- Python-3.4.0/Objects/typeobject.c
++++ Python-3.4.0/Objects/typeobject.c
[email protected]@ -4,6 +4,10 @@
+ #include "frameobject.h"
+ #include "structmember.h"
+ 
++#ifdef WITH_DTRACE
++#include "pydtrace.h"
++#endif
++
+ #include <ctype.h>
+ 
+ 
[email protected]@ -880,8 +884,29 @@
+ PyType_GenericAlloc(PyTypeObject *type, Py_ssize_t nitems)
+ {
+     PyObject *obj;
+-    const size_t size = _PyObject_VAR_SIZE(type, nitems+1);
++    size_t size;
++
++#ifdef WITH_DTRACE
++    PyObject *mod;
++    char *mod_name;
++
++    if (PYTHON_INSTANCE_NEW_START_ENABLED()) {
++        if (type->tp_flags & Py_TPFLAGS_HEAPTYPE) {
++            mod = PyDict_GetItemString(type->tp_dict, "__module__");
++            if (mod == NULL || !PyUnicode_Check(mod)) {
++                mod_name = "?";
++            } else {
++                mod_name = PyUnicode_AsUTF8(mod);
++                if (!mod_name)
++                    mod_name = "?";
++            }
++            PYTHON_INSTANCE_NEW_START((char *)(type->tp_name), mod_name);
++        }
++    }
++#endif
++
+     /* note that we need to add one, for the sentinel */
++    size = _PyObject_VAR_SIZE(type, nitems+1);
+ 
+     if (PyType_IS_GC(type))
+         obj = _PyObject_GC_Malloc(size);
[email protected]@ -903,6 +928,23 @@
+ 
+     if (PyType_IS_GC(type))
+         _PyObject_GC_TRACK(obj);
++
++#ifdef WITH_DTRACE
++    if (PYTHON_INSTANCE_NEW_DONE_ENABLED()) {
++        if (type->tp_flags & Py_TPFLAGS_HEAPTYPE) {
++            mod = PyDict_GetItemString(type->tp_dict, "__module__");
++            if (mod == NULL || !PyUnicode_Check(mod)) {
++                mod_name = "?";
++            } else {
++                mod_name = PyUnicode_AsUTF8(mod);
++                if (!mod_name)
++                    mod_name = "?";
++            }
++            PYTHON_INSTANCE_NEW_DONE((char *)(type->tp_name), mod_name);
++        }
++    }
++#endif
++
+     return obj;
+ }
+ 
[email protected]@ -1023,9 +1065,56 @@
+     return 0;
+ }
+ 
++#ifdef WITH_DTRACE
++static void subtype_dealloc2(PyObject *);  /* Forward declaration */
++
+ static void
+ subtype_dealloc(PyObject *self)
+ {
++    PyObject *mod;
++    char *mod_name;
++    PyTypeObject *type;
++
++    type = Py_TYPE(self);
++    Py_INCREF(type);
++
++    if (PYTHON_INSTANCE_DELETE_START_ENABLED()) {
++        mod = PyDict_GetItemString(type->tp_dict, "__module__");
++        if (mod == NULL || !PyUnicode_Check(mod)) {
++            mod_name = "?";
++        } else {
++            mod_name = PyUnicode_AsUTF8(mod);
++            if (!mod_name)
++                mod_name = "?";
++        }
++        PYTHON_INSTANCE_DELETE_START((char *)(type->tp_name), mod_name);
++    }
++
++    subtype_dealloc2(self);
++
++    if (PYTHON_INSTANCE_DELETE_DONE_ENABLED()) {
++        mod = PyDict_GetItemString(type->tp_dict, "__module__");
++        if (mod == NULL || !PyUnicode_Check(mod)) {
++            mod_name = "?";
++        } else {
++            mod_name = PyUnicode_AsUTF8(mod);
++            if (!mod_name)
++                mod_name = "?";
++        }
++        PYTHON_INSTANCE_DELETE_DONE((char *)(type->tp_name), mod_name);
++    }
++    Py_DECREF(type);
++}
++#endif
++
++static void
++#ifdef WITH_DTRACE
++subtype_dealloc2
++#else
++subtype_dealloc
++#endif
++(PyObject *self)
++{
+     PyTypeObject *type, *base;
+     destructor basedealloc;
+     PyThreadState *tstate = PyThreadState_GET();
+--- Python-3.4.0/Python/ceval.c
++++ Python-3.4.0/Python/ceval.c
[email protected]@ -18,6 +18,13 @@
+ 
+ #include <ctype.h>
+ 
++#ifdef WITH_DTRACE
++#include "pydtrace.h"
++#else
++/* We can not have conditional compilation inside macros */
++#define PYTHON_LINE_ENABLED() (0)
++#endif
++
+ #ifndef WITH_TSC
+ 
+ #define READ_TIMESTAMP(var)
[email protected]@ -119,6 +126,12 @@
+ #define CALL_FLAG_VAR 1
+ #define CALL_FLAG_KW 2
+ 
++#ifdef WITH_DTRACE
++static void maybe_dtrace_line(PyFrameObject *frame,
++                              int *instr_lb, int *instr_ub,
++                              int *instr_prev);
++#endif
++
+ #ifdef LLTRACE
+ static int lltrace;
+ static int prtrace(PyObject *, char *);
[email protected]@ -778,6 +791,49 @@
+                       NULL, NULL);
+ }
+ 
++#ifdef WITH_DTRACE
++static void
++dtrace_entry(PyFrameObject *f)
++{
++    char *filename;
++    char *name;
++    int lineno;
++
++    filename = PyUnicode_AsUTF8(f->f_code->co_filename);
++    name = PyUnicode_AsUTF8(f->f_code->co_name);
++    lineno = PyCode_Addr2Line(f->f_code, f->f_lasti);
++    PYTHON_FUNCTION_ENTRY(filename, name, lineno);
++
++    /*
++     * Currently a USDT tail-call will not receive the correct arguments.
++     * Disable the tail call here.
++     */
++#if defined(__sparc)
++    asm("nop");
++#endif
++}
++
++static void
++dtrace_return(PyFrameObject *f)
++{
++    char *filename;
++    char *name;
++    int lineno;
++
++    filename = PyUnicode_AsUTF8(f->f_code->co_filename);
++    name = PyUnicode_AsUTF8(f->f_code->co_name);
++    lineno = PyCode_Addr2Line(f->f_code, f->f_lasti);
++    PYTHON_FUNCTION_RETURN(filename, name, lineno);
++
++    /*
++     * Currently a USDT tail-call will not receive the correct arguments.
++     * Disable the tail call here.
++     */
++#if defined(__sparc)
++    asm("nop");
++#endif
++}
++#endif
+ 
+ /* Interpreter main loop */
+ 
[email protected]@ -789,8 +845,16 @@
+     return PyEval_EvalFrameEx(f, 0);
+ }
+ 
++
+ PyObject *
++#if defined(WITH_DTRACE) && defined(__amd64)
++PyEval_EvalFrameExReal(long a1, long a2, long a3, long a4, long a5, long a6,
++    PyFrameObject *f, int throwflag)
++#elif defined(WITH_DTRACE) && defined(__sparc)
++PyEval_EvalFrameExReal(PyFrameObject *f, int throwflag)
++#else
+ PyEval_EvalFrameEx(PyFrameObject *f, int throwflag)
++#endif
+ {
+ #ifdef DXPAIRS
+     int lastopcode = 0;
[email protected]@ -911,7 +975,7 @@
+ #ifdef LLTRACE
+ #define FAST_DISPATCH() \
+     { \
+-        if (!lltrace && !_Py_TracingPossible) { \
++        if (!lltrace && !_Py_TracingPossible && !PYTHON_LINE_ENABLED()) { \
+             f->f_lasti = INSTR_OFFSET(); \
+             goto *opcode_targets[*next_instr++]; \
+         } \
[email protected]@ -920,7 +984,7 @@
+ #else
+ #define FAST_DISPATCH() \
+     { \
+-        if (!_Py_TracingPossible) { \
++        if (!_Py_TracingPossible && !PYTHON_LINE_ENABLED()) { \
+             f->f_lasti = INSTR_OFFSET(); \
+             goto *opcode_targets[*next_instr++]; \
+         } \
[email protected]@ -1156,6 +1220,11 @@
+         }
+     }
+ 
++#ifdef WITH_DTRACE
++    if (PYTHON_FUNCTION_ENTRY_ENABLED())
++        dtrace_entry(f);
++#endif
++
+     co = f->f_code;
+     names = co->co_names;
+     consts = co->co_consts;
[email protected]@ -1343,6 +1412,12 @@
+         /* Main switch on opcode */
+         READ_TIMESTAMP(inst0);
+ 
++#ifdef WITH_DTRACE
++        if (PYTHON_LINE_ENABLED()) {
++            maybe_dtrace_line(f, &instr_lb, &instr_ub, &instr_prev);
++        }
++#endif
++
+         switch (opcode) {
+ 
+         /* BEWARE!
[email protected]@ -3216,6 +3291,10 @@
+ 
+     /* pop frame */
+ exit_eval_frame:
++#ifdef WITH_DTRACE
++    if (PYTHON_FUNCTION_RETURN_ENABLED())
++        dtrace_return(f);
++#endif
+     Py_LeaveRecursiveCall();
+     f->f_executing = 0;
+     tstate->frame = f->f_back;
[email protected]@ -3915,6 +3994,57 @@
+     return result;
+ }
+ 
++/*
++ * These shenanigans look like utter madness, but what we're actually doing is
++ * making sure that the ustack helper will see the PyFrameObject pointer on the
++ * stack. We have two tricky cases:
++ *
++ * amd64
++ *
++ * We use up the six registers for passing arguments, meaning the call can't
++ * use a register for passing 'f', and has to push it onto the stack in a known
++ * location.
++ *
++ * And how does "throwflag" figure in to this? -PN
++ *
++ * SPARC
++ *
++ * Here the problem is that (on 32-bit) the compiler is re-using %i0 before
++ * some calls inside PyEval_EvalFrameReal(), which means that when it's saved,
++ * it's just some junk value rather than the real first argument. So, instead,
++ * we trace our proxy PyEval_EvalFrame(), where we 'know' the compiler won't
++ * decide to re-use %i0. We also need to defeat optimization of our proxy.
++ */
++
++#if defined(WITH_DTRACE)
++
++#if defined(__amd64)
++
++PyObject *
++PyEval_EvalFrameEx(PyFrameObject *f, int throwflag)
++{
++    volatile PyObject *f2;
++    f2 = PyEval_EvalFrameExReal(0, 0, 0, 0, 0, 0, f, throwflag);
++    return (PyObject *)f2;
++}
++
++#elif defined(__sparc)
++
++volatile int dummy;
++
++PyObject *
++PyEval_EvalFrameEx(PyFrameObject *f, int throwflag)
++{
++    volatile PyObject *f2;
++    f2 = PyEval_EvalFrameExReal(f, throwflag);
++    dummy = f->ob_base.ob_base.ob_refcnt;
++    return (PyObject *)f2;
++}
++
++#endif
++#endif
++
++
+ PyObject *
+ _PyEval_CallTracing(PyObject *func, PyObject *args)
+ {
[email protected]@ -3932,6 +4062,51 @@
+     return result;
+ }
+ 
++#ifdef WITH_DTRACE
++/* See Objects/lnotab_notes.txt for a description of how tracing works. */
++/* Practically a ripoff of "maybe_call_line_trace" function. */
++static void
++maybe_dtrace_line(PyFrameObject *frame,
++                  int *instr_lb, int *instr_ub, int *instr_prev)
++{
++    int line = frame->f_lineno;
++    char *co_filename, *co_name;
++
++    /* 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;
++        co_filename = PyUnicode_AsUTF8(frame->f_code->co_filename);
++        if (!co_filename)
++            co_filename = "?";
++        co_name = PyUnicode_AsUTF8(frame->f_code->co_name);
++        if (!co_name)
++            co_name = "?";
++        PYTHON_LINE(co_filename, co_name, line);
++    }
++    *instr_prev = frame->f_lasti;
++
++    /*
++     * Currently a USDT tail-call will not receive the correct arguments.
++     * Disable the tail call here.
++     */
++#if defined(__sparc)
++    asm("nop");
++#endif
++}
++#endif
++
+ /* See Objects/lnotab_notes.txt for a description of how tracing works. */
+ static int
+ maybe_call_line_trace(Py_tracefunc func, PyObject *obj,
+--- Python-3.4.0/configure
++++ Python-3.4.0/configure
[email protected]@ -642,6 +642,11 @@
+ MACHDEP_OBJS
+ DYNLOADFILE
+ DLINCLDIR
++DTRACEOBJS
++DTRACE_LINKER
++DTRACE_NM
++DFLAGS
++DTRACE
+ THREADOBJ
+ LDLAST
+ USE_THREAD_MODULE
[email protected]@ -811,6 +816,7 @@
+ with_tsc
+ with_pymalloc
+ with_valgrind
++with_dtrace
+ with_fpectl
+ with_libm
+ with_libc
[email protected]@ -1494,6 +1500,7 @@
+   --with(out)-tsc         enable/disable timestamp counter profile
+   --with(out)-pymalloc    disable/enable specialized mallocs
+   --with-valgrind         Enable Valgrind support
++  --with(out)-dtrace      disable/enable dtrace support
+   --with-fpectl           enable SIGFPE catching
+   --with-libm=STRING      math library
+   --with-libc=STRING      C library
[email protected]@ -10391,6 +10398,174 @@
+     OPT="-DDYNAMIC_ANNOTATIONS_ENABLED=1 $OPT"
+ fi
+ 
++# Check for dtrace support
++{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for --with-dtrace" >&5
++$as_echo_n "checking for --with-dtrace... " >&6; }
++
++# Check whether --with-dtrace was given.
++if test "${with_dtrace+set}" = set; then :
++  withval=$with_dtrace;
++else
++  with_dtrace=no
++fi
++
++{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $with_dtrace" >&5
++$as_echo "$with_dtrace" >&6; }
++
++
++
++
++
++DTRACE=
++DFLAGS=
++if test "$with_dtrace" = "yes"
++then
++    DTRACE_NM=OTHER
++    DTRACE_LINKER=ld
++    DTRACEOBJS="Python/pydtrace.o"
++    # Extract the first word of "dtrace", so it can be a program name with args.
++set dummy dtrace; ac_word=$2
++{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5
++$as_echo_n "checking for $ac_word... " >&6; }
++if ${ac_cv_path_DTRACE+:} false; then :
++  $as_echo_n "(cached) " >&6
++else
++  case $DTRACE in
++  [\\/]* | ?:[\\/]*)
++  ac_cv_path_DTRACE="$DTRACE" # Let the user override the test with a path.
++  ;;
++  *)
++  as_save_IFS=$IFS; IFS=$PATH_SEPARATOR
++for as_dir in $PATH$PATH_SEPARATOR/usr/sbin
++do
++  IFS=$as_save_IFS
++  test -z "$as_dir" && as_dir=.
++    for ac_exec_ext in '' $ac_executable_extensions; do
++  if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then
++    ac_cv_path_DTRACE="$as_dir/$ac_word$ac_exec_ext"
++    $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5
++    break 2
++  fi
++done
++  done
++IFS=$as_save_IFS
++
++  test -z "$ac_cv_path_DTRACE" && ac_cv_path_DTRACE="dtrace"
++  ;;
++esac
++fi
++DTRACE=$ac_cv_path_DTRACE
++if test -n "$DTRACE"; then
++  { $as_echo "$as_me:${as_lineno-$LINENO}: result: $DTRACE" >&5
++$as_echo "$DTRACE" >&6; }
++else
++  { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5
++$as_echo "no" >&6; }
++fi
++
++
++    # The cast to long int works around a bug in the HP C Compiler
++# version HP92453-01 B.11.11.23709.GP, which incorrectly rejects
++# declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'.
++# This bug is HP SR number 8606223364.
++{ $as_echo "$as_me:${as_lineno-$LINENO}: checking size of long" >&5
++$as_echo_n "checking size of long... " >&6; }
++if ${ac_cv_sizeof_long+:} false; then :
++  $as_echo_n "(cached) " >&6
++else
++  if ac_fn_c_compute_int "$LINENO" "(long int) (sizeof (long))" "ac_cv_sizeof_long"        "$ac_includes_default"; then :
++
++else
++  if test "$ac_cv_type_long" = yes; then
++     { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
++$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
++as_fn_error 77 "cannot compute sizeof (long)
++See \`config.log' for more details" "$LINENO" 5; }
++   else
++     ac_cv_sizeof_long=0
++   fi
++fi
++
++fi
++{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_sizeof_long" >&5
++$as_echo "$ac_cv_sizeof_long" >&6; }
++
++
++
++cat >>confdefs.h <<_ACEOF
++#define SIZEOF_LONG $ac_cv_sizeof_long
++_ACEOF
++
++
++    if test "$ac_cv_sizeof_long" -eq 8
++    then
++        DFLAGS="-64"
++    else
++        DFLAGS="-32"
++    fi
++    sys_release="$ac_sys_release"
++    case $ac_sys_system/$sys_release in
++        SunOS/5.10)
++            DTRACE_NM=SOLARIS
++            DTRACE_LINKER=/usr/ccs/bin/ld
++            ;;
++        SunOS/5.11 | SunOS/5.12)
++            DTRACE_NM=SOLARIS
++            DTRACE_LINKER=/usr/bin/ld
++	    ;;
++        SunOS/*)
++            DTRACE_LINKER=/usr/ccs/bin/ld
++            ;;
++        Darwin/*)
++            DTRACEOBJS=""  # Not needed in Mac
++            # The cast to long int works around a bug in the HP C Compiler
++# version HP92453-01 B.11.11.23709.GP, which incorrectly rejects
++# declarations like `int a3[[(sizeof (unsigned char)) >= 0]];'.
++# This bug is HP SR number 8606223364.
++{ $as_echo "$as_me:${as_lineno-$LINENO}: checking size of long" >&5
++$as_echo_n "checking size of long... " >&6; }
++if ${ac_cv_sizeof_long+:} false; then :
++  $as_echo_n "(cached) " >&6
++else
++  if ac_fn_c_compute_int "$LINENO" "(long int) (sizeof (long))" "ac_cv_sizeof_long"        "$ac_includes_default"; then :
++
++else
++  if test "$ac_cv_type_long" = yes; then
++     { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5
++$as_echo "$as_me: error: in \`$ac_pwd':" >&2;}
++as_fn_error 77 "cannot compute sizeof (long)
++See \`config.log' for more details" "$LINENO" 5; }
++   else
++     ac_cv_sizeof_long=0
++   fi
++fi
++
++fi
++{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_sizeof_long" >&5
++$as_echo "$ac_cv_sizeof_long" >&6; }
++
++
++
++cat >>confdefs.h <<_ACEOF
++#define SIZEOF_LONG $ac_cv_sizeof_long
++_ACEOF
++
++
++            if test "$ac_cv_sizeof_long" -eq 8
++            then
++                DFLAGS="-arch i386"
++            else
++                DFLAGS="-arch x86_64"
++            fi
++            ;;
++    esac
++
++$as_echo "#define WITH_DTRACE 1" >>confdefs.h
++
++fi
++
++
++
+ # -I${DLINCLDIR} is added to the compile rule for importdl.o
+ 
+ DLINCLDIR=.
+--- Python-3.4.0/configure.ac
++++ Python-3.4.0/configure.ac
[email protected]@ -2868,6 +2868,62 @@
+     OPT="-DDYNAMIC_ANNOTATIONS_ENABLED=1 $OPT"
+ fi
+ 
++# Check for dtrace support
++AC_MSG_CHECKING(for --with-dtrace)
++AC_ARG_WITH(dtrace,
++  AC_HELP_STRING(--with(out)-dtrace, disable/enable dtrace support),,
++  with_dtrace=no)
++AC_MSG_RESULT($with_dtrace)
++
++AC_SUBST(DTRACE)
++AC_SUBST(DFLAGS)
++AC_SUBST(DTRACE_NM)
++AC_SUBST(DTRACE_LINKER)
++DTRACE=
++DFLAGS=
++if test "$with_dtrace" = "yes"
++then
++    DTRACE_NM=OTHER
++    DTRACE_LINKER=ld
++    DTRACEOBJS="Python/pydtrace.o"
++    AC_PATH_PROG(DTRACE, [dtrace], [dtrace], [$PATH$PATH_SEPARATOR/usr/sbin])
++    AC_CHECK_SIZEOF([long])
++    if [test "$ac_cv_sizeof_long" -eq 8]
++    then
++        DFLAGS="-64"
++    else
++        DFLAGS="-32"
++    fi
++    sys_release="$ac_sys_release"
++    case $ac_sys_system/$sys_release in
++        SunOS/5.10)
++            DTRACE_NM=SOLARIS
++            DTRACE_LINKER=/usr/ccs/bin/ld
++            ;;
++        SunOS/5.11 | SunOS/5.12)
++            DTRACE_NM=SOLARIS
++            DTRACE_LINKER=/usr/bin/ld
++	    ;;
++        SunOS/*)
++            DTRACE_LINKER=/usr/ccs/bin/ld
++            ;;
++        Darwin/*)
++            DTRACEOBJS=""  # Not needed in Mac
++            AC_CHECK_SIZEOF([long])
++            if [test "$ac_cv_sizeof_long" -eq 8]
++            then
++                DFLAGS="-arch i386"
++            else
++                DFLAGS="-arch x86_64"
++            fi
++            ;;
++    esac
++    AC_DEFINE(WITH_DTRACE, 1, 
++     [Define if you want to compile in Dtrace support])
++fi
++
++AC_SUBST(DTRACEOBJS)
++
+ # -I${DLINCLDIR} is added to the compile rule for importdl.o
+ AC_SUBST(DLINCLDIR)
+ DLINCLDIR=.
+--- Python-3.4.0/pyconfig.h.in
++++ Python-3.4.0/pyconfig.h.in
[email protected]@ -1328,6 +1328,9 @@
+ /* Define if you want documentation strings in extension modules */
+ #undef WITH_DOC_STRINGS
+ 
++/* Define if you want to compile in Dtrace support */
++#undef WITH_DTRACE
++
+ /* Define if you want to use the new-style (Openstep, Rhapsody, MacOS) dynamic
+    linker (dyld) instead of the old-style (NextStep) dynamic linker (rld).
+    Dyld is necessary to support frameworks. */
+--- Python-3.4.0/setup.py
++++ Python-3.4.0/setup.py
[email protected]@ -637,6 +637,9 @@
+         # syslog daemon interface
+         exts.append( Extension('syslog', ['syslogmodule.c']) )
+ 
++        # jcea DTRACE probes
++        exts.append( Extension('dtrace', ['dtracemodule.c']) )
++
+         #
+         # Here ends the simple stuff.  From here on, modules need certain
+         # libraries, are platform-specific, or present other surprises.
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/components/python/python34/patches/01-bits.patch	Mon May 19 07:37:20 2014 -0700
@@ -0,0 +1,28 @@
+#
+# This patch addresses problems with the configure script.
+# As it is Solaris-specific, it is not suitable for upstream.
+#
+--- Python-3.4.0/configure.ac.~1~	2014-03-16 19:31:31.000000000 -0700
++++ Python-3.4.0/configure.ac	2014-03-17 11:11:22.990261823 -0700
[email protected]@ -5,7 +5,7 @@
+ # Set VERSION so we only need to edit in one place (i.e., here)
+ m4_define(PYTHON_VERSION, 3.4)
+ 
+-AC_PREREQ(2.65)
++AC_PREREQ(2.68)
+ 
+ AC_INIT(python, PYTHON_VERSION, http://bugs.python.org/)
+ 
[email protected]@ -2108,12 +2108,6 @@
+ if test -z "$CCSHARED"
+ then
+ 	case $ac_sys_system/$ac_sys_release in
+-	SunOS*) if test "$GCC" = yes;
+-		then CCSHARED="-fPIC";
+-		elif test `uname -p` = sparc;
+-		then CCSHARED="-xcode=pic32";
+-		else CCSHARED="-Kpic";
+-		fi;;
+ 	hp*|HP*) if test "$GCC" = yes;
+ 		 then CCSHARED="-fPIC";
+ 		 else CCSHARED="+z";
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/components/python/python34/patches/02-ext-stdio.patch	Mon May 19 07:37:20 2014 -0700
@@ -0,0 +1,43 @@
+This patch provides extended file stdio support.
+As it is Solaris-specific, it is not suitable for upstream.
+Note that this patch is no longer needed, since is we build Python 3 64-bit
+only, but we are keeping it around as a precaution in case we need to add
+32-bit support back in at some point.  If a time comes when we are certain
+we will never need 32-bit support, then the patch can be removed.
+
+--- Python-3.4.0/Modules/python.c.~1~	2014-03-16 19:31:31.000000000 -0700
++++ Python-3.4.0/Modules/python.c	2014-03-17 11:08:20.154195402 -0700
[email protected]@ -15,6 +15,13 @@
+ }
+ #else
+ 
++#if defined(sun) && defined(__SVR4) && !defined(_LP64)
++#define USE_EXTENDED_FILE_STDIO 1
++#include <stdio.h>
++#include <stdio_ext.h>
++#include <signal.h>
++#endif
++
+ int
+ main(int argc, char **argv)
+ {
[email protected]@ -44,6 +51,19 @@
+     fpsetmask(m & ~FP_X_OFL);
+ #endif
+ 
++#ifdef USE_EXTENDED_FILE_STDIO
++    /*
++     * enable extended FILE facility on Solaris so that Python
++     * apps can keep more than 256 file descriptors open
++     */
++    struct rlimit rlp;
++    (void) getrlimit(RLIMIT_NOFILE, &rlp);
++    rlp.rlim_cur = rlp.rlim_max;
++    if (setrlimit(RLIMIT_NOFILE, &rlp) != -1) {
++            enable_extended_FILE_stdio(-1, 0);
++    }
++#endif
++
+     oldloc = _PyMem_RawStrdup(setlocale(LC_ALL, NULL));
+     if (!oldloc) {
+         fprintf(stderr, "out of memory\n");
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/components/python/python34/patches/03-setup.patch	Mon May 19 07:37:20 2014 -0700
@@ -0,0 +1,28 @@
+This patch modifies the setup script to support Solaris.
+As it is Solaris-specific, it is not suitable for upstream.
+
+--- Python-3.4.0/setup.py.~2~	2014-03-19 10:36:25.778101571 -0700
++++ Python-3.4.0/setup.py	2014-03-19 10:36:25.855568930 -0700
[email protected]@ -728,6 +728,13 @@
+                                                      ['/usr/lib/termcap'],
+                                                      'termcap'):
+                 readline_libs.append('termcap')
++
++            if host_platform == 'sunos5':
++                # insert '-zrecord' before the readline libraries that we
++                # want to link with to avoid rl_insert() elimination
++                readline_extra_link_args = ('-Wl,-zrecord','-lreadline','-lncurses')
++                readline_libs = ()
++
+             exts.append( Extension('readline', ['readline.c'],
+                                    library_dirs=['/usr/lib/termcap'],
+                                    extra_link_args=readline_extra_link_args,
[email protected]@ -1900,7 +1907,7 @@
+             # this option. If you want to compile ctypes with the Sun
+             # compiler, please research a proper solution, instead of
+             # finding some -z option for the Sun compiler.
+-            extra_link_args.append('-mimpure-text')
++            pass
+ 
+         elif host_platform.startswith('hp-ux'):
+             extra_link_args.append('-fPIC')
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/components/python/python34/patches/04-vendor-packages.patch	Mon May 19 07:37:20 2014 -0700
@@ -0,0 +1,8 @@
+This patch makes Python support the vendor-packages directory.
+As it is Solaris-specific, it is not suitable for upstream.
+
+--- /dev/null   Sat Feb 12 00:21:26 2011
++++ Python-3.4.0/Lib/site-packages/vendor-packages.pth  Sat Feb 12 00:47:05 2011
[email protected]@ -0,0 +1,1 @@
++import site; site.addsitedir('/usr/lib/python3.4/vendor-packages')
+
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/components/python/python34/patches/05-studio-profile.patch	Mon May 19 07:37:20 2014 -0700
@@ -0,0 +1,77 @@
+This changes Python's standard profile-guided build target to work with
+Studio instead of gcc.  The unfortunate repetition of options seen below
+is a workaround for build peculiarities and to meet Studio's requirement
+that the profiling options be used at all steps of the build -- not just
+compilation.  As it is Solaris-specific, it is not suitable for upstream.
+
+--- Python-3.4.0/Makefile.pre.in.~2~	2014-03-19 10:42:20.230354945 -0700
++++ Python-3.4.0/Makefile.pre.in	2014-03-19 10:42:20.412767814 -0700
[email protected]@ -472,30 +472,39 @@
+ profile-opt:
+ 	@echo "Building with support for profile generation:"
+ 	$(MAKE) clean
++	$(MAKE) profile-removal
+ 	$(MAKE) build_all_generate_profile
+ 	@echo "Running benchmark to generate profile data:"
+-	$(MAKE) profile-removal
+ 	$(MAKE) run_profile_task
+ 	@echo "Rebuilding with profile guided optimizations:"
+ 	$(MAKE) clean
+ 	$(MAKE) build_all_use_profile
+ 
+ build_all_generate_profile:
+-	$(MAKE) all CFLAGS="$(CFLAGS) -fprofile-generate" LIBS="$(LIBS) -lgcov"
++	$(MAKE) all CC="$(CC) -xprofile=collect:$(XPROFILE_DIR)" \
++	    CFLAGS="$(CFLAGS) -xprofile=collect:$(XPROFILE_DIR)" \
++	    LDFLAGS="$(LDFLAGS) -xprofile=collect:$(XPROFILE_DIR)" \
++	    BLDSHARED="$(BLDSHARED) -xprofile=collect:$(XPROFILE_DIR)"
+ 
+ run_profile_task:
+ 	: # FIXME: can't run for a cross build
+-	$(RUNSHARED) ./$(BUILDPYTHON) $(PROFILE_TASK)
++	LD_LIBRARY_PATH=. $(RUNSHARED) ./$(BUILDPYTHON) $(PROFILE_TASK)
+ 
+ build_all_use_profile:
+-	$(MAKE) all CFLAGS="$(CFLAGS) -fprofile-use -fprofile-correction"
++	$(MAKE) all CC="$(CC) -xprofile=use:$(XPROFILE_DIR)" \
++	    CFLAGS="$(CFLAGS) -xprofile=use:$(XPROFILE_DIR)" \
++	    LDFLAGS="$(LDFLAGS) -xprofile=use:$(XPROFILE_DIR)" \
++	    BLDSHARED="$(BLDSHARED) -xprofile=use:$(XPROFILE_DIR)"
+ 
+ # Compile and run with gcov
+ .PHONY=coverage coverage-lcov coverage-report
+ coverage:
+ 	@echo "Building with support for coverage checking:"
+ 	$(MAKE) clean profile-removal
+-	$(MAKE) all CFLAGS="$(CFLAGS) -O0 -pg -fprofile-arcs -ftest-coverage" LIBS="$(LIBS) -lgcov"
++	$(MAKE) all CC="$(CC) -xprofile=tcov" \
++	    CFLAGS="$(CFLAGS) -xO1 -xprofile=tcov" \
++	    LDFLAGS="$(LDFLAGS) -xprofile=tcov" \
++	    BLDSHARED="$(BLDSHARED) -xprofile=tcov"
+ 
+ coverage-lcov:
+ 	@echo "Creating Coverage HTML report with LCOV:"
[email protected]@ -556,13 +565,9 @@
+ # -s, --silent or --quiet is always the first char.
+ # Under BSD make, MAKEFLAGS might be " -s -v x=y".
+ sharedmods: $(BUILDPYTHON) pybuilddir.txt
+-	@case "$$MAKEFLAGS" in \
+-	    *\ -s*|s*) quiet="-q";; \
+-	    *) quiet="";; \
+-	esac; \
+ 	$(RUNSHARED) CC='$(CC)' LDSHARED='$(BLDSHARED)' OPT='$(OPT)' \
+ 		_TCLTK_INCLUDES='$(TCLTK_INCLUDES)' _TCLTK_LIBS='$(TCLTK_LIBS)' \
+-		$(PYTHON_FOR_BUILD) $(srcdir)/setup.py $$quiet build
++		$(PYTHON_FOR_BUILD) $(srcdir)/setup.py build
+ 
+ # Build static library
+ # avoid long command lines, same as LIBRARY_OBJS
[email protected]@ -1575,7 +1580,7 @@
+ 	-rm -f Modules/_testembed Modules/_freeze_importlib
+ 
+ profile-removal:
+-	find . -name '*.gc??' -exec rm -f {} ';'
++	find . -name '*profile' -exec rm -f {} ';'
+ 	rm -f $(COVERAGE_INFO)
+ 	rm -rf $(COVERAGE_REPORT)
+ 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/components/python/python34/patches/06-solaris-64-bit.patch	Mon May 19 07:37:20 2014 -0700
@@ -0,0 +1,210 @@
+This patch ensures that 64-bit shared objects are in a subdirectory named
+"64".  Note that changes to the Lib/distutils/tests/test_build.py and
+Lib/distutils/tests/test_install.py avoid running tests that fail due to
+this patch.  As this is Solaris-specific, it is not suitable for upstream.
+
+--- Python-3.4.0/Lib/distutils/command/build_ext.py.~1~	2014-03-16 19:31:29.000000000 -0700
++++ Python-3.4.0/Lib/distutils/command/build_ext.py	2014-03-17 13:18:10.057787061 -0700
[email protected]@ -668,7 +668,12 @@
+         ext_suffix = get_config_var('EXT_SUFFIX')
+         if os.name == 'nt' and self.debug:
+             return os.path.join(*ext_path) + '_d' + ext_suffix
+-        return os.path.join(*ext_path) + ext_suffix
++        #return os.path.join(*ext_path) + ext_suffix
++        path = os.path.join (ext_path)
++        if sys.maxsize == 2147483647:
++            return os.path.join(*ext_path) + ext_suffix
++        (dirname, basename) = os.path.split(os.path.join(*ext_path));
++        return os.path.join(dirname, "64", basename + ext_suffix)
+ 
+     def get_export_symbols(self, ext):
+         """Return the list of symbols that a shared extension has to
+--- Python-3.4.0/Lib/distutils/tests/test_build_ext.py.~1~	2014-03-16 19:31:29.000000000 -0700
++++ Python-3.4.0/Lib/distutils/tests/test_build_ext.py	2014-03-17 13:18:10.098081226 -0700
[email protected]@ -317,7 +317,7 @@
+         ext_suffix = sysconfig.get_config_var('EXT_SUFFIX')
+         self.assertTrue(so_file.endswith(ext_suffix))
+         so_dir = os.path.dirname(so_file)
+-        self.assertEqual(so_dir, other_tmp_dir)
++        #self.assertEqual(so_dir, other_tmp_dir)
+ 
+         cmd.inplace = 0
+         cmd.compiler = None
[email protected]@ -364,7 +364,7 @@
+         curdir = os.getcwd()
+         wanted = os.path.join(curdir, 'src', 'lxml', 'etree' + ext)
+         path = cmd.get_ext_fullpath('lxml.etree')
+-        self.assertEqual(wanted, path)
++        #self.assertEqual(wanted, path)
+ 
+         # building lxml.etree not inplace
+         cmd.inplace = 0
+--- Python-3.4.0/Lib/sysconfig.py.~1~	2014-03-16 19:31:30.000000000 -0700
++++ Python-3.4.0/Lib/sysconfig.py	2014-03-17 13:18:10.099539252 -0700
[email protected]@ -392,7 +392,11 @@
+     if hasattr(sys, "gettotalrefcount"):
+         pybuilddir += '-pydebug'
+     os.makedirs(pybuilddir, exist_ok=True)
+-    destfile = os.path.join(pybuilddir, name + '.py')
++    if sys.maxsize == 2147483647:
++        destfile = os.path.join(pybuilddir, name + '.py')
++    else:
++        os.makedirs(pybuilddir + '/64', exist_ok=True)
++        destfile = os.path.join(pybuilddir + '/64', name + '.py')
+ 
+     with open(destfile, 'w', encoding='utf8') as f:
+         f.write('# system configuration generated and used by'
+--- Python-3.4.0/Modules/getpath.c.~1~	2014-03-16 19:31:31.000000000 -0700
++++ Python-3.4.0/Modules/getpath.c	2014-04-25 15:02:02.837613851 -0700
[email protected]@ -697,6 +697,10 @@
+         wcsncpy(exec_prefix, _exec_prefix, MAXPATHLEN);
+         joinpath(exec_prefix, L"lib/lib-dynload");
+     }
++    if (sizeof(void *) == 8 && wcslen(exec_prefix) + 3 <= MAXPATHLEN) {
++        wcscat(exec_prefix, L"/64");
++    }
++
+     /* If we found EXEC_PREFIX do *not* reduce it!  (Yet.) */
+ 
+     if ((!pfound || !efound) && !Py_FrozenFlag)
[email protected]@ -710,8 +714,30 @@
+     if (_rtpypath && _rtpypath[0] != '\0') {
+         size_t rtpypath_len;
+         rtpypath = _Py_char2wchar(_rtpypath, &rtpypath_len);
+-        if (rtpypath != NULL)
+-            bufsz += rtpypath_len + 1;
++        if (rtpypath != NULL) {
++            wchar_t *orig_rtpypath = rtpypath;
++
++            /*
++             * Split the path; for each component, add that component + "/64"
++             * (if in 64-bit mode) and the component unadorned (regardless).
++             */
++            while (1) {
++                wchar_t *delim = wcschr(rtpypath, DELIM);
++                if (delim) {
++                    /* once for usual, another for usual + "/64" */
++                    bufsz += delim - rtpypath + 1;
++                    if (sizeof(void *) == 8)
++                        bufsz += delim - rtpypath + 1 + 3;
++                } else {
++                    bufsz += wcslen(rtpypath) + 1;
++                    if (sizeof(void *) == 8)
++                        bufsz += wcslen(rtpypath) + 1 + 3;
++                    break;
++                }
++                rtpypath = delim + 1;
++            }
++            rtpypath = orig_rtpypath;
++        }
+     }
+ 
+     defpath = _pythonpath;
[email protected]@ -723,9 +749,19 @@
+             /* Paths are relative to prefix */
+             bufsz += prefixsz;
+ 
+-        if (delim)
++        if (delim) {
++            if (sizeof(void *) == 8) {
++                bufsz += delim - defpath + 1 + 3;
++                if (defpath[0] != SEP)
++                    bufsz += prefixsz;
++            }
+             bufsz += delim - defpath + 1;
+-        else {
++        } else {
++            if (sizeof(void *) == 8) {
++                bufsz += wcslen(defpath) + 1 + 3;
++                if (defpath[0] != SEP)
++                    bufsz += prefixsz;
++            }
+             bufsz += wcslen(defpath) + 1;
+             break;
+         }
[email protected]@ -741,13 +777,38 @@
+             "Not enough memory for dynamic PYTHONPATH");
+     }
+ 
++    buf[0] = '\0';
+     /* Run-time value of $PYTHONPATH goes first */
+     if (rtpypath) {
+-        wcscpy(buf, rtpypath);
+-        wcscat(buf, delimiter);
++        wchar_t *orig_rtpypath = rtpypath;
++
++        while (1) {
++            wchar_t *delim = wcschr(rtpypath, DELIM);
++
++            if (delim) {
++                *delim = '\0';
++                if (sizeof(void *) == 8) {
++                    wcscat(buf, rtpypath);
++                    wcscat(buf, L"/64");
++                    wcscat(buf, delimiter);
++                }
++                wcscat(buf, rtpypath);
++                wcscat(buf, delimiter);
++                *delim = DELIM;
++            } else {
++                if (sizeof(void *) == 8) {
++                    wcscat(buf, rtpypath);
++                    wcscat(buf, L"/64");
++                    wcscat(buf, delimiter);
++                }
++                wcscat(buf, rtpypath);
++                wcscat(buf, delimiter);
++                break;
++            }
++            rtpypath = delim + 1;
++        }
++        rtpypath = orig_rtpypath;
+     }
+-    else
+-        buf[0] = '\0';
+ 
+     /* Next is the default zip path */
+     wcscat(buf, zip_path);
[email protected]@ -766,18 +827,35 @@
+         }
+ 
+         if (delim) {
+-            size_t len = delim - defpath + 1;
+-            size_t end = wcslen(buf) + len;
+-            wcsncat(buf, defpath, len);
+-            *(buf + end) = '\0';
+-        }
+-        else {
++            *delim = '\0';
++            if (sizeof(void *) == 8) {
++                wcscat(buf, defpath);
++                wcscat(buf, L"/64");
++                wcscat(buf, delimiter);
++                if (defpath[0] != SEP) {
++                    wcscat(buf, prefix);
++                    wcscat(buf, separator);
++                }
++            }
+             wcscat(buf, defpath);
++            wcscat(buf, delimiter);
++            *delim = DELIM;
++        } else {
++            if (sizeof(void *) == 8) {
++                wcscat(buf, defpath);
++                wcscat(buf, L"/64");
++                wcscat(buf, delimiter);
++                if (defpath[0] != SEP) {
++                    wcscat(buf, prefix);
++                    wcscat(buf, separator);
++                }
++            }
++            wcscat(buf, defpath);
++            wcscat(buf, delimiter);
+             break;
+         }
+         defpath = delim + 1;
+     }
+-    wcscat(buf, delimiter);
+ 
+     /* Finally, on goes the directory for dynamic-load modules */
+     wcscat(buf, exec_prefix);
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/components/python/python34/patches/07-ucred.patch	Mon May 19 07:37:20 2014 -0700
@@ -0,0 +1,476 @@
+This patch provides Python ucred support.  It may be contributed upstream at
+some point, but the suitability (or lack thereof) has not yet been determined.
+
+diff --git Python-2.6.4/Modules/ucred.c Python-2.6.4/Modules/ucred.c
+new file mode 100644
+--- /dev/null
++++ Python-2.6.4/Modules/ucred.c
[email protected]@ -0,0 +1,404 @@
++/*
++ * Permission is hereby granted, free of charge, to any person obtaining a copy
++ * of this software and associated documentation files (the "Software"), to
++ * deal in the Software without restriction, including without limitation the
++ * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
++ * sell copies of the Software, and to permit persons to whom the Software is
++ * furnished to do so, subject to the following conditions:
++ *
++ * The above copyright notice and this permission notice shall be included in
++ * all copies or substantial portions of the Software.
++ *
++ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
++ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
++ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
++ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
++ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
++ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
++ * DEALINGS IN THE SOFTWARE.
++ *
++ * Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved.
++ */
++
++#include <Python.h>
++
++#include <stdio.h>
++#include <priv.h>
++#include <ucred.h>
++#include <ctype.h>
++#include <tsol/label.h>
++
++typedef struct {
++	PyObject_HEAD
++	ucred_t *ucred;
++} pyucred_t;
++
++#define pyucred_getlongid(name, type)				\
++	static PyObject *					\
++	pyucred_get##name(pyucred_t *uc)			\
++	{ 							\
++		type val;					\
++								\
++		if (uc->ucred == NULL) {			\
++			errno = EINVAL;				\
++			PyErr_SetFromErrno(PyExc_OSError);	\
++			return (NULL);				\
++		}						\
++								\
++		if ((val = ucred_get##name(uc->ucred)) == -1) {	\
++			PyErr_SetFromErrno(PyExc_OSError);	\
++			return (NULL);				\
++		}						\
++								\
++		return (Py_BuildValue("l", (long)val));		\
++	}
++
++pyucred_getlongid(euid, uid_t)
++pyucred_getlongid(ruid, uid_t)
++pyucred_getlongid(suid, uid_t)
++pyucred_getlongid(egid, gid_t)
++pyucred_getlongid(rgid, gid_t)
++pyucred_getlongid(sgid, gid_t)
++pyucred_getlongid(pid, pid_t)
++pyucred_getlongid(projid, projid_t)
++pyucred_getlongid(zoneid, zoneid_t)
++
++static PyObject *
++pyucred_getgroups(pyucred_t *uc)
++{
++	const gid_t *groups;
++	PyObject *list;
++	int len;
++	int i;
++
++	if (uc->ucred == NULL) {
++		errno = EINVAL;
++		PyErr_SetFromErrno(PyExc_OSError);
++		return (NULL);
++	}
++
++	if ((len = ucred_getgroups(uc->ucred, &groups)) == -1) {
++		PyErr_SetFromErrno(PyExc_OSError);
++		return (NULL);
++	}
++
++	if ((list = PyList_New(len)) == NULL)
++		return (NULL);
++
++	for (i = 0; i < len; i++) {
++		PyObject *gid = Py_BuildValue("l", (long)groups[i]);
++		if (PyList_SetItem(list, i, gid) == -1)
++			return (NULL);
++	}
++
++	return (list);
++}
++
++static PyObject *
++pyucred_getlabel(pyucred_t *uc)
++{
++	m_label_t *label;
++	PyObject *ret;
++	char *str;
++
++	if (uc->ucred == NULL) {
++		errno = EINVAL;
++		PyErr_SetFromErrno(PyExc_OSError);
++		return (NULL);
++	}
++
++	label = ucred_getlabel(uc->ucred);
++	if (label == NULL)
++		return (Py_BuildValue("s", ""));
++
++	if (label_to_str(label, &str, M_LABEL, DEF_NAMES) == -1) {
++		PyErr_SetFromErrno(PyExc_OSError);
++		return (NULL);
++	}
++
++	ret = Py_BuildValue("s", str);
++	free(str);
++	return (ret);
++}
++
++static PyObject *
++pyucred_getpflags(pyucred_t *uc, PyObject *args, PyObject *kwargs)
++{
++	static char *kwlist[] = { "flags", NULL };
++	uint_t flags;
++
++	if (uc->ucred == NULL) {
++		errno = EINVAL;
++		PyErr_SetFromErrno(PyExc_OSError);
++		return (NULL);
++	}
++
++	if (!PyArg_ParseTupleAndKeywords(args, kwargs, "i", kwlist,
++	    &flags))
++		return (NULL);
++
++	if ((flags = ucred_getpflags(uc->ucred, flags)) == (uint_t)-1) {
++		PyErr_SetFromErrno(PyExc_OSError);
++		return (NULL);
++	}
++
++	return (Py_BuildValue("i", flags));
++}
++
++static PyObject *
++pyucred_has_priv(pyucred_t *uc, PyObject *args, PyObject *kwargs)
++{
++	static char *kwlist[] = { "set", "priv", NULL };
++	const priv_set_t *privs;
++	const char *set;
++	const char *priv;
++
++	if (uc->ucred == NULL) {
++		errno = EINVAL;
++		PyErr_SetFromErrno(PyExc_OSError);
++		return (NULL);
++	}
++
++	if (!PyArg_ParseTupleAndKeywords(args, kwargs, "ss", kwlist,
++	    &set, &priv))
++		return (NULL);
++
++	if ((privs = ucred_getprivset(uc->ucred, set)) == NULL) {
++		PyErr_SetFromErrno(PyExc_OSError);
++		return (NULL);
++	}
++
++	if (priv_ismember(privs, priv)) {
++		Py_INCREF(Py_True);
++		return Py_True;
++	}
++
++	Py_INCREF(Py_False);
++	return Py_False;
++}
++
++PyDoc_STRVAR(pyucred_getlabel_doc,
++    "getlabel() -> string\n"
++    "\n"
++    "Return the Trusted Extensions label string, or an "
++    "empty string if not available. The label string is "
++    "converted using the default name and M_LABEL (human-readable). "
++    "Raises OSError. See label_to_str(3TSOL).");
++PyDoc_STRVAR(pyucred_getpflags_doc,
++    "getpflags(flags) -> int\n"
++    "\n"
++    "Return the values of the specified privilege flags.");
++PyDoc_STRVAR(pyucred_has_priv_doc,
++    "has_priv(set, priv) -> bool\n"
++    "\n"
++    "Return true if the given privilege is set in the "
++    "specified set. Raises OSError if the set or privilege is "
++    "invalid, or a problem occurs.\n"
++    "\n"
++    "Currently, the following privilege sets are defined, as "
++    "described in privileges(5):\n"
++    "\n"
++    "Effective\n"
++    "Permitted\n"
++    "Inheritable\n"
++    "Limit\n");
++
++static PyMethodDef pyucred_methods[] = {
++	{ "geteuid", (PyCFunction)pyucred_geteuid, METH_NOARGS,
++	    "Return the effective user ID." },
++	{ "getruid", (PyCFunction)pyucred_getruid, METH_NOARGS,
++	    "Return the real user ID." },
++	{ "getsuid", (PyCFunction)pyucred_getsuid, METH_NOARGS,
++	    "Return the saved user ID." },
++	{ "getegid", (PyCFunction)pyucred_getegid, METH_NOARGS,
++	    "Return the effective group ID." },
++	{ "getrgid", (PyCFunction)pyucred_getrgid, METH_NOARGS,
++	    "Return the real group ID." },
++	{ "getsgid", (PyCFunction)pyucred_getsgid, METH_NOARGS,
++	    "Return the saved group ID." },
++	{ "getpid", (PyCFunction)pyucred_getpid, METH_NOARGS,
++	    "Return the effective user ID." },
++	{ "getprojid", (PyCFunction)pyucred_getprojid, METH_NOARGS,
++	    "Return the project ID." },
++	{ "getzoneid", (PyCFunction)pyucred_getzoneid, METH_NOARGS,
++	    "Return the zone ID." },
++	{ "getgroups", (PyCFunction)pyucred_getgroups, METH_NOARGS,
++	    "Return a list of group IDs." },
++	{ "getlabel", (PyCFunction)pyucred_getlabel, METH_NOARGS,
++	    pyucred_getlabel_doc },
++	{ "getpflags", (PyCFunction)pyucred_getpflags,
++	    METH_VARARGS|METH_KEYWORDS, pyucred_getpflags_doc },
++	{ "has_priv", (PyCFunction)pyucred_has_priv,
++	    METH_VARARGS|METH_KEYWORDS, pyucred_has_priv_doc },
++	{ NULL, NULL }
++};
++
++static int
++pyucred_init(PyObject *self, PyObject *args, PyObject *kwargs)
++{
++	pyucred_t *uc = (pyucred_t *)self;
++	uc->ucred = NULL;
++	return (0);
++}
++
++static void
++pyucred_dealloc(PyObject *self)
++{
++	pyucred_t *uc = (pyucred_t *)self;
++	if (uc->ucred != NULL)
++		ucred_free(uc->ucred);
++	Py_TYPE(self)->tp_free(self);
++}
++
++static PyTypeObject pyucred_type = {
++	PyVarObject_HEAD_INIT(NULL, 0)
++	"ucred.ucred",             /*tp_name*/
++	sizeof (pyucred_t),        /*tp_basicsize*/
++	0,                         /*tp_itemsize*/
++	pyucred_dealloc,           /*tp_dealloc*/
++	0,                         /*tp_print*/
++	0,                         /*tp_getattr*/
++	0,                         /*tp_setattr*/
++	0,                         /*tp_reserved*/
++	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*/
++	"user credentials",        /*tp_doc */
++	0,		           /* tp_traverse */
++	0,		           /* tp_clear */
++	0,		           /* tp_richcompare */
++	0,		           /* tp_weaklistoffset */
++	0,		           /* tp_iter */
++	0,		           /* tp_iternext */
++	pyucred_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)pyucred_init,    /* tp_init */
++	0,                         /* tp_alloc */
++	0,                         /* tp_new */
++	0,                         /* tp_free */
++	0,                         /* tp_is_gc */
++};
++
++static PyObject *
++pyucred_new(const ucred_t *uc)
++{
++	pyucred_t *self;
++
++	self = (pyucred_t *)PyObject_CallObject((PyObject *)&pyucred_type, NULL);
++
++	if (self == NULL)
++		return (NULL);
++
++	self->ucred = (ucred_t *)uc;
++
++	return ((PyObject *)self);
++}
++
++static PyObject *
++pyucred_get(PyObject *o, PyObject *args, PyObject *kwargs)
++{
++	static char *kwlist[] = { "pid", NULL };
++	ucred_t *ucred = NULL;
++	int pid;
++
++	if (!PyArg_ParseTupleAndKeywords(args, kwargs, "i", kwlist,
++	    &pid))
++		return (NULL);
++
++	ucred = ucred_get(pid);
++
++	if (ucred == NULL) {
++		PyErr_SetFromErrno(PyExc_OSError);
++		return (NULL);
++	}
++
++	return (pyucred_new(ucred));
++}
++
++static PyObject *
++pyucred_getpeer(PyObject *o, PyObject *args, PyObject *kwargs)
++{
++	static char *kwlist[] = { "fd", NULL };
++	ucred_t *ucred = NULL;
++	int fd;
++
++	if (!PyArg_ParseTupleAndKeywords(args, kwargs, "i", kwlist,
++	    &fd))
++		return (NULL);
++
++	if (getpeerucred(fd, &ucred) == -1) {
++		PyErr_SetFromErrno(PyExc_OSError);
++		return (NULL);
++	}
++
++	return (pyucred_new(ucred));
++}
++
++PyDoc_STRVAR(pyucred_get_doc,
++    "get(pid) -> ucred\n"
++    "\n"
++    "Return the credentials of the specified process ID. "
++    "Raises OSError. See ucred_get(3C).");
++PyDoc_STRVAR(pyucred_getpeer_doc,
++    "getpeer(fd) -> ucred\n"
++    "\n"
++    "Return the credentials of the peer endpoint of a "
++    "connection-oriented socket (SOCK_STREAM) or STREAM fd "
++    "at the time the endpoint was created or the connection "
++    "was established. Raises OSError. See getpeerucred(3C).");
++
++static struct PyMethodDef pyucred_module_methods[] = {
++	{ "get", (PyCFunction) pyucred_get,
++	  METH_VARARGS|METH_KEYWORDS, pyucred_get_doc },
++	{ "getpeer", (PyCFunction) pyucred_getpeer,
++	  METH_VARARGS|METH_KEYWORDS, pyucred_getpeer_doc },
++	{ NULL, NULL, 0, NULL }
++};
++
++PyDoc_STRVAR(pyucred_module_doc,
++    "This module provides an interface to the user credential access "
++    "methods, obtainable either by process ID or file descriptor.");
++
++PyMODINIT_FUNC
++PyInit_ucred (void)
++{
++	PyObject *m;
++
++	static struct PyModuleDef moduledef = {
++	    PyModuleDef_HEAD_INIT,
++	    "ucred",
++	    pyucred_module_doc,
++	    -1,
++	    pyucred_module_methods,
++	    NULL,
++	    NULL,
++	    NULL,
++	    NULL,
++	};
++
++	m = PyModule_Create(&moduledef);
++
++	pyucred_type.tp_new = PyType_GenericNew;
++	if (PyType_Ready(&pyucred_type) < 0)
++		return NULL;
++
++	Py_INCREF(&pyucred_type);
++
++	PyModule_AddObject(m, "ucred", (PyObject *)&pyucred_type);
++
++	return m;
++}
+--- Python-3.4.0/setup.py.~3~	2014-03-19 10:44:16.508585670 -0700
++++ Python-3.4.0/setup.py	2014-03-19 10:44:16.596735089 -0700
[email protected]@ -1467,6 +1467,13 @@
+         # Stefan Krah's _decimal module
+         exts.append(self._decimal_ext())
+ 
++        # ucred module (Solaris)
++        ucred_inc = find_file('ucred.h', [], inc_dirs)
++        tsol_inc = find_file('tsol/label.h', [], inc_dirs)
++        if ucred_inc is not None and tsol_inc is not None:
++            exts.append( Extension('ucred', ['ucred.c'],
++                                   libraries = ['tsol']) )
++
+         # Thomas Heller's _ctypes module
+         self.detect_ctypes(inc_dirs, lib_dirs)
+ 
+--- /dev/null	2011-02-12 03:14:16.000000000 -0600
++++ Python-2.6.4/Lib/test/ucredtest.py	2011-01-20 13:52:42.945657919 -0600
[email protected]@ -0,0 +1,45 @@
++#!/usr/bin/python3.4
++
++import ucred
++import os
++
++uc = ucred.get(os.getpid())
++
++print("pid = %d" % uc.getpid())
++print("euid = %d" % uc.geteuid())
++print("ruid = %d" % uc.getruid())
++print("suid = %d" % uc.getsuid())
++print("egid = %d" % uc.getegid())
++print("rgid = %d" % uc.getrgid())
++print("sgid = %d" % uc.getsgid())
++print("zoneid = %d" % uc.getzoneid())
++print("projid = %d" % uc.getprojid())
++print("groups = %s" % uc.getgroups())
++print("label = %s" % uc.getlabel())
++
++print("getpflags(0x1) = %d" % uc.getpflags(0x1))
++print("getpflags(0x2) = %d" % uc.getpflags(0x2))
++print("has_priv(Effective, proc_fork) = %d" % uc.has_priv("Effective", "proc_fork"))
++print("has_priv(Permitted, proc_fork) = %d" % uc.has_priv("Permitted", "proc_fork"))
++print("has_priv(Inheritable, proc_fork) = %d" % uc.has_priv("Inheritable", "proc_fork"))
++print("has_priv(Limit, file_setid) = %d" % uc.has_priv("Limit", "file_setid"))
++print("has_priv(Effective, file_setid) = %d" % uc.has_priv("Effective", "file_setid"))
++try:
++    uc.has_priv("Effective", "proc_bork")
++except OSError as e:
++    print(e)
++try:
++    uc.has_priv("Defective", "proc_fork")
++except OSError as e:
++    print(e)
++try:
++    uc.has_priv("Defective", "proc_bork")
++except OSError as e:
++    print(e)
++
++del uc
++uc = ucred.ucred()
++try:
++    uc.getpid()
++except OSError as e:
++    print(e)
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/components/python/python34/patches/08-dlpi.patch	Mon May 19 07:37:20 2014 -0700
@@ -0,0 +1,1341 @@
+This patch provides Python dlpi support.  It may be contributed upstream at
+some point, but the suitability (or lack thereof) has not yet been determined.
+
+--- /dev/null
++++ Python-3.4.0/Modules/dlpimodule.c
[email protected]@ -0,0 +1,1219 @@
++/*
++ * Permission is hereby granted, free of charge, to any person obtaining a copy
++ * of this software and associated documentation files (the "Software"), to
++ * deal in the Software without restriction, including without limitation the
++ * rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
++ * sell copies of the Software, and to permit persons to whom the Software is
++ * furnished to do so, subject to the following conditions:
++ *
++ * The above copyright notice and this permission notice shall be included in
++ * all copies or substantial portions of the Software.
++ *
++ * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
++ * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
++ * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
++ * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
++ * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
++ * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
++ * DEALINGS IN THE SOFTWARE.
++ *
++ * Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved.
++ */
++
++#include <Python.h>
++#include <stdio.h>
++#include <libdlpi.h>
++
++typedef struct {
++	PyObject_HEAD
++	dlpi_handle_t dlpihdl;
++} pylink_t;
++
++typedef struct {
++	PyObject *pyfunc;
++	PyObject *pyarg;
++} callback_data_t;
++
++/*
++ * dlpi_err: the only exception raised for libdlpi related error.
++ * The accompanying value is:
++ * (dlpi_error_number, string), when it's a dlpi specific error,
++ * or, (DL_SYSERR, errno, string), when it's coming from a system call.
++ */
++static PyObject *dlpi_err;
++
++static void
++dlpi_raise_exception(int err)
++{
++	PyObject *e = NULL;
++
++	if (err == DL_SYSERR) {
++		e = Py_BuildValue("(iis)", DL_SYSERR, errno, strerror(errno));
++	} else {
++		e = Py_BuildValue("(is)", err, dlpi_strerror(err));
++	}
++	if (e != NULL) {
++		PyErr_SetObject(dlpi_err, e);
++		Py_DECREF(e);
++	}
++}
++
++PyDoc_STRVAR(link_doc,
++    "link(linkname[, flags]) -> link object\n"
++    "\n"
++    "Open linkname with specified flags.\n"
++    "Three flags are supported: PASSIVE, RAW, NATIVE.\n"
++    "And these flags can be bitwise-OR'ed together(default flag is 0).\n"
++    "You need sys_net_rawaccess privilege to open a link.\n"
++    "See dlpi_open(3DLPI).\n"
++);
++static int
++link_init(PyObject *self, PyObject *args, PyObject *kwds)
++{
++	uint_t flags = 0;
++	dlpi_handle_t dh;
++	char *linkname;
++	int rval;
++	static char *keywords[] = {"linkname", "flags", NULL};
++	pylink_t *link = (pylink_t *)self;
++
++	if (!PyArg_ParseTupleAndKeywords(args, kwds, "s|I", keywords,
++	    &linkname, &flags))
++		return (-1);
++
++	if ((rval = dlpi_open(linkname, &dh, flags)) != DLPI_SUCCESS) {
++		dlpi_raise_exception(rval);
++		return (-1);
++	}
++
++	link->dlpihdl = dh;
++
++	return (0);
++}
++
++static void
++link_dealloc(pylink_t *link)
++{
++	if (link->dlpihdl != NULL)
++		dlpi_close(link->dlpihdl);
++	Py_TYPE(link)->tp_free((PyObject *)link);
++}
++
++PyDoc_STRVAR(bind_doc,
++    "bind(sap) -> unsigned int\n"
++    "\n"
++    "Attempts to bind the link to specified SAP, or ANY_SAP.\n"
++    "Returns the SAP that the function actually bound to, which\n"
++    "could be different from the SAP requested.\n"
++    "See dlpi_bind(3DLPI).\n"
++);
++static PyObject *
++link_bind(pylink_t *link, PyObject *args, PyObject *kwds)
++{
++	uint_t sap = 0, boundsap = 0;
++	static char *keywords[] = {"sap", NULL};
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if (!PyArg_ParseTupleAndKeywords(args, kwds, "I", keywords, &sap))
++		return (NULL);
++
++	if ((rval = dlpi_bind(link->dlpihdl, sap, &boundsap)) !=
++	    DLPI_SUCCESS) {
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	return (Py_BuildValue("I", boundsap));
++}
++
++PyDoc_STRVAR(unbind_doc,
++    "unbind() -> None\n"
++    "\n"
++    "Attempts to unbind the link from previously bound sap.\n"
++    "See dlpi_unbind(3DLPI).\n"
++);
++static PyObject *
++link_unbind(pylink_t *link)
++{
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if ((rval = dlpi_unbind(link->dlpihdl)) != DLPI_SUCCESS) {
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	Py_INCREF(Py_None);
++	return (Py_None);
++}
++
++PyDoc_STRVAR(send_doc,
++    "send(destaddr, message[, sap, minpri, maxpri]) -> None\n"
++    "\n"
++    "Attempts to send message over this link to sap on destaddr.\n"
++    "If SAP is not specified, the bound SAP is used\n"
++    "You can also specify priority range (minpri, maxpri).\n"
++    "See dlpi_send(3DLPI).\n"
++);
++static PyObject *
++link_send(pylink_t *link, PyObject *args, PyObject *kwds)
++{
++	char *daddr = NULL, *msgbuf = NULL;
++	size_t daddrlen = 0, msglen = 0;
++	t_scalar_t minpri = DL_QOS_DONT_CARE, maxpri = DL_QOS_DONT_CARE;
++	uint_t sap = DLPI_ANY_SAP;
++	dlpi_sendinfo_t ds, *dsp = NULL;
++	static char *keywords[] =
++	    {"destaddr", "message", "sap", "minpri", "maxpri", NULL};
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if (!PyArg_ParseTupleAndKeywords(args, kwds, "s#s#|Iii", keywords,
++	    &daddr, &daddrlen, &msgbuf, &msglen, &sap, &minpri, &maxpri))
++		return (NULL);
++
++	if ((sap != DLPI_ANY_SAP) || (minpri != DL_QOS_DONT_CARE) ||
++	    (maxpri != DL_QOS_DONT_CARE)) {
++		ds.dsi_sap = sap;
++		ds.dsi_prio.dl_min = minpri;
++		ds.dsi_prio.dl_max = maxpri;
++		dsp = &ds;
++	}
++
++	if ((rval = dlpi_send(link->dlpihdl, daddr, daddrlen,
++	    msgbuf, msglen, dsp)) != DLPI_SUCCESS) {
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	Py_INCREF(Py_None);
++	return (Py_None);
++}
++
++PyDoc_STRVAR(recv_doc,
++    "recv(msglen[, timeout]) -> (string, string), or (None, None)\n"
++    "\n"
++    "Attempts to receive message over this link.\n"
++    "You need to specify the message length for the received message.\n"
++    "And you can specify timeout value in milliseconds.\n"
++    "The default timeout value is -1 (wait forever).\n"
++    "Returns (source address, message data), or (None, None) when error occurs.\n"
++    "See dlpi_recv(3DLPI).\n"
++);
++static PyObject *
++link_recv(pylink_t *link, PyObject *args, PyObject *kwds)
++{
++	PyObject *obj;
++	char *saddr = NULL, *msgbuf = NULL;
++	size_t saddrlen = 0, msglen = 0, *saddrlenp = NULL, *msglenp = NULL;
++	int msec = -1; /* block until receive data */
++	static char *keywords[] = {"msglen", "timeout", NULL};
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if (!PyArg_ParseTupleAndKeywords(args, kwds, "k|i",
++	    keywords, &msglen, &msec))
++		return (NULL);
++
++	if (msglen > 0) {
++		msgbuf = malloc(msglen);
++		if (msgbuf == NULL) {
++			dlpi_raise_exception(DL_SYSERR);
++			return (NULL);
++		}
++		saddrlen = DLPI_PHYSADDR_MAX;
++		saddr = malloc(saddrlen);
++		if (saddr == NULL) {
++			dlpi_raise_exception(DL_SYSERR);
++			free(msgbuf);
++			return (NULL);
++		}
++		msglenp = &msglen;
++		saddrlenp = &saddrlen;
++	}
++
++	if ((rval = dlpi_recv(link->dlpihdl, saddr, saddrlenp, msgbuf,
++	    msglenp, msec, NULL)) != DLPI_SUCCESS) {
++		if (msgbuf != NULL)
++			free(msgbuf);
++		if (saddr != NULL)
++			free(saddr);
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	obj = Py_BuildValue("s#s#", saddr, saddrlen, msgbuf, msglen);
++	if (msgbuf != NULL)
++		free(msgbuf);
++	if (saddr != NULL)
++		free(saddr);
++	return (obj);
++}
++
++PyDoc_STRVAR(disabmulti_doc,
++    "disabmulti(address) -> None\n"
++    "\n"
++    "Disable a specified multicast address on this link.\n"
++    "See dlpi_disabmulti(3DLPI).\n"
++);
++static PyObject *
++link_disabmulti(pylink_t *link, PyObject *args, PyObject *kwds)
++{
++	char *addr = NULL;
++	size_t addrlen = 0;
++	static char *keywords[] = {"address", NULL};
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if (!PyArg_ParseTupleAndKeywords(args, kwds, "s#", keywords,
++	    &addr, &addrlen))
++		return (NULL);
++
++	if ((addrlen == 0) || (addrlen > DLPI_PHYSADDR_MAX)) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if ((rval = dlpi_disabmulti(link->dlpihdl, addr, addrlen)) !=
++	    DLPI_SUCCESS) {
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	Py_INCREF(Py_None);
++	return (Py_None);
++}
++
++PyDoc_STRVAR(enabmulti_doc,
++    "enabmulti(address) -> None\n"
++    "\n"
++    "Enable a specified multicast address on this link.\n"
++    "See dlpi_enabmulti(3DLPI).\n"
++);
++static PyObject *
++link_enabmulti(pylink_t *link, PyObject *args, PyObject *kwds)
++{
++	char *addr = NULL;
++	size_t addrlen = 0;
++	static char *keywords[] = {"address", NULL};
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if (!PyArg_ParseTupleAndKeywords(args, kwds, "s#", keywords,
++	    &addr, &addrlen))
++		return (NULL);
++
++	if ((addrlen == 0) || (addrlen > DLPI_PHYSADDR_MAX)) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if ((rval = dlpi_enabmulti(link->dlpihdl, addr, addrlen)) !=
++	    DLPI_SUCCESS) {
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	Py_INCREF(Py_None);
++	return (Py_None);
++}
++
++static void
++dlpi_callback(dlpi_handle_t hdl, dlpi_notifyinfo_t *ni, void *arg)
++{
++	callback_data_t *cd = (callback_data_t *)arg;
++	PyObject *arglist, *result;
++
++	switch (ni->dni_note) {
++	case DL_NOTE_SPEED:
++		arglist = Py_BuildValue("(OII)",
++		    cd->pyarg, ni->dni_note, ni->dni_speed);
++		break;
++	case DL_NOTE_SDU_SIZE:
++		arglist = Py_BuildValue("(OII)",
++		    cd->pyarg, ni->dni_note, ni->dni_size);
++		break;
++	case DL_NOTE_PHYS_ADDR:
++		arglist = Py_BuildValue("(OIs#)",
++		    cd->pyarg, ni->dni_note, ni->dni_physaddr,
++		    ni->dni_physaddrlen);
++		break;
++	default:
++		arglist = Py_BuildValue("(OIO)", cd->pyarg, ni->dni_note,
++		    Py_None);
++	}
++
++	result = PyEval_CallObject(cd->pyfunc, arglist);
++	Py_DECREF(arglist);
++	if (result == NULL) {
++		PyErr_Clear(); /* cannot raise error */
++	}
++	Py_DECREF(result);
++	Py_DECREF(cd->pyfunc);
++	Py_XDECREF(cd->pyarg);
++	free(cd);
++}
++
++PyDoc_STRVAR(enabnotify_doc,
++    "enabnotify(events, function[, arg]) -> unsigned long\n"
++    "\n"
++    "Enables a notification callback for the set of specified events,\n"
++    "which must be one or more (by a logical OR) events listed as below:\n"
++    "NOTE_LINK_DOWN         Notify when link has gone down\n"
++    "NOTE_LINK_UP           Notify when link has come up\n"
++    "NOTE_PHYS_ADDR         Notify when address changes\n"
++    "NOTE_SDU_SIZE          Notify when MTU changes\n"
++    "NOTE_SPEED             Notify when speed changes\n"
++    "NOTE_PROMISC_ON_PHYS   Notify when PROMISC_PHYS is set\n"
++    "NOTE_PROMISC_OFF_PHYS  Notify when PROMISC_PHYS is cleared\n"
++    "Returns a handle for this registration.\n"
++    "See dlpi_enabnotify(3DLPI).\n"
++);
++static PyObject *
++link_enabnotify(pylink_t *link, PyObject *args, PyObject *kwds)
++{
++	PyObject *func = NULL, *arg = NULL;
++	callback_data_t *cd;
++	uint_t notes = 0;
++	static char *keywords[] = {"events", "function", "arg", NULL};
++	dlpi_notifyid_t id;
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if (!PyArg_ParseTupleAndKeywords(args, kwds, "IO|O",
++	    keywords, &notes, &func, &arg))
++		return (NULL);
++
++	if (!PyCallable_Check(func)) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	cd = malloc(sizeof(callback_data_t));
++	if (cd == NULL) {
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++	Py_INCREF(func);
++	Py_XINCREF(arg);
++	cd->pyfunc = func;
++	cd->pyarg = arg;
++
++	if ((rval = dlpi_enabnotify(link->dlpihdl, notes, dlpi_callback,
++	    cd, &id)) != DLPI_SUCCESS) {
++		free(cd);
++		Py_DECREF(func);
++		Py_XDECREF(arg);
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	return (Py_BuildValue("k", id));
++}
++
++PyDoc_STRVAR(disabnotify_doc,
++    "disabnotify(handle) -> argument object, or None\n"
++    "\n"
++    "Disables the notification registration associated with handle.\n"
++    "You should get this handle by calling enabnotify().\n"
++    "Returns the argument passed in when registering the callback, or None.\n"
++    "See dlpi_disabnotify(3DLPI).\n"
++);
++static PyObject *
++link_disabnotify(pylink_t *link, PyObject *args, PyObject *kwds)
++{
++	dlpi_notifyid_t id;
++	callback_data_t *arg;
++	PyObject *pyargsaved;
++	static char *keywords[] = {"handle", NULL};
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if (!PyArg_ParseTupleAndKeywords(args, kwds, "k", keywords, &id))
++		return (NULL);
++
++	if ((rval = dlpi_disabnotify(link->dlpihdl, id, (void **)&arg)) !=
++	    DLPI_SUCCESS) {
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	/* clean up */
++	pyargsaved = arg->pyarg;
++	Py_XINCREF(pyargsaved);
++	Py_XDECREF(arg->pyarg);
++	Py_DECREF(arg->pyfunc);
++	free(arg);
++
++	if (pyargsaved != NULL)
++		return (pyargsaved);
++
++	Py_INCREF(Py_None);
++	return (Py_None);
++}
++
++PyDoc_STRVAR(get_sap_doc,
++    "get_sap() -> unsigned int\n"
++    "\n"
++    "Returns the sap bound to this link.\n"
++    "See dlpi_info(3DLPI).\n"
++);
++static PyObject *
++link_get_sap(pylink_t *link)
++{
++	dlpi_info_t info;
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if ((rval = dlpi_info(link->dlpihdl, &info, 0)) !=
++	    DLPI_SUCCESS) {
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	return (Py_BuildValue("I", info.di_sap));
++}
++
++PyDoc_STRVAR(get_fd_doc,
++    "get_fd() -> int\n"
++    "\n"
++    "Returns the integer file descriptor that can be used to directly\n"
++    "operate on the link.\n"
++    "See dlpi_fd(3DLPI).\n"
++);
++static PyObject *
++link_get_fd(pylink_t *link)
++{
++	int fd;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if ((fd = dlpi_fd(link->dlpihdl)) == -1) {
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	return (Py_BuildValue("i", fd));
++}
++
++PyDoc_STRVAR(get_linkname_doc,
++    "get_linkname() -> string\n"
++    "\n"
++    "Returns the name of the link.\n"
++    "See dlpi_linkname(3DLPI).\n"
++);
++static PyObject *
++link_get_linkname(pylink_t *link)
++{
++	const char *name = NULL;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if ((name = dlpi_linkname(link->dlpihdl)) == NULL) {
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	return (Py_BuildValue("s", name));
++}
++
++PyDoc_STRVAR(get_bcastaddr_doc,
++    "get_bcastaddr() -> string, or None\n"
++    "\n"
++    "Returns the broadcast address of the link.\n"
++    "Returns None if the broadcast address is empty.\n"
++    "See dlpi_info(3DLPI).\n"
++);
++static PyObject *
++link_get_bcastaddr(pylink_t *link)
++{
++	char *addr[DLPI_PHYSADDR_MAX];
++	size_t addrlen = 0;
++	dlpi_info_t info;
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if ((rval = dlpi_info(link->dlpihdl, &info, 0)) !=
++	    DLPI_SUCCESS) {
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	if (info.di_bcastaddrlen == 0) {
++		Py_INCREF(Py_None);
++		return (Py_None);
++	}
++
++	return (Py_BuildValue("s#", info.di_bcastaddr, info.di_bcastaddrlen));
++}
++
++PyDoc_STRVAR(get_physaddr_doc,
++    "get_physaddr(addrtype) -> string, or None\n"
++    "\n"
++    "Addrtype can be any one of the value listed below:\n"
++    "FACT_PHYS_ADDR    Factory physical address\n"
++    "CURR_PHYS_ADDR    Current physical address\n"
++    "Returns the corresponding physical address of the link.\n"
++    "See dlpi_get_physaddr(3DLPI).\n"
++);
++static PyObject *
++link_get_physaddr(pylink_t *link, PyObject *args, PyObject *kwds)
++{
++	char *addr[DLPI_PHYSADDR_MAX];
++	size_t addrlen = DLPI_PHYSADDR_MAX;
++	static char *keywords[] = {"addrtype", NULL};
++	uint_t type;
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if (!PyArg_ParseTupleAndKeywords(args, kwds, "I", keywords, &type))
++		return (NULL);
++
++	if ((rval = dlpi_get_physaddr(link->dlpihdl, type, addr, &addrlen)) !=
++	    DLPI_SUCCESS) {
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	return (Py_BuildValue("s#", addr, addrlen));
++}
++
++PyDoc_STRVAR(set_physaddr_doc,
++    "set_physaddr(address) -> None\n"
++    "\n"
++    "Sets the physical address of the link.\n"
++    "See dlpi_set_physaddr(3DLPI).\n"
++);
++static PyObject *
++link_set_physaddr(pylink_t *link, PyObject *args, PyObject *kwds)
++{
++	char *addr = NULL;
++	size_t addrlen = 0;
++	static char *keywords[] = {"address", NULL};
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if (!PyArg_ParseTupleAndKeywords(args, kwds, "s#", keywords,
++	    &addr, &addrlen))
++		return (NULL);
++
++	if ((rval = dlpi_set_physaddr(link->dlpihdl, DL_CURR_PHYS_ADDR,
++	    addr, addrlen)) != DLPI_SUCCESS) {
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	Py_INCREF(Py_None);
++	return (Py_None);
++}
++
++PyDoc_STRVAR(promiscon_doc,
++    "promiscon([level]) -> None\n"
++    "\n"
++    "Enables promiscuous mode for the link at levels:\n"
++    "PROMISC_PHYS     Promiscuous mode at the physical level(default)\n"
++    "PROMISC_SAP      Promiscuous mode at the SAP level\n"
++    "PROMISC_MULTI    Promiscuous mode for all multicast addresses\n"
++    "See dlpi_promiscon(3DLPI).\n"
++);
++static PyObject *
++link_promiscon(pylink_t *link, PyObject *args, PyObject *kwds)
++{
++	uint_t level = DL_PROMISC_PHYS;
++	static char *keywords[] = {"level", NULL};
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if (!PyArg_ParseTupleAndKeywords(args, kwds, "|I", keywords, &level))
++		return (NULL);
++
++	if ((rval = dlpi_promiscon(link->dlpihdl, level)) != DLPI_SUCCESS) {
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	Py_INCREF(Py_None);
++	return (Py_None);
++}
++
++PyDoc_STRVAR(promiscoff_doc,
++    "promiscoff([level]) -> None\n"
++    "\n"
++    "Disables promiscuous mode for the link at levels:\n"
++    "PROMISC_PHYS     Promiscuous mode at the physical level(default)\n"
++    "PROMISC_SAP      Promiscuous mode at the SAP level\n"
++    "PROMISC_MULTI    Promiscuous mode for all multicast addresses\n"
++    "See dlpi_promiscoff(3DLPI).\n"
++);
++static PyObject *
++link_promiscoff(pylink_t *link, PyObject *args, PyObject *kwds)
++{
++	uint_t level = DL_PROMISC_PHYS;
++	static char *keywords[] = {"level", NULL};
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if (!PyArg_ParseTupleAndKeywords(args, kwds, "|I", keywords, &level))
++		return (NULL);
++
++	if ((rval = dlpi_promiscoff(link->dlpihdl, level)) != DLPI_SUCCESS) {
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	Py_INCREF(Py_None);
++	return (Py_None);
++}
++
++PyDoc_STRVAR(get_timeout_doc,
++    "get_timeout() -> int\n"
++    "\n"
++    "Returns current time out value of the link.\n"
++    "See dlpi_info(3DLPI).\n"
++);
++static PyObject *
++link_get_timeout(pylink_t *link)
++{
++	dlpi_info_t info;
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if ((rval = dlpi_info(link->dlpihdl, &info, 0)) !=
++	    DLPI_SUCCESS) {
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	return (Py_BuildValue("i", info.di_timeout));
++}
++
++PyDoc_STRVAR(get_mactype_doc,
++    "get_mactype() -> unsigned char\n"
++    "\n"
++    "Returns MAC type of the link.\n"
++    "See <sys/dlpi.h> for the list of possible MAC types.\n"
++    "See dlpi_info(3DLPI).\n"
++);
++static PyObject *
++link_get_mactype(pylink_t *link)
++{
++	dlpi_info_t info;
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if ((rval = dlpi_info(link->dlpihdl, &info, 0)) !=
++	    DLPI_SUCCESS) {
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	return (Py_BuildValue("B", info.di_mactype));
++}
++
++PyDoc_STRVAR(set_timeout_doc,
++    "set_timeout(timeout) -> None\n"
++    "\n"
++    "Sets time out value of the link (default value: DEF_TIMEOUT).\n"
++    "See dlpi_set_timeout(3DLPI).\n"
++);
++static PyObject *
++link_set_timeout(pylink_t *link, PyObject *args, PyObject *kwds)
++{
++	int timeout = DLPI_DEF_TIMEOUT;
++	static char *keywords[] = {"timeout", NULL};
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if (!PyArg_ParseTupleAndKeywords(args, kwds, "i", keywords, &timeout))
++		return (NULL);
++
++	if ((rval = dlpi_set_timeout(link->dlpihdl, timeout)) != DLPI_SUCCESS) {
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	Py_INCREF(Py_None);
++	return (Py_None);
++}
++
++PyDoc_STRVAR(get_sdu_doc,
++    "get_sdu() -> (unsigned int, unsigned int)\n"
++    "\n"
++    "Returns (min sdu, max sdu).\n"
++    "See dlpi_info(3DLPI).\n"
++);
++static PyObject *
++link_get_sdu(pylink_t *link)
++{
++	dlpi_info_t info;
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if ((rval = dlpi_info(link->dlpihdl, &info, 0)) !=
++	    DLPI_SUCCESS) {
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	return (Py_BuildValue("II", info.di_min_sdu, info.di_max_sdu));
++}
++
++PyDoc_STRVAR(get_state_doc,
++    "get_state() -> unsigned int\n"
++    "\n"
++    "Returns current state of the link (either UNBOUND or IDLE).\n"
++    "See dlpi_info(3DLPI).\n"
++);
++static PyObject *
++link_get_state(pylink_t *link)
++{
++	dlpi_info_t info;
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if ((rval = dlpi_info(link->dlpihdl, &info, 0)) !=
++	    DLPI_SUCCESS) {
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	return (Py_BuildValue("I", info.di_state));
++}
++
++PyDoc_STRVAR(get_qos_select_doc,
++    "get_qos_select() -> (unsigned int, int, int, int)\n"
++    "\n"
++    "Returns (qos type, trans delay, priority, residul err).\n"
++    "Unsupported QOS parameters are set to UNKNOWN.\n"
++    "See dlpi_info(3DLPI).\n"
++);
++static PyObject *
++link_get_qos_select(pylink_t *link)
++{
++	dlpi_info_t info;
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if ((rval = dlpi_info(link->dlpihdl, &info, 0)) !=
++	    DLPI_SUCCESS) {
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	return (Py_BuildValue("Iiiii",
++	    info.di_qos_sel.dl_qos_type,
++	    info.di_qos_sel.dl_trans_delay,
++	    info.di_qos_sel.dl_priority,
++	    info.di_qos_sel.dl_residual_error));
++}
++
++PyDoc_STRVAR(get_qos_range_doc,
++    "get_qos_range() -> \n"
++    "	(unsigned int, (int, int), (int, int), (int, int), int)\n"
++    "\n"
++    "Returns (qos type, (trans delay target, trans delay accept),\n"
++    "(min priority, max priority), (min protection, max protection),\n"
++    "residual err).\n"
++    "Unsupported QOS range values are set to UNKNOWN.\n"
++    "See dlpi_info(3DLPI).\n"
++);
++static PyObject *
++link_get_qos_range(pylink_t *link)
++{
++	dlpi_info_t info;
++	int rval;
++
++	if (link->dlpihdl == NULL) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	if ((rval = dlpi_info(link->dlpihdl, &info, 0)) !=
++	    DLPI_SUCCESS) {
++		dlpi_raise_exception(rval);
++		return (NULL);
++	}
++
++	return (Py_BuildValue("I(ii)(ii)(ii)i",
++	    info.di_qos_range.dl_qos_type,
++	    info.di_qos_range.dl_trans_delay.dl_target_value,
++	    info.di_qos_range.dl_trans_delay.dl_accept_value,
++	    info.di_qos_range.dl_priority.dl_min,
++	    info.di_qos_range.dl_priority.dl_max,
++	    info.di_qos_range.dl_protection.dl_min,
++	    info.di_qos_range.dl_protection.dl_max,
++	    info.di_qos_range.dl_residual_error));
++}
++
++static PyMethodDef pylink_methods[] = {
++	{"bind", (PyCFunction)link_bind, METH_VARARGS|METH_KEYWORDS, bind_doc},
++	{"unbind", (PyCFunction)link_unbind, METH_NOARGS, unbind_doc},
++	{"send", (PyCFunction)link_send, METH_VARARGS|METH_KEYWORDS,
++	    send_doc},
++	{"recv", (PyCFunction)link_recv, METH_VARARGS|METH_KEYWORDS,
++	    recv_doc},
++	{"disabmulti", (PyCFunction)link_disabmulti, METH_VARARGS|METH_KEYWORDS,
++	    disabmulti_doc},
++	{"enabmulti", (PyCFunction)link_enabmulti, METH_VARARGS|METH_KEYWORDS,
++	    enabmulti_doc},
++	{"enabnotify", (PyCFunction)link_enabnotify,
++	    METH_VARARGS|METH_KEYWORDS, enabnotify_doc},
++	{"disabnotify", (PyCFunction)link_disabnotify,
++	    METH_VARARGS|METH_KEYWORDS, disabnotify_doc},
++	{"get_fd", (PyCFunction)link_get_fd, METH_NOARGS, get_fd_doc},
++	{"get_sap", (PyCFunction)link_get_sap, METH_NOARGS, get_sap_doc},
++	{"get_mactype", (PyCFunction)link_get_mactype, METH_NOARGS,
++	    get_mactype_doc},
++	{"get_linkname", (PyCFunction)link_get_linkname, METH_NOARGS,
++	    get_linkname_doc},
++	{"get_bcastaddr", (PyCFunction)link_get_bcastaddr, METH_NOARGS,
++	    get_bcastaddr_doc},
++	{"get_physaddr", (PyCFunction)link_get_physaddr,
++	    METH_VARARGS|METH_KEYWORDS, get_physaddr_doc},
++	{"set_physaddr", (PyCFunction)link_set_physaddr,
++	    METH_VARARGS|METH_KEYWORDS, set_physaddr_doc},
++	{"promiscon", (PyCFunction)link_promiscon, METH_VARARGS|METH_KEYWORDS,
++	    promiscon_doc},
++	{"promiscoff", (PyCFunction)link_promiscoff, METH_VARARGS|METH_KEYWORDS,
++	    promiscoff_doc},
++	{"get_timeout", (PyCFunction)link_get_timeout, METH_NOARGS,
++	    get_timeout_doc},
++	{"set_timeout", (PyCFunction)link_set_timeout,
++	    METH_VARARGS|METH_KEYWORDS, set_timeout_doc},
++	{"get_sdu", (PyCFunction)link_get_sdu, METH_NOARGS, get_sdu_doc},
++	{"get_state", (PyCFunction)link_get_state, METH_NOARGS,
++	    get_state_doc},
++	{"get_qos_select", (PyCFunction)link_get_qos_select, METH_NOARGS,
++	    get_qos_select_doc},
++	{"get_qos_range", (PyCFunction)link_get_qos_range, METH_NOARGS,
++	    get_qos_range_doc},
++	{NULL, NULL}
++};
++
++static PyTypeObject pylink_type = {
++	PyVarObject_HEAD_INIT(NULL, 0)	/* Must fill in type value later */
++	"dlpi.link",				/* tp_name */
++	sizeof(pylink_t),			/* tp_basicsize */
++	0,					/* tp_itemsize */
++	(destructor)link_dealloc,		/* tp_dealloc */
++	0,					/* tp_print */
++	0,					/* tp_getattr */
++	0,					/* tp_setattr */
++	0,					/* tp_reserved */
++	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 */
++	link_doc,				/* tp_doc */
++	0,					/* tp_traverse */
++	0,					/* tp_clear */
++	0,					/* tp_richcompare */
++	0,					/* tp_weaklistoffset */
++	0,					/* tp_iter */
++	0,					/* tp_iternext */
++	pylink_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)link_init,			/* tp_init */
++	0,					/* tp_alloc */
++	PyType_GenericNew,			/* tp_new */
++	0,					/* tp_free */
++	0,					/* tp_is_gc */
++};
++
++PyDoc_STRVAR(arptype_doc,
++    "arptype(arptype) -> unsigned int\n"
++    "\n"
++    "Converts a DLPI MAC type to an ARP hardware type defined\n"
++    " in <netinet/arp.h>\n"
++    "See dlpi_arptype(3DLPI)\n"
++);
++static PyObject *
++arptype(PyObject *dlpi, PyObject *args, PyObject *kwds)
++{
++	static char *keywords[] = {"arptype", NULL};
++	uint_t dlpityp, arptyp;
++
++	if (!PyArg_ParseTupleAndKeywords(args, kwds, "I", keywords, &dlpityp))
++		return (NULL);
++
++	if ((arptyp = dlpi_arptype(dlpityp)) == 0) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	return (Py_BuildValue("I", arptyp));
++}
++
++PyDoc_STRVAR(iftype_doc,
++    "iftype(iftype) -> unsigned int\n"
++    "\n"
++    "Converts a DLPI MAC type to a BSD socket interface type\n"
++    "defined in <net/if_types.h>\n"
++    "See dlpi_iftype(3DLPI)\n"
++);
++static PyObject *
++iftype(PyObject *dlpi, PyObject *args, PyObject *kwds)
++{
++	static char *keywords[] = {"iftype", NULL};
++	uint_t dlpityp, iftyp;
++
++	if (!PyArg_ParseTupleAndKeywords(args, kwds, "I", keywords, &dlpityp))
++		return (NULL);
++
++	if ((iftyp = dlpi_iftype(dlpityp)) == 0) {
++		errno = EINVAL;
++		dlpi_raise_exception(DL_SYSERR);
++		return (NULL);
++	}
++
++	return (Py_BuildValue("I", iftyp));
++}
++
++PyDoc_STRVAR(mactype_doc,
++    "mactype(mactype) -> string\n"
++    "\n"
++    "Returns a string that describes the specified mactype.\n"
++    "Valid mac types are defined in <sys/dlpi.h>.\n"
++    "See dlpi_mactype(3DLPI)\n"
++);
++static PyObject *
++mactype(PyObject *dlpi, PyObject *args, PyObject *kwds)
++{
++	static char *keywords[] = {"mactype", NULL};
++	uint_t mactyp;
++
++	if (!PyArg_ParseTupleAndKeywords(args, kwds, "I", keywords, &mactyp))
++		return (NULL);
++
++	return (Py_BuildValue("s", dlpi_mactype(mactyp)));
++}
++
++static boolean_t
++link_walker(const char *name, void *arg)
++{
++	PyObject *linkname;
++	PyObject *list = (PyObject *)arg;
++
++	if ((list == NULL) || !PyList_Check(list))
++		return (B_FALSE);
++
++	linkname = Py_BuildValue("s", name);
++	if (PyList_Append(list, linkname) == -1)
++		return (B_TRUE);
++
++	Py_DECREF(linkname);
++	return (B_FALSE);
++}
++
++PyDoc_STRVAR(listlink_doc,
++    "listlink() -> list\n"
++    "\n"
++    "Returns a list containing link names of all links on the system.\n"
++);
++static PyObject *
++listlink(PyObject *dlpi)
++{
++	PyObject *list;
++
++	if ((list = PyList_New(0)) == NULL)
++		return (NULL);
++
++	dlpi_walk(link_walker, list, 0);
++	return (list);
++}
++
++static PyMethodDef dlpi_methods[] = {
++	{"arptype", (PyCFunction)arptype, METH_VARARGS|METH_KEYWORDS,
++	    arptype_doc},
++	{"iftype", (PyCFunction)iftype, METH_VARARGS|METH_KEYWORDS,
++	    iftype_doc},
++	{"mactype", (PyCFunction)mactype, METH_VARARGS|METH_KEYWORDS,
++	    mactype_doc},
++	{"listlink", (PyCFunction)listlink, METH_NOARGS, listlink_doc},
++	{NULL}
++};
++
++PyMODINIT_FUNC
++PyInit_dlpi (void)
++{
++	PyObject *mod;
++
++	if (PyType_Ready(&pylink_type) < 0)
++		return NULL;
++
++	static struct PyModuleDef moduledef = {
++	    PyModuleDef_HEAD_INIT,
++	    "dlpi",
++	    NULL,
++	    -1,
++	    dlpi_methods,
++	    NULL,
++	    NULL,
++	    NULL,
++	    NULL,
++	};
++
++	mod = PyModule_Create(&moduledef);
++	if (mod == NULL)
++		return NULL;
++
++	dlpi_err = PyErr_NewException("dlpi.error", NULL, NULL);
++	if (dlpi_err == NULL)
++		return NULL;
++	PyModule_AddObject(mod, "error", dlpi_err);
++
++	Py_INCREF(&pylink_type);
++	PyModule_AddObject(mod, "link", (PyObject *)&pylink_type);
++	PyModule_AddIntConstant(mod, "PASSIVE", DLPI_PASSIVE);
++	PyModule_AddIntConstant(mod, "RAW", DLPI_RAW);
++	PyModule_AddIntConstant(mod, "NATIVE", DLPI_NATIVE);
++	PyModule_AddIntConstant(mod, "ANY_SAP", DLPI_ANY_SAP);
++	PyModule_AddIntConstant(mod, "DEF_TIMEOUT", DLPI_DEF_TIMEOUT);
++	PyModule_AddIntConstant(mod, "NOTE_LINK_DOWN", DL_NOTE_LINK_DOWN);
++	PyModule_AddIntConstant(mod, "NOTE_LINK_UP", DL_NOTE_LINK_UP);
++	PyModule_AddIntConstant(mod, "NOTE_PHYS_ADDR", DL_NOTE_PHYS_ADDR);
++	PyModule_AddIntConstant(mod, "NOTE_SDU_SIZE", DL_NOTE_SDU_SIZE);
++	PyModule_AddIntConstant(mod, "NOTE_SPEED", DL_NOTE_SPEED);
++	PyModule_AddIntConstant(mod, "NOTE_PROMISC_ON_PHYS",
++	    DL_NOTE_PROMISC_ON_PHYS);
++	PyModule_AddIntConstant(mod, "NOTE_PROMISC_OFF_PHYS",
++	    DL_NOTE_PROMISC_OFF_PHYS);
++	PyModule_AddIntConstant(mod, "FACT_PHYS_ADDR", DL_FACT_PHYS_ADDR);
++	PyModule_AddIntConstant(mod, "CURR_PHYS_ADDR", DL_CURR_PHYS_ADDR);
++	PyModule_AddIntConstant(mod, "PROMISC_PHYS", DL_PROMISC_PHYS);
++	PyModule_AddIntConstant(mod, "PROMISC_SAP", DL_PROMISC_SAP);
++	PyModule_AddIntConstant(mod, "PROMISC_MULTI", DL_PROMISC_MULTI);
++	PyModule_AddIntConstant(mod, "UNKNOWN", DL_UNKNOWN);
++	PyModule_AddIntConstant(mod, "UNBOUND", DL_UNBOUND);
++	PyModule_AddIntConstant(mod, "IDLE", DL_IDLE);
++	PyModule_AddIntConstant(mod, "SYSERR", DL_SYSERR);
++
++	return mod;
++}
+--- Python-3.4.0/setup.py.~4~	2014-03-19 10:45:51.118227834 -0700
++++ Python-3.4.0/setup.py	2014-03-19 10:45:51.146201564 -0700
[email protected]@ -1474,6 +1474,12 @@
+             exts.append( Extension('ucred', ['ucred.c'],
+                                    libraries = ['tsol']) )
+ 
++        # dlpi module (Solaris)
++        dlpi_inc = find_file('libdlpi.h', [], inc_dirs)
++        if dlpi_inc is not None:
++            exts.append( Extension('dlpi', ['dlpimodule.c'],
++                                   libraries = ['dlpi']) )
++
+         # Thomas Heller's _ctypes module
+         self.detect_ctypes(inc_dirs, lib_dirs)
+ 
+diff --git Python-2.6.4/lib/test/dlpitest.py Python-2.6.4/Lib/test/dlpitest.py
+new file mode 100644
+--- /dev/null	2011-02-12 03:13:26.000000000 -0600
++++ Python-2.6.4/Lib/test/dlpitest.py	2011-01-20 13:52:42.895865414 -0600
[email protected]@ -0,0 +1,96 @@
++#!/usr/bin/python3.4
++
++import dlpi
++import sys
++import time
++import struct
++
++#test listlink
++linklist = dlpi.listlink()
++print("Found %d links:" % len(linklist))
++print(linklist)
++
++#pick up the first data link for below testing
++linkname = linklist[0]
++
++#open link
++print("opening link: " + linkname + "...")
++testlink = dlpi.link(linkname)
++
++#read some info of testlink
++print("linkname is %s" % testlink.get_linkname())
++print("link fd is %d" % testlink.get_fd())
++mactype = testlink.get_mactype()
++print("dlpi mactype is %d" % mactype)
++print("after convert:")
++print("\tmactype is %s" % dlpi.mactype(mactype))
++print("\tiftype is %d" % dlpi.iftype(mactype))
++print("\tarptype is %d" % dlpi.arptype(mactype))
++bcastaddr = testlink.get_bcastaddr()
++print("broadcast addr is: ", end=' ')
++print(struct.unpack("BBBBBB",bcastaddr))
++physaddr = testlink.get_physaddr(dlpi.FACT_PHYS_ADDR)
++print("factory physical address is: ", end=' ')
++print(struct.unpack("BBBBBB",physaddr))
++print("current timeout value is %d" % testlink.get_timeout())
++print("sdu is:", end=' ')
++print(testlink.get_sdu())
++print("qos select is:", end=' ')
++print(testlink.get_qos_select())
++print("qos range is:", end=' ')
++print(testlink.get_qos_range())
++
++#set some config value of testlink and read them again
++print("setting current physiacal addr to aa:0:10:13:27:5")
++testlink.set_physaddr('\xaa\0\x10\x13\x27\5')
++physaddr = testlink.get_physaddr(dlpi.CURR_PHYS_ADDR)
++print("current physical addr is: ", end=' ')
++print(struct.unpack("BBBBBB",physaddr))
++print("set timeout value to 6...")
++testlink.set_timeout(6)
++print("timeout value is %d" % testlink.get_timeout())
++
++#test enable/disable multicast
++print("enable/disable multicast address 1:0:5e:0:0:5")
++testlink.enabmulti('\1\0\x5e\0\0\5')
++testlink.disabmulti('\1\0\x5e\0\0\5')
++
++#test bind
++print("binding to SAP 0x9000...")
++testlink.bind(0x9000)
++print("sap is %x" % testlink.get_sap())
++print("state is: %d"  % testlink.get_state())
++
++#test send
++print("sending broadcast loopback packet...")
++testlink.send(bcastaddr, '\0\1\2\3\4\5')
++
++#test notify functionality
++arg = "notification callback arg"
++def notify(arg, notes, value):
++	print("NOTE_PROMISC_ON_PHYS notification received with arg: '%s'" % arg)
++print("enabled notification on NOTE_PROMISC_ON_PHYS")
++id = testlink.enabnotify(dlpi.NOTE_PROMISC_ON_PHYS, notify, arg) #enable notification
++testlink.promiscon() #trigger the event (will be seen while receiving pkt below)
++
++#test receive
++print("testing receiving...")
++try:
++	testlink.recv(0, 0) #should see NOTE_PROMISC_ON_PHYS event here
++except dlpi.error as err:
++	errnum, errinfo = err
++	if errnum == 10006:
++		pass #timeout error is expected here
++	else: #test fails if reach here
++		print("test failed", end=' ')
++		print(errnum, end=' ')
++		print(err)
++
++testlink.promiscoff()
++testlink.disabnotify(id) #disable notification
++
++#test unbind
++print("unbinding...")
++testlink.unbind()
++print("sap is %x" % testlink.get_sap())
++print("state is: %d"  % testlink.get_state())
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/components/python/python34/patches/09-encoding-alias.patch	Mon May 19 07:37:20 2014 -0700
@@ -0,0 +1,37 @@
+Add missing encoding aliases.  It may be contributed upstream at some point,
+but the suitability (or lack thereof) has not yet been determined.
+
+--- Python-3.4.0/Lib/encodings/aliases.py.~1~	2014-03-16 19:31:29.000000000 -0700
++++ Python-3.4.0/Lib/encodings/aliases.py	2014-03-17 13:26:52.837734374 -0700
[email protected]@ -79,6 +79,7 @@
+ 
+     # cp1251 codec
+     '1251'               : 'cp1251',
++    'ansi_1251'          : 'cp1251',
+     'windows_1251'       : 'cp1251',
+ 
+     # cp1252 codec
[email protected]@ -233,6 +234,7 @@
+     'u_jis'              : 'euc_jp',
+ 
+     # euc_kr codec
++    '5601'               : 'euc_kr',
+     'euckr'              : 'euc_kr',
+     'korean'             : 'euc_kr',
+     'ksc5601'            : 'euc_kr',
[email protected]@ -474,6 +476,7 @@
+     'shiftjis'           : 'shift_jis',
+     'sjis'               : 'shift_jis',
+     's_jis'              : 'shift_jis',
++    'pck'                : 'shift_jis',
+ 
+     # shift_jis_2004 codec
+     'shiftjis2004'       : 'shift_jis_2004',
[email protected]@ -493,6 +496,7 @@
+     'tis_620_0'          : 'tis_620',
+     'tis_620_2529_0'     : 'tis_620',
+     'tis_620_2529_1'     : 'tis_620',
++    'tis620.2533'        : 'tis_620',
+     'iso_ir_166'         : 'tis_620',
+ 
+     # utf_16 codec
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/components/python/python34/patches/10-rbac.patch	Mon May 19 07:37:20 2014 -0700
@@ -0,0 +1,1602 @@
+This patch provides Python RBAC support.  It may be contributed upstream at
+some point, but the suitability (or lack thereof) has not yet been determined.
+
+diff --git Python-2.6.4/Modules/authattr.c Python-2.6.4/Modules/authattr.c
+new file mode 100644
+--- /dev/null
++++ Python-2.6.4/Modules/authattr.c
[email protected]@ -0,0 +1,261 @@
++/*
++ * CDDL HEADER START
++ *
++ * The contents of this file are subject to the terms of the
++ * Common Development and Distribution License (the "License").
++ * You may not use this file except in compliance with the License.
++ *
++ * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
++ * or http://www.opensolaris.org/os/licensing.
++ * See the License for the specific language governing permissions
++ * and limitations under the License.
++ *
++ * When distributing Covered Code, include this CDDL HEADER in each
++ * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
++ * If applicable, add the following below this CDDL HEADER, with the
++ * fields enclosed by brackets "[]" replaced with your own identifying
++ * information: Portions Copyright [yyyy] [name of copyright owner]
++ *
++ * CDDL HEADER END
++ */
++
++/*
++ * Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved.
++ */
++
++/*
++ * RBAC Bindings for Python - auth_attr functions
++ */
++
++#include <auth_attr.h>
++#include "Python.h"
++#include "pyrbac.h"
++
++static PyObject*
++pyrbac_setauthattr(PyObject* self, PyObject* args) {
++	setauthattr();
++	return Py_None;
++}
++
++static PyObject*
++pyrbac_endauthattr(PyObject* self, PyObject* args) {
++	endauthattr();
++	return Py_None;
++}
++
++PyObject*
++pyrbac_getauthnamattr(PyObject* self, char* authname, int mode) {
++	
++
++	
++	authattr_t * ret_authattr = (mode == PYRBAC_NAM_MODE) ? getauthnam(authname) : getauthattr();
++	if (ret_authattr == NULL)
++		return Py_None;
++		
++	PyObject* kv_data = PyDict_New();
++	if (kv_data == NULL) {
++		free_authattr(ret_authattr);
++		return NULL;
++	}
++
++	if(ret_authattr->attr != NULL) {
++		int len;
++		for(len = 0; len < ret_authattr->attr->length; len++) {
++			kv_t current = ret_authattr->attr->data[len];
++
++			PyObject* set = PyList_New(NULL);
++			char* saveptr;
++			char* item = strtok_r(current.value, ",", &saveptr);
++			PyList_Append(set, PyBytes_FromString(item));
++
++			while((item = strtok_r(NULL, ",", &saveptr)) != NULL) {
++				if(PyList_Append(set, PyBytes_FromString(item)) != 0) {
++					Py_XDECREF(set);
++					Py_XDECREF(kv_data);
++					free_authattr(ret_authattr);
++					return NULL;
++				}
++			}
++			if(PyDict_SetItemString(kv_data, current.key, set)) {
++					free_authattr(ret_authattr);
++					return NULL;
++			}
++		}
++	}
++	PyObject * retval = Py_BuildValue("{s:s,s:s,s:s,s:s,s:s,s:O}",
++		"name",ret_authattr->name,
++		"res1",ret_authattr->res1,
++		"res2",ret_authattr->res2,
++		"short",ret_authattr->short_desc,
++		"long",ret_authattr->long_desc,
++		"attributes",kv_data);
++
++	free_authattr(ret_authattr);
++	return retval;
++
++}
++
++static PyObject*
++pyrbac_getauthattr(PyObject* self, PyObject* args) {
++	return(pyrbac_getauthnamattr(self, NULL, PYRBAC_ATTR_MODE));
++}
++
++static PyObject*
++pyrbac_getauthnam(PyObject* self, PyObject* args) {
++	char* name = NULL;
++	if(!PyArg_ParseTuple(args, "s:getauthnam", &name))
++		return NULL;
++	return(pyrbac_getauthnamattr(self, name, PYRBAC_NAM_MODE));
++}
++
++static PyObject *
++pyrbac_chkauthattr(PyObject* self, PyObject* args) {
++	char* authstring = NULL;
++	char* username = NULL;
++	if(!PyArg_ParseTuple(args, "ss:chkauthattr", &authstring, &username))
++		return NULL;
++	return PyBool_FromLong((long)chkauthattr(authstring, username));
++}
++
++static PyObject*
++pyrbac_authattr_next(PyObject* self, PyObject* args) {
++	PyObject* retval = pyrbac_getauthattr(self, args);
++	if( retval == Py_None ) {
++		setauthattr();
++		return NULL;
++	}
++	return retval;
++}
++static PyObject*
++pyrbac_authattr__iter__(PyObject* self, PyObject* args) {
++	return self;
++}
++
++typedef struct {
++	PyObject_HEAD
++} Authattr;
++
++static void
++Authattr_dealloc(Authattr* self) {
++	endauthattr();
++	Py_TYPE(self)->tp_free((PyObject*) self);
++}
++
++static PyObject*
++Authattr_new(PyTypeObject *type, PyObject *args, PyObject *kwds) {
++	Authattr *self;
++	self = (Authattr*)type->tp_alloc(type, 0);
++
++	return ((PyObject *) self);
++}
++
++static int
++Authattr_init(Authattr* self, PyObject *args, PyObject *kwargs) {
++	setauthattr();
++	return 0;
++}
++
++static char pyrbac_authattr__doc__[];
++
++PyDoc_STRVAR(pyrbac_authattr__doc__, """provides interfaces to the auth_attr \
++database. may be iterated over to return all auth_attr entries\n\n\
++Methods provided:\n\
++setauthattr\n\
++endauthattr\n\
++getauthattr\n\
++chkauthattr\n\
++getauthnam""");
++
++static char pyrbac_setauthattr__doc__[];
++static char pyrbac_endauthattr__doc__[];
++static char pyrbac_getauthattr__doc__[];
++static char pyrbac_chkauthattr__doc__[];
++
++PyDoc_STRVAR(pyrbac_setauthattr__doc__, 
++"\"rewinds\" the auth_attr functions to the first entry in the db. Called \
++automatically by the constructor\n\tArguments: None\n\tReturns: None");
++
++PyDoc_STRVAR(pyrbac_endauthattr__doc__, 
++"closes the auth_attr database, cleans up storage. called automatically by \
++the destructor\n\tArguments: None\n\tReturns: None");
++
++PyDoc_STRVAR(pyrbac_chkauthattr__doc__, "verifies if a user has a given \
++authorization.\n\tArguments: 2 Python strings, 'authname' and 'username'\n\
++\tReturns: True if the user is authorized, False otherwise");
++
++PyDoc_STRVAR(pyrbac_getauthattr__doc__, 
++"return one entry from the auth_attr database\n\
++\tArguments: None\n\
++\tReturns: a dict representing the authattr_t struct:\n\
++\t\t\"name\": Authorization Name\n\
++\t\t\"res1\": reserved\n\
++\t\t\"res2\": reserved\n\
++\t\t\"short\": Short Description\n\
++\t\t\"long\": Long Description\n\
++\t\t\"attributes\": A Python dict keyed by attribute & valued as either a list \
++or a string depending on value");
++
++PyDoc_STRVAR(pyrbac_getauthnam__doc__, 
++"searches the auth_attr database for a given authorization name\n\
++\tArguments: a Python string containing the auth name\n\
++\tReturns: a dict representing the authattr_t struct:\n\
++\t\t\"name\": Authorization Name\n\
++\t\t\"res1\": reserved\n\
++\t\t\"res2\": reserved\n\
++\t\t\"short\": Short Description\n\
++\t\t\"long\": Long Description\n\
++\t\t\"attributes\": A Python dict keyed by attribute & valued as either a list \
++or a string depending on value");
++
++static PyMethodDef Authattr_methods[] = {
++	{"setauthattr", pyrbac_setauthattr, METH_NOARGS, pyrbac_setauthattr__doc__},
++	{"endauthattr", pyrbac_endauthattr, METH_NOARGS, pyrbac_endauthattr__doc__},
++	{"chkauthattr", pyrbac_chkauthattr, METH_VARARGS, pyrbac_chkauthattr__doc__},
++	{"getauthattr", pyrbac_getauthattr, METH_NOARGS, pyrbac_getauthattr__doc__},
++	{"getauthnam", pyrbac_getauthnam, METH_VARARGS, pyrbac_getauthnam__doc__},
++	{NULL, NULL}
++};
++
++PyTypeObject AuthattrType = {
++	PyVarObject_HEAD_INIT(NULL, 0)
++	"rbac.authattr",              /*tp_name*/
++	sizeof(Authattr),             /*tp_basicsize*/
++	0,                            /*tp_itemsize*/
++	(destructor)Authattr_dealloc, /*tp_dealloc*/
++	0,                            /*tp_print*/
++	0,                            /*tp_getattr*/
++	0,                            /*tp_setattr*/
++	0,                            /*tp_reserved*/
++	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_BASETYPE,          /*tp_flags*/
++	pyrbac_authattr__doc__,       /* tp_doc */
++	0,		              /* tp_traverse */
++	0,		              /* tp_clear */
++	0,		              /* tp_richcompare */
++	0,		              /* tp_weaklistoffset */
++	pyrbac_authattr__iter__,      /* tp_iter */
++	pyrbac_authattr_next,         /* tp_iternext */
++	Authattr_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)Authattr_init,      /* tp_init */
++	0,                            /* tp_alloc */
++	Authattr_new,                 /* tp_new */
++	0,                            /* tp_free */
++	0,                            /* tp_is_gc */
++};
+diff --git Python-2.6.4/Modules/execattr.c Python-2.6.4/Modules/execattr.c
+new file mode 100644
+--- /dev/null
++++ Python-2.6.4/Modules/execattr.c
[email protected]@ -0,0 +1,313 @@
++/*
++ * CDDL HEADER START
++ *
++ * The contents of this file are subject to the terms of the
++ * Common Development and Distribution License (the "License").
++ * You may not use this file except in compliance with the License.
++ *
++ * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
++ * or http://www.opensolaris.org/os/licensing.
++ * See the License for the specific language governing permissions
++ * and limitations under the License.
++ *
++ * When distributing Covered Code, include this CDDL HEADER in each
++ * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
++ * If applicable, add the following below this CDDL HEADER, with the
++ * fields enclosed by brackets "[]" replaced with your own identifying
++ * information: Portions Copyright [yyyy] [name of copyright owner]
++ *
++ * CDDL HEADER END
++ */
++
++/*
++ * Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved.
++ */
++
++/*
++ * RBAC Bindings for Python - exec_attr functions
++ */
++
++#include <exec_attr.h>
++#include "Python.h"
++#include "pyrbac.h"
++
++static PyObject *
++pyrbac_setexecattr(PyObject* self, PyObject* args) {
++	setexecattr();
++	return Py_None;
++}
++
++static PyObject *
++pyrbac_endexecattr(PyObject* self, PyObject* args) {
++	endexecattr();
++	return Py_None;
++}
++
++PyObject *
++pyrbac_getexecuserprofattr(PyObject* self, char* userprofname, char* type, char* id, int mode) {
++
++	PyObject* ep_data = (mode == PYRBAC_ATTR_MODE) ? NULL : PyList_New(0);
++	
++	if (ep_data == NULL && mode != PYRBAC_ATTR_MODE )
++		return NULL;
++	
++	execattr_t *execprof;
++	if (mode == PYRBAC_USER_MODE)
++		execprof = getexecuser(userprofname, type, id, GET_ALL);
++	else if (mode == PYRBAC_PROF_MODE)
++		execprof = getexecprof(userprofname, type, id, GET_ALL);
++	else if (mode == PYRBAC_ATTR_MODE)
++		execprof = getexecattr();
++	else
++		return NULL;
++
++	if (execprof == NULL)
++		return Py_None;
++	
++	execattr_t *execprof_head = execprof;
++
++	while(execprof != NULL) {
++		
++		PyObject* kv_data = PyDict_New();
++
++		if(execprof->attr != NULL) {
++			int len;
++			for(len = 0; len < execprof->attr->length; len++) {
++				kv_t current = execprof->attr->data[len];
++
++				PyObject* set = PyList_New(NULL);
++				char* saveptr;
++				char* item = strtok_r(current.value, ",", &saveptr);
++				PyList_Append(set, PyBytes_FromString(item));
++
++				while((item = strtok_r(NULL, ",", &saveptr)) != NULL) {
++					if(PyList_Append(set, PyBytes_FromString(item)) != 0) {
++						Py_XDECREF(set);
++						Py_XDECREF(kv_data);
++						free_execattr(execprof_head);
++						return NULL;
++					}
++				}
++				if(PyDict_SetItemString(kv_data, current.key, set)) {
++						free_execattr(execprof_head);
++						return NULL;
++				}
++			}
++		}
++		PyObject* entry = Py_BuildValue("{s:s,s:s,s:s,s:s,s:s,s:s,s:O}",
++			"name", execprof->name,
++			"type", execprof->type,
++			"policy", execprof->policy,
++			"res1", execprof->res1,
++			"res2", execprof->res2,
++			"id", execprof->id,
++			"attributes", kv_data);
++		
++		if (entry == NULL) {
++			Py_XDECREF(kv_data);
++			free_execattr(execprof_head);
++			return NULL;
++		}
++		
++		if (mode == PYRBAC_ATTR_MODE) {
++			free_execattr(execprof_head);
++			return(entry);
++		}
++		PyList_Append(ep_data, entry);
++		execprof = execprof->next;
++	}
++
++	free_execattr(execprof_head);
++	return(ep_data);
++ 
++}
++
++static PyObject *
++pyrbac_getexecuser(PyObject* self, PyObject* args) {
++	char* username = NULL;
++	char* type = NULL;
++	char* id = NULL;
++	
++	if(!PyArg_ParseTuple(args, "sss:getexecuser", &username, &type, &id))
++		return NULL;
++
++	return (pyrbac_getexecuserprofattr(self, username, type, id, PYRBAC_USER_MODE));
++}
++
++static PyObject *
++pyrbac_getexecprof(PyObject* self, PyObject* args) {
++
++	char* profname = NULL;
++	char* type = NULL;
++	char* id = NULL;
++	
++	if(!PyArg_ParseTuple(args, "sss:getexecprof", &profname, &type, &id))
++		return NULL;
++
++	return (pyrbac_getexecuserprofattr(self, profname, type, id, PYRBAC_PROF_MODE));
++}
++
++static PyObject*
++pyrbac_getexecattr(PyObject* self, PyObject* args) {
++	return pyrbac_getexecuserprofattr(self, NULL, NULL, NULL, PYRBAC_ATTR_MODE);
++}
++
++static PyObject*
++pyrbac_execattr_next(PyObject* self, PyObject* args) {
++	PyObject* retval = pyrbac_getexecattr(self, args);
++	if( retval == Py_None ) {
++		setexecattr();
++		return NULL;
++	}
++	return retval;
++}
++static PyObject*
++pyrbac_execattr__iter__(PyObject* self, PyObject* args) {
++	return self;
++}
++
++typedef struct {
++	PyObject_HEAD
++} Execattr;
++
++static void
++Execattr_dealloc(Execattr* self) {
++	endexecattr();
++	Py_TYPE(self)->tp_free((PyObject*) self);
++}
++
++static PyObject*
++Execattr_new(PyTypeObject *type, PyObject *args, PyObject *kwds) {
++	Execattr *self;
++	self = (Execattr*)type->tp_alloc(type, 0);
++
++	return ((PyObject *) self);
++}
++
++static int
++Execattr_init(Execattr* self, PyObject *args, PyObject *kwargs) {
++	setexecattr();
++	return 0;
++}
++
++static char pyrbac_execattr__doc__[];
++
++PyDoc_STRVAR(pyrbac_execattr__doc__, "provides functions for \
++interacting with the execution profiles database. May be iterated over to \
++enumerate exec_attr(4) entries\n\n\
++Methods provided:\n\
++setexecattr\n\
++endexecattr\n\
++getexecattr\n\
++getexecprof\n\
++getexecuser");
++
++
++static char pyrbac_getexecuser__doc__[];
++static char pyrbac_getexecprof__doc__[];
++static char pyrbac_getexecattr__doc__[];
++static char pyrbac_setexecattr__doc__[];
++static char pyrbac_endexecattr__doc__[];
++
++PyDoc_STRVAR(pyrbac_setexecattr__doc__,
++"\"rewinds\" the exec_attr functions to the first entry in the db. Called \
++automatically by the constructor.\n\
++\tArguments: None\
++\tReturns: None");
++
++PyDoc_STRVAR(pyrbac_endexecattr__doc__, 
++"closes the exec_attr database, cleans up storage. called automatically by \
++the destructor.\n\
++\tArguments: None\
++\tReturns: None");
++
++PyDoc_STRVAR(pyrbac_getexecuser__doc__, "corresponds with getexecuser(3SECDB)\
++\nTakes: \'username\', \'type\', \'id\'\n\
++Return: a single exec_attr entry\n\
++\tArguments: None\n\
++\tReturns: a dict representation of an execattr_t struct:\n\
++\t\t\"name\": Authorization Name\n\
++\t\t\"type\": Profile Type\n\
++\t\t\"policy\": Policy attributes are relevant in\n\
++\t\t\"res1\": reserved\n\
++\t\t\"res2\": reserved\n\
++\t\t\"id\": unique identifier\n\
++\t\t\"attributes\": A Python dict keyed by attribute & valued as\
++either a list or a string depending on value");
++
++PyDoc_STRVAR(pyrbac_getexecprof__doc__, "corresponds with getexecprof(3SECDB)\
++\nTakes: \'profile name\', \'type\', \'id\'\n\
++\tReturns: a dict representation of an execattr_t struct:\n\
++\t\t\"name\": Authorization Name\n\
++\t\t\"type\": Profile Type\n\
++\t\t\"policy\": Policy attributes are relevant in\n\
++\t\t\"res1\": reserved\n\
++\t\t\"res2\": reserved\n\
++\t\t\"id\": unique identifier\n\
++\t\t\"attributes\": A Python dict keyed by attribute & valued as\
++either a list or a string depending on value");
++
++PyDoc_STRVAR(pyrbac_getexecattr__doc__, "corresponds with getexecattr(3SECDB)\
++\nTakes 0 arguments\n\
++\tReturns: a dict representation of an execattr_t struct:\n\
++\t\t\"name\": Authorization Name\n\
++\t\t\"type\": Profile Type\n\
++\t\t\"policy\": Policy attributes are relevant in\n\
++\t\t\"res1\": reserved\n\
++\t\t\"res2\": reserved\n\
++\t\t\"id\": unique identifier\n\
++\t\t\"attributes\": A Python dict keyed by attribute & valued as\
++either a list or a string depending on value");
++
++static PyMethodDef Execattr_methods[] = {
++	{"setexecattr", pyrbac_setexecattr, METH_NOARGS, pyrbac_setexecattr__doc__},
++	{"endexecattr", pyrbac_endexecattr, METH_NOARGS, pyrbac_endexecattr__doc__},
++	{"getexecprof", pyrbac_getexecprof, METH_VARARGS, pyrbac_getexecprof__doc__},	
++	{"getexecuser", pyrbac_getexecuser, METH_VARARGS, pyrbac_getexecuser__doc__},
++	{"getexecattr", pyrbac_getexecattr, METH_NOARGS, pyrbac_getexecattr__doc__},
++	{NULL, NULL}
++};
++
++PyTypeObject ExecattrType = {
++	PyVarObject_HEAD_INIT(NULL, 0)
++	"rbac.execattr",              /*tp_name*/
++	sizeof(Execattr),             /*tp_basicsize*/
++	0,                            /*tp_itemsize*/
++	(destructor)Execattr_dealloc, /*tp_dealloc*/
++	0,                            /*tp_print*/
++	0,                            /*tp_getattr*/
++	0,                            /*tp_setattr*/
++	0,                            /*tp_reserved*/
++	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_BASETYPE,          /*tp_flags*/
++	pyrbac_execattr__doc__,       /* tp_doc */
++	0,		              /* tp_traverse */
++	0,		              /* tp_clear */
++	0,		              /* tp_richcompare */
++	0,		              /* tp_weaklistoffset */
++	pyrbac_execattr__iter__,      /* tp_iter */
++	pyrbac_execattr_next,         /* tp_iternext */
++	Execattr_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)Execattr_init,      /* tp_init */
++	0,                            /* tp_alloc */
++	Execattr_new,                 /* tp_new */
++	0,                            /* tp_free */
++	0,                            /* tp_is_gc */
++};
+diff --git Python-2.6.4/Modules/privileges.c Python-2.6.4/Modules/privileges.c
+new file mode 100644
+--- /dev/null
++++ Python-2.6.4/Modules/privileges.c
[email protected]@ -0,0 +1,243 @@
++/*
++ * CDDL HEADER START
++ *
++ * The contents of this file are subject to the terms of the
++ * Common Development and Distribution License (the "License").
++ * You may not use this file except in compliance with the License.
++ *
++ * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
++ * or http://www.opensolaris.org/os/licensing.
++ * See the License for the specific language governing permissions
++ * and limitations under the License.
++ *
++ * When distributing Covered Code, include this CDDL HEADER in each
++ * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
++ * If applicable, add the following below this CDDL HEADER, with the
++ * fields enclosed by brackets "[]" replaced with your own identifying
++ * information: Portions Copyright [yyyy] [name of copyright owner]
++ *
++ * CDDL HEADER END
++ */
++
++/*
++ * Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved.
++ */
++
++/*
++ * privileges(5) bindings for Python
++ */
++
++#include <priv.h>
++#include "Python.h"
++
++static PyObject *
++pyprivileges_setppriv( PyObject *self, PyObject *args) {
++	priv_op_t op = -1 ; 
++	priv_ptype_t which = NULL;
++
++	PyObject* set_list = NULL;
++
++	priv_set_t * set = NULL;
++
++	if(!PyArg_ParseTuple(args, "iiO:setppriv", &op, &which, &set_list))
++		return NULL;
++	
++	if((op != PRIV_ON && op != PRIV_OFF && op != PRIV_SET) ||
++		(which != PRIV_PERMITTED && which != PRIV_EFFECTIVE &&
++		which != PRIV_INHERITABLE && which != PRIV_LIMIT))
++		return NULL;
++	
++	PyObject* set_string = PyList_GetItem(set_list, 0);
++	int i;
++	for (i = 1; i < PyList_Size(set_list); ++i) {
++		PyBytes_Concat(&set_string, PyBytes_FromString(","));
++		PyBytes_Concat(&set_string, PyList_GetItem(set_list, i));
++	}
++
++	set = priv_str_to_set(PyBytes_AsString(set_string), ",", NULL );
++
++	if ( set == NULL )
++		return NULL;
++
++	long ret = (long) setppriv(op, which, set);
++	priv_freeset(set);	
++	// Python inverts true & false
++	if(ret)
++		Py_RETURN_FALSE;
++	
++	Py_RETURN_TRUE;
++}
++
++static PyObject *
++pyprivileges_getppriv( PyObject *self, PyObject *args) {
++
++	char* set_str = NULL;
++	priv_ptype_t which = NULL;
++	priv_set_t * set = priv_allocset();
++	if (set == NULL)
++		return NULL;
++
++	if(!PyArg_ParseTuple(args, "i:getppriv", &which))
++		return NULL;
++
++	if (which != PRIV_PERMITTED && which != PRIV_EFFECTIVE &&
++	which != PRIV_INHERITABLE && which != PRIV_LIMIT)
++		return NULL;
++
++	if (getppriv(which, set) != 0)
++		return NULL;
++	
++	set_str = priv_set_to_str(set, ',', PRIV_STR_LIT);
++	priv_freeset(set);
++	
++	PyObject* set_list = PyList_New(NULL);
++	char* saveptr;
++	char* item = strtok_r(set_str, ",", &saveptr);
++	PyList_Append(set_list, PyBytes_FromString(item));
++
++	while((item = strtok_r(NULL, ",", &saveptr)) != NULL) {
++		if(PyList_Append(set_list, PyBytes_FromString(item)) != 0) {
++			Py_XDECREF(set_list);
++			return NULL;
++		}
++	}
++
++	return(set_list);
++}
++
++static PyObject *
++pyprivileges_priv_inverse( PyObject *self, PyObject *args ) {
++
++	PyObject* set_list_in = NULL;
++	if(!PyArg_ParseTuple(args, "O:priv_inverse", &set_list_in))
++		return NULL;
++
++	PyObject* set_string = PyList_GetItem(set_list_in, 0);
++	int i;
++	for (i = 1; i < PyList_Size(set_list_in); ++i) {
++		PyBytes_Concat(set_string, PyBytes_FromString(","));
++		PyBytes_Concat(set_string, PyList_GetItem(set_list_in, i));
++	}
++
++	priv_set_t * set = priv_str_to_set(PyBytes_AsString(set_string), ",", NULL);
++	if (set == NULL)
++		return NULL;
++	priv_inverse(set);
++	char * ret_str = priv_set_to_str(set, ',', PRIV_STR_LIT);
++	priv_freeset(set);
++	
++	PyObject* set_list_out = PyList_New(NULL);
++	char* saveptr;
++	char* item = strtok_r(ret_str, ",", &saveptr);
++	PyList_Append(set_list_out, PyBytes_FromString(item));
++
++	while((item = strtok_r(NULL, ",", &saveptr)) != NULL) {
++		if(PyList_Append(set_list_out, PyBytes_FromString(item)) != 0) {
++			Py_XDECREF(set_list_out);
++			return NULL;
++		}
++	}
++	
++	Py_XDECREF(set_list_in);
++	
++	return(set_list_out);
++}
++
++/* priv_ineffect is a convienient wrapper to priv_get
++ * however priv_set is, in the context of python, not
++ * much of a convienience, so it's omitted
++ */
++static PyObject * 
++pyprivileges_priv_ineffect(PyObject* self, PyObject* args) {
++	char* privstring=NULL;
++	if (!PyArg_ParseTuple(args, "s:priv_ineffect", &privstring))
++		return NULL;
++	return PyBool_FromLong(priv_ineffect(privstring));
++}
++
++
++static char pyprivileges__doc__[];
++PyDoc_STRVAR(pyprivileges__doc__, 
++"Provides functions for interacting with the Solaris privileges(5) framework\n\
++Functions provided:\n\
++setppriv\n\
++getppriv\n\
++priv_ineffect\n\
++priv_inverse");
++
++static char pyprivileges_setppriv__doc__[];
++static char pyprivileges_getppriv__doc__[];
++static char pyprivileges_priv_ineffect__doc__[];
++static char pyprivileges_priv_inverse__doc__[];
++
++PyDoc_STRVAR(pyprivileges_setppriv__doc__, 
++"Facilitates setting the permitted/inheritable/limit/effective privileges set\n\
++\tArguments:\n\
++\t\tone of (PRIV_ON|PRIV_OFF|PRIV_SET)\n\
++\t\tone of (PRIV_PERMITTED|PRIV_INHERITABLE|PRIV_LIMIT|PRIV_EFFECTIVE)\n\
++\t\tset of privileges: a list of strings\n\
++\tReturns: True on success, False on failure\
++");
++
++PyDoc_STRVAR(pyprivileges_getppriv__doc__, 
++"Return the process privilege set\n\
++\tArguments:\n\
++\t\tone of (PRIV_PERMITTED|PRIV_INHERITABLE|PRIV_LIMIT|PRIV_EFFECTIVE)\n\
++\tReturns: a Python list of strings");
++	
++PyDoc_STRVAR(pyprivileges_priv_ineffect__doc__, 
++"Checks for a privileges presence in the effective set\n\
++\tArguments: a String\n\
++\tReturns: True if the privilege is in effect, False otherwise");
++
++PyDoc_STRVAR(pyprivileges_priv_inverse__doc__, 
++"The complement of the set of privileges\n\
++\tArguments: a list of strings\n\tReturns: a list of strings");
++
++static PyMethodDef module_methods[] = {
++	{"setppriv", pyprivileges_setppriv, METH_VARARGS, pyprivileges_setppriv__doc__}, 
++	{"getppriv", pyprivileges_getppriv, METH_VARARGS, pyprivileges_getppriv__doc__}, 
++	{"priv_ineffect", pyprivileges_priv_ineffect, METH_VARARGS, pyprivileges_priv_ineffect__doc__},
++	{"priv_inverse", pyprivileges_priv_inverse, METH_VARARGS, pyprivileges_priv_inverse__doc__},
++	{NULL, NULL}
++};
++
++
++#ifndef PyMODINIT_FUNC	/* declarations for DLL import/export */
++#define PyMODINIT_FUNC void
++#endif
++PyMODINIT_FUNC
++PyInit_privileges (void) {
++	PyObject* m;
++
++	static struct PyModuleDef moduledef = {
++	    PyModuleDef_HEAD_INIT,
++	    "privileges",
++	    pyprivileges__doc__,
++	    -1,
++	    module_methods,
++	    NULL,
++	    NULL,
++	    NULL,
++	    NULL,
++	};
++
++	m = PyModule_Create(&moduledef);
++	if ( m == NULL )
++		return m;
++		
++	PyObject* d = PyModule_GetDict(m);
++	if (d == NULL)
++		return m;
++
++	PyDict_SetItemString(d, "PRIV_ON", PyLong_FromLong((long)PRIV_ON));
++	PyDict_SetItemString(d, "PRIV_OFF", PyLong_FromLong((long)PRIV_OFF));
++	PyDict_SetItemString(d, "PRIV_SET", PyLong_FromLong((long)PRIV_SET));
++
++	PyDict_SetItemString(d, "PRIV_PERMITTED", PyLong_FromLong((long)PRIV_PERMITTED));
++	PyDict_SetItemString(d, "PRIV_INHERITABLE", PyLong_FromLong((long)PRIV_INHERITABLE));
++	PyDict_SetItemString(d, "PRIV_LIMIT", PyLong_FromLong((long)PRIV_LIMIT));
++	PyDict_SetItemString(d, "PRIV_EFFECTIVE", PyLong_FromLong((long)PRIV_EFFECTIVE));
++
++       return m;
++}
+diff --git Python-2.6.4/Modules/pyrbac.c Python-2.6.4/Modules/pyrbac.c
+new file mode 100644
+--- /dev/null
++++ Python-2.6.4/Modules/pyrbac.c
[email protected]@ -0,0 +1,82 @@
++/*
++ * CDDL HEADER START
++ *
++ * The contents of this file are subject to the terms of the
++ * Common Development and Distribution License (the "License").
++ * You may not use this file except in compliance with the License.
++ *
++ * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
++ * or http://www.opensolaris.org/os/licensing.
++ * See the License for the specific language governing permissions
++ * and limitations under the License.
++ *
++ * When distributing Covered Code, include this CDDL HEADER in each
++ * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
++ * If applicable, add the following below this CDDL HEADER, with the
++ * fields enclosed by brackets "[]" replaced with your own identifying
++ * information: Portions Copyright [yyyy] [name of copyright owner]
++ *
++ * CDDL HEADER END
++ */
++
++/*
++ * Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved.
++ */
++
++/*
++ * RBAC Bindings for Python
++ */
++
++#include <Python.h>
++#include "pyrbac.h"
++
++static PyMethodDef module_methods[] = {NULL};
++static char pyrbac__doc__[];
++
++PyDoc_STRVAR(pyrbac__doc__, "provides access to some objects \
++for interaction with the Solaris Role-Based Access Control \
++framework.\n\nDynamic objects:\n\
++userattr -- for interacting with user_attr(4)\n\
++authattr -- for interacting with auth_attr(4)\n\
++execattr -- for interacting with exec_attr(4)\n");
++
++#ifndef PyMODINIT_FUNC	/* declarations for DLL import/export */
++#define PyMODINIT_FUNC void
++#endif
++PyMODINIT_FUNC
++PyInit_rbac (void) {
++	PyObject* m;
++
++	if (PyType_Ready(&AuthattrType) < 0 || 
++		PyType_Ready(&ExecattrType) < 0 ||
++		PyType_Ready(&UserattrType) < 0 )
++		return NULL;
++
++       static struct PyModuleDef moduledef = {
++           PyModuleDef_HEAD_INIT,
++           "rbac",
++           pyrbac__doc__,
++           -1,
++           module_methods,
++           NULL,
++           NULL,
++           NULL,
++           NULL,
++       };
++
++       m = PyModule_Create(&moduledef);
++	if ( m == NULL )
++		return NULL;
++	
++	Py_INCREF(&AuthattrType);
++	PyModule_AddObject(m, "authattr", (PyObject*)&AuthattrType);
++
++	Py_INCREF(&ExecattrType);
++	PyModule_AddObject(m, "execattr", (PyObject*)&ExecattrType);
++
++	Py_INCREF(&UserattrType);
++	PyModule_AddObject(m, "userattr", (PyObject*)&UserattrType);
++
++	return m;
++
++}
+diff --git Python-2.6.4/Modules/pyrbac.h Python-2.6.4/Modules/pyrbac.h
+new file mode 100644
+--- /dev/null
++++ Python-2.6.4/Modules/pyrbac.h
[email protected]@ -0,0 +1,45 @@
++/*
++ * CDDL HEADER START
++ *
++ * The contents of this file are subject to the terms of the
++ * Common Development and Distribution License (the "License").
++ * You may not use this file except in compliance with the License.
++ *
++ * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
++ * or http://www.opensolaris.org/os/licensing.
++ * See the License for the specific language governing permissions
++ * and limitations under the License.
++ *
++ * When distributing Covered Code, include this CDDL HEADER in each
++ * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
++ * If applicable, add the following below this CDDL HEADER, with the
++ * fields enclosed by brackets "[]" replaced with your own identifying
++ * information: Portions Copyright [yyyy] [name of copyright owner]
++ *
++ * CDDL HEADER END
++ */
++
++/*
++ * Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved.
++ */
++
++/* 
++ * RBAC bindings for python
++ */
++#ifndef PYRBAC_H
++#define PYRBAC_H
++
++#include <secdb.h>
++
++
++#define PYRBAC_USER_MODE 1
++#define PYRBAC_PROF_MODE 2
++#define PYRBAC_ATTR_MODE 3
++#define PYRBAC_NAM_MODE 4
++#define PYRBAC_UID_MODE 5
++
++PyTypeObject AuthattrType;
++PyTypeObject ExecattrType;
++PyTypeObject UserattrType;
++
++#endif
+diff --git Python-2.6.4/Modules/userattr.c Python-2.6.4/Modules/userattr.c
+new file mode 100644
+--- /dev/null
++++ Python-2.6.4/Modules/userattr.c
[email protected]@ -0,0 +1,308 @@
++/*
++ * CDDL HEADER START
++ *
++ * The contents of this file are subject to the terms of the
++ * Common Development and Distribution License (the "License").
++ * You may not use this file except in compliance with the License.
++ *
++ * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
++ * or http://www.opensolaris.org/os/licensing.
++ * See the License for the specific language governing permissions
++ * and limitations under the License.
++ *
++ * When distributing Covered Code, include this CDDL HEADER in each
++ * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
++ * If applicable, add the following below this CDDL HEADER, with the
++ * fields enclosed by brackets "[]" replaced with your own identifying
++ * information: Portions Copyright [yyyy] [name of copyright owner]
++ *
++ * CDDL HEADER END
++ */
++
++/*
++ * Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved.
++ */
++
++/*
++ * RBAC Bindings for Python - user_attr functions
++ */
++
++#include <stdio.h>
++#include <user_attr.h>
++#include "Python.h"
++#include "pyrbac.h"
++
++static PyObject*
++pyrbac_setuserattr(PyObject* self, PyObject* args) {
++	setuserattr();
++	return Py_None;
++}
++
++static PyObject*
++pyrbac_enduserattr(PyObject* self, PyObject* args) {
++	enduserattr();
++	return Py_None;
++}
++
++PyObject*
++pyrbac_getuseruidnamattr(PyObject* self, void* arg, int mode, char* filename) {
++	
++	userattr_t *ret_userattr;
++
++	if (mode == PYRBAC_ATTR_MODE) {
++	    if (filename != NULL) {
++            FILE* file = fopen(filename, "r");
++            if (file == NULL)
++                return NULL;
++	        ret_userattr = fgetuserattr(file);
++	        if (fclose(file))
++                return NULL;
++	    }
++	    else
++	    	ret_userattr = getuserattr();
++	}
++	else if (mode == PYRBAC_NAM_MODE)
++		ret_userattr = getusernam((char*) arg);
++	else if (mode == PYRBAC_UID_MODE)
++		ret_userattr = getuseruid(*((uid_t*) arg));
++	
++	if (ret_userattr == NULL)
++		return Py_None;
++	
++	PyObject* entry = PyTuple_New(5);
++	if (entry == NULL) {
++		free_userattr(ret_userattr);
++		return NULL;
++	}
++	
++	PyObject* kv_data = PyDict_New();
++
++	if(ret_userattr->attr != NULL) {
++		int len;
++		for(len = 0; len < ret_userattr->attr->length; len++) {
++			kv_t current = ret_userattr->attr->data[len];
++
++			PyObject* set = PyList_New(NULL);
++			char* saveptr;
++			char* item = strtok_r(current.value, ",", &saveptr);
++			PyList_Append(set, PyBytes_FromString(item));
++
++			while((item = strtok_r(NULL, ",", &saveptr)) != NULL) {
++				if(PyList_Append(set, PyBytes_FromString(item)) != 0) {
++					Py_XDECREF(set);
++					Py_XDECREF(kv_data);
++					free_userattr(ret_userattr);
++					return NULL;
++				}
++			}
++			if(PyDict_SetItemString(kv_data, current.key, set)) {
++					free_userattr(ret_userattr);
++					return NULL;
++			}
++		}
++	}
++	entry = Py_BuildValue("{s:s,s:s,s:s,s:s,s:O}", 
++		"name", ret_userattr->name,
++		"qualifier", ret_userattr->qualifier,
++		"res1", ret_userattr->res1,
++		"res2", ret_userattr->res2,
++		"attributes", kv_data);
++
++	free_userattr(ret_userattr);
++	
++	return entry;
++}
++
++
++static PyObject*
++pyrbac_getuserattr(PyObject* self, PyObject* args) {
++	return(pyrbac_getuseruidnamattr(self, (void*) NULL, PYRBAC_ATTR_MODE, NULL));
++}
++
++static PyObject*
++pyrbac_fgetuserattr(PyObject* self, PyObject* args) {
++	char* filename = NULL;
++	if(!PyArg_ParseTuple(args, "s:fgetuserattr", &filename))
++		return NULL;
++	return(pyrbac_getuseruidnamattr(self, NULL, PYRBAC_ATTR_MODE, filename));
++}
++
++static PyObject*
++pyrbac_getusernam(PyObject* self, PyObject* args) {
++	char* name = NULL;
++	if(!PyArg_ParseTuple(args, "s:getusernam", &name))
++		return NULL;
++	return(pyrbac_getuseruidnamattr(self, (void*) name, PYRBAC_NAM_MODE, NULL));
++}
++
++static PyObject*
++pyrbac_getuseruid(PyObject* self, PyObject* args) {
++	uid_t uid;
++	if(!PyArg_ParseTuple(args, "i:getuseruid", &uid))
++		return NULL;
++	return(pyrbac_getuseruidnamattr(self, (void*) &uid, PYRBAC_UID_MODE, NULL));
++}
++
++static PyObject*
++pyrbac_userattr_next(PyObject* self, PyObject* args) {
++	PyObject* retval = pyrbac_getuserattr(self, args);
++	if( retval == Py_None ) {
++		setuserattr();
++		return NULL;
++	}
++	return retval;
++}
++static PyObject*
++pyrbac_userattr__iter__(PyObject* self, PyObject* args) {
++	return self;
++}
++
++typedef struct {
++	PyObject_HEAD
++} Userattr;
++
++static void
++Userattr_dealloc(Userattr* self) {
++	enduserattr();
++	Py_TYPE(self)->tp_free((PyObject*) self);
++}
++
++static PyObject*
++Userattr_new(PyTypeObject *type, PyObject *args, PyObject *kwds) {
++	Userattr *self;
++	self = (Userattr*)type->tp_alloc(type, 0);
++
++	return ((PyObject *) self);
++}
++
++static int
++Userattr_init(Userattr* self, PyObject *args, PyObject *kwargs) {
++	setuserattr();
++	return 0;
++}
++
++static char pyrbac_userattr__doc__[];
++PyDoc_STRVAR(pyrbac_userattr__doc__, "provides functions for \
++interacting with the extended user attributes database. May be iterated over \
++to enumerate user_attr(4) entries\n\n\
++Methods provided:\n\
++setuserattr\n\
++enduserattr\n\
++getuserattr\n\
++fgetuserattr\n\
++getusernam\n\
++getuseruid");
++
++static char pyrbac_setuserattr__doc__[];
++static char pyrbac_enduserattr__doc__[];
++static char pyrbac_getuserattr__doc__[];
++static char pyrbac_getusernam__doc__[];
++static char pyrbac_getuseruid__doc__[];
++
++PyDoc_STRVAR(pyrbac_setuserattr__doc__, "\"rewinds\" the user_attr functions \
++to the first entry in the db. Called automatically by the constructor.\n\
++\tArguments: None\n\
++\tReturns: None");
++
++PyDoc_STRVAR(pyrbac_enduserattr__doc__, "closes the user_attr database, \
++cleans up storage. called automatically by the destructor\n\
++\tArguments: None\n\
++\tReturns: None");
++
++PyDoc_STRVAR(pyrbac_getuserattr__doc__, "Return a single user_attr entry\n \
++\tArguments: None\n\
++\tReturns: a dict representation of a userattr_t struct:\n\
++\t\t\"name\": username\n\
++\t\t\"qualifier\": reserved\n\
++\t\t\"res1\": reserved\n\
++\t\t\"res2\": reserved\n\
++\t\t\"attributes\": A Python dict keyed by attribute & valued as either a list \
++or a string depending on value"
++);
++
++PyDoc_STRVAR(pyrbac_fgetuserattr__doc__, "Return a single user_attr entry \
++from a file, bypassing nsswitch.conf\n\
++\tArguments: \'filename\'\n\
++\tReturns: a dict representation of a userattr_t struct:\n\
++\t\t\"name\": username\n\
++\t\t\"qualifier\": reserved\n\
++\t\t\"res1\": reserved\n\
++\t\t\"res2\": reserved\n\
++\t\t\"attributes\": A Python dict keyed by attribute & valued as either a list \
++or a string depending on value");
++
++PyDoc_STRVAR(pyrbac_getusernam__doc__, "Searches for a user_attr entry with a \
++given user name\n\
++\tArgument: \'username\'\n\
++\tReturns: a dict representation of a userattr_t struct:\n\
++\t\t\"name\": username\n\
++\t\t\"qualifier\": reserved\n\
++\t\t\"res1\": reserved\n\
++\t\t\"res2\": reserved\n\
++\t\t\"attributes\": A Python dict keyed by attribute & valued as either a list \
++or a string depending on value");
++
++PyDoc_STRVAR(pyrbac_getuseruid__doc__, "Searches for a user_attr entry with a \
++given uid\n\
++\tArgument: uid\n\
++\tReturns: a dict representation of a userattr_t struct:\n\
++\t\t\"name\": username\n\
++\t\t\"qualifier\": reserved\n\
++\t\t\"res1\": reserved\n\
++\t\t\"res2\": reserved\n\
++\t\t\"attributes\": A Python dict keyed by attribute & valued as either a list \
++or a string depending on value");
++
++static PyMethodDef Userattr_methods[] = {
++	{"setuserattr", pyrbac_setuserattr, METH_NOARGS, pyrbac_setuserattr__doc__},
++	{"enduserattr", pyrbac_enduserattr, METH_NOARGS, pyrbac_enduserattr__doc__},
++	{"getuserattr", pyrbac_getuserattr, METH_NOARGS, pyrbac_getuserattr__doc__},
++	{"fgetuserattr", pyrbac_fgetuserattr, METH_VARARGS, pyrbac_fgetuserattr__doc__},
++	{"getusernam", pyrbac_getusernam, METH_VARARGS, pyrbac_getusernam__doc__},
++	{"getuseruid", pyrbac_getuseruid, METH_VARARGS, pyrbac_getuseruid__doc__},
++	{NULL, NULL}
++};
++
++PyTypeObject UserattrType = {
++	PyVarObject_HEAD_INIT(NULL, 0)
++	"rbac.userattr",              /*tp_name*/
++	sizeof(Userattr),             /*tp_basicsize*/
++	0,                            /*tp_itemsize*/
++	(destructor)Userattr_dealloc, /*tp_dealloc*/
++	0,                            /*tp_print*/
++	0,                            /*tp_getattr*/
++	0,                            /*tp_setattr*/
++	0,                            /*tp_reserved*/
++	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_BASETYPE,          /*tp_flags*/
++	pyrbac_userattr__doc__,       /* tp_doc */
++	0,		              /* tp_traverse */
++	0,		              /* tp_clear */
++	0,		              /* tp_richcompare */
++	0,		              /* tp_weaklistoffset */
++	pyrbac_userattr__iter__,      /* tp_iter */
++	pyrbac_userattr_next,         /* tp_iternext */
++	Userattr_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)Userattr_init,      /* tp_init */
++	0,                            /* tp_alloc */
++	Userattr_new,                 /* tp_new */
++	0,                            /* tp_free */
++	0,                            /* tp_is_gc */
++};
+--- Python-3.4.0/setup.py.~5~	2014-03-19 10:47:07.143319629 -0700
++++ Python-3.4.0/setup.py	2014-03-19 10:47:07.193485865 -0700
[email protected]@ -1480,6 +1480,22 @@
+             exts.append( Extension('dlpi', ['dlpimodule.c'],
+                                    libraries = ['dlpi']) )
+ 
++        # privileges module (Solaris)
++        priv_inc = find_file('priv.h', [], inc_dirs)
++        if priv_inc is not None:
++            exts.append( Extension('privileges', ['privileges.c']))
++
++        # rbac module (Solaris)
++        secdb_inc = find_file('secdb.h', [], inc_dirs)
++        aa_inc = find_file('auth_attr.h', [], inc_dirs)
++        ea_inc = find_file('exec_attr.h', [], inc_dirs)
++        ua_inc = find_file('user_attr.h', [], inc_dirs)
++        if secdb_inc is not None and aa_inc is not None and \
++            ea_inc is not None and ua_inc is not None:
++            exts.append( Extension('rbac', ['pyrbac.c', 'authattr.c', \
++                                   'execattr.c', 'userattr.c'],
++                                   libraries = ['nsl', 'socket', 'secdb']) )
++
+         # Thomas Heller's _ctypes module
+         self.detect_ctypes(inc_dirs, lib_dirs)
+ 
+--- /dev/null	2011-02-12 03:13:57.000000000 -0600
++++ Python-3.4.0/Lib/test/privrbactest.py	2011-01-20 13:52:42.862305331 -0600
[email protected]@ -0,0 +1,289 @@
++#!/usr/bin/python3.4
++#
++# CDDL HEADER START
++#
++# The contents of this file are subject to the terms of the
++# Common Development and Distribution License (the "License").
++# You may not use this file except in compliance with the License.
++#
++# You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
++# or http://www.opensolaris.org/os/licensing.
++# See the License for the specific language governing permissions
++# and limitations under the License.
++#
++# When distributing Covered Code, include this CDDL HEADER in each
++# file and include the License file at usr/src/OPENSOLARIS.LICENSE.
++# If applicable, add the following below this CDDL HEADER, with the
++# fields enclosed by brackets "[]" replaced with your own identifying
++# information: Portions Copyright [yyyy] [name of copyright owner]
++#
++# CDDL HEADER END
++#
++
++# Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved.
++
++import privileges
++import rbac
++import os
++import sys
++import tempfile
++
++# privileges tests
++
++def test_setppriv():
++    amchild = os.fork()
++    if amchild == 0:
++        if privileges.setppriv(privileges.PRIV_OFF, privileges.PRIV_EFFECTIVE, 
++            ['proc_fork']):
++            try:
++                os.fork()
++                sys.exit(1)
++            except OSError as e:
++                sys.exit(0)
++
++    child = os.wait()
++    if child[1] is not 0:
++        print("setppriv. Bad exit status from pid %i\n" % child[0])
++        return False
++    return True
++
++def test_getppriv():
++    if 'proc_fork' in privileges.getppriv(privileges.PRIV_LIMIT):
++        return True
++    print("getppriv or PRIV_PROC_FORK not in PRIV_LIMIT.\n")
++    return False
++
++def test_priv_ineffect():
++    if privileges.priv_ineffect('proc_fork'):
++        return True
++    print("priv_ineffect or PRIV_PROC_FORK not in effect\n")
++    return False
++
++# authattr tests
++
++def test_chkauthattr():
++    try:
++        a = rbac.authattr()
++    except Exception as e:
++        print("Could not instantiate authattr object: %s\n" % e)
++        return False
++    try:
++        res = a.chkauthattr('solaris.*', 'root')
++    except Exception as e:
++        print("chkauthattr failed: %s\n" % e)
++        return False
++    if not res:
++        print("chkauthattr failed or \'root\' lacks \'solaris.*\'\n")
++        return False
++    return True
++
++def test_getauthattr():
++    try:
++        a = rbac.authattr()
++    except Exception as e:
++        print("Could not instantiate authattr object: %s\n" % e)
++        return False
++    try:
++        res = a.getauthattr()
++    except Exception as e:
++        print("getauthattr failed: %s\n" % e)
++        return False
++    if not 'name' in list(res.keys()):
++        print("getauthattr failed\n")
++        return False
++    return True
++
++def test_getauthnam():
++    try:
++        a = rbac.authattr()
++    except Exception as e:
++        print("Could not instantiate authattr object: %s\n" % e)
++        return False
++    try:
++        res = a.getauthnam('solaris.')
++    except Exception as e:
++        print("getauthnam failed: %s\n" % e)
++        return False
++    if not res:
++        print("getauthnam failed or \'solaris.\' not in auth_attr(4)\n")
++        return False
++    return True
++
++def test_authattr_iter():
++    try:
++        a = rbac.authattr()
++    except Exception as e:
++        print("Could not instantiate authattr object: %s\n" % e)
++        return False
++    res = next(a)
++    if not 'name' in list(res.keys()) or type(a) != type(a.__iter__()):
++        print("authattr object is not an iterable\n")
++        return False
++    return True
++
++# execattr tests
++
++def test_getexecattr():
++    try:
++        a = rbac.execattr()
++    except Exception as e:
++        print("Could not instantiate execattr object: %s\n" % e)
++        return False
++    try:
++        res = a.getexecattr()
++    except Exception as e:
++        print("getexecattr failed: %s\n" % e)
++        return False
++    if not 'name' in list(res.keys()):
++        print("getexecattr failed\n")
++        return False
++    return True
++
++def test_getexecuser():
++    try:
++        a = rbac.execattr()
++    except Exception as e:
++        print("Could not instantiate execattr object: %s\n" % e)
++        return False
++    try:
++        res = a.getexecuser("root", "act", "*;*;*;*;*")
++    except Exception as e:
++        print("getexecuser failed: %s\n" % e)
++        return False
++    if not res:
++        print("getexecuser failed or \'root\' not assigned to \'act\', " \
++            "\'*;*;*;*;*\' \n")
++        return False
++    return True
++
++
++def test_getexecprof():
++    try:
++        a = rbac.execattr()
++    except Exception as e:
++        print("Could not instantiate execattr object: %s\n" % e)
++        return False
++    try:
++        res = a.getexecprof("All", "cmd", "*")
++    except Exception as e:
++        print("getexecprof failed: %s\n" % e)
++        return False
++    if not res:
++        print("getexecprof failed or \'All\' not granted \'cmd\' : \'*\'\n")
++        return False
++    return True
++
++def test_execattr_iter():
++    try:
++        a = rbac.execattr()
++    except Exception as e:
++        print("Could not instantiate execattr object: %s\n" % e)
++        return False
++    res = next(a)
++    if not 'name' in list(res.keys()) or type(a) != type(a.__iter__()):
++        print("execattr object is not an iterable\n")
++        return False
++    return True
++
++# userattr tests
++
++def test_getuserattr():
++    try:
++        a = rbac.userattr()
++    except Exception as e:
++        print("Could not instantiate userattr object: %s\n" % e)
++        return False
++    try:
++        res = a.getuserattr()
++    except Exception as e:
++        print("getuserattr failed: %s\n" % e)
++        return False
++    if not 'name' in list(res.keys()):
++        print("getuserattr failed\n")
++        return False
++    return True
++
++def test_fgetuserattr():
++    temp = tempfile.NamedTemporaryFile()
++    temp.write("user::::profiles=Software Installation;roles=foo;"\
++        "auths=solaris.foo.bar")
++    temp.seek(0)
++    try:
++        a = rbac.userattr()
++    except Exception as e:
++        print("Could not instantiate userattr object: %s\n" % e)
++        return False
++    try:
++        res = a.fgetuserattr(temp.name)
++        temp.close()    
++    except Exception as e:
++        print("fgetuserattr failed: %s\n" % e)
++        temp.close()
++        return False
++    if not 'name' in list(res.keys()):
++        print("fgetuserattr failed\n")
++        return False
++    return True
++
++def test_getuseruid():
++    try:
++        a = rbac.userattr()
++    except Exception as e:
++        print("Could not instantiate userattr object: %s\n" % e)
++        return False
++    try:
++        res = a.getuseruid(0)
++    except Exception as e:
++        print("getusernam failed: %s\n" % e)
++        return False
++    if not 'name' in res:
++        print("getusernam failed or no uid 0\n")
++        return False
++    return True
++
++def test_getusernam():
++    try:
++        a = rbac.userattr()
++    except Exception as e:
++        print("Could not instantiate userattr object: %s\n" % e)
++        return False
++    try:
++        res = a.getusernam('root')
++    except Exception as e:
++        print("getusernam failed: %s\n" % e)
++        return False
++    if not 'name' in res:
++        print("getusernam failed or no \'root\' user\n")
++        return False
++    return True
++
++def test_userattr_iter():
++    try:
++        a = rbac.userattr()
++    except Exception as e:
++        print("Could not instantiate userattr object: %s\n" % e)
++        return False
++    res = next(a)
++    if not 'name' in list(res.keys()) or type(a) != type(a.__iter__()):
++        print("userattr object is not an iterable\n")
++        return False
++    return True
++