{"id":120,"date":"2014-08-12T20:15:09","date_gmt":"2014-08-13T03:15:09","guid":{"rendered":"https:\/\/www.falatic.com\/?p=120"},"modified":"2014-08-25T22:03:19","modified_gmt":"2014-08-26T05:03:19","slug":"a-guide-to-building-python-2-x-and-3-x-extensions-for-windows","status":"publish","type":"post","link":"https:\/\/www.falatic.com\/index.php\/120\/a-guide-to-building-python-2-x-and-3-x-extensions-for-windows","title":{"rendered":"A Guide to Building Python 2.x and 3.x Extensions for Windows"},"content":{"rendered":"<p>I am a proponent\u00a0of <em>not<\/em> rebuilding binaries when possible (thanks to <a href=\"http:\/\/www.lfd.uci.edu\/~gohlke\/pythonlibs\/\" target=\"_blank\">Gohlke&#8217;s <em>Unofficial Windows Binaries for Python Extension Packages<\/em><\/a>\u00a0site and the <a href=\"https:\/\/pypi.python.org\/pypi\/wheel\" target=\"_blank\">Python\u00a0wheels<\/a>), but there are many times I need\u00a0to rebuild a binary Python extension, either to fix a problem or to get a package (or version <em>of<\/em> a package) that&#8217;s not on there. I&#8217;ve been around the block and back trying to build Python extensions for Windows using the various flavors of MinGW with (very)\u00a0limited\u00a0success, and have come to the conclusion that the best way is the direct way &#8211; build them using the same Windows SDKs that are used to build CPython itself&#8230;<\/p>\n<p><!--more-->It turns out that&#8217;s a pretty painless process, but first, some assumptions:<\/p>\n<ul>\n<li>You&#8217;re running Windows 7 (though this\u00a0probably works just as well on Windows 8)<\/li>\n<li>You&#8217;ve already installed Python 2.x (e.g., 2.7.8) or 3.x (e.g., 3.4.1) from <a href=\"https:\/\/www.python.org\/\" target=\"_blank\">Python.org<\/a><\/li>\n<\/ul>\n<p><em>I&#8217;m using 64-bit Windows&#8230; I would think using the 32-bit compilers with 32-bit Python would work as well on this platform, whereas is you&#8217;re using 32-bit Windows I doubt you&#8217;ll get far with 64-bit anything.<\/em><\/p>\n<p>First, you might\u00a0want to install the Visual Studio Express version(s) appropriate to the Python you&#8217;ll be building against:<\/p>\n<ul>\n<li>Python 2.x? Use\u00a0<em><a title=\"Direct link\" href=\"http:\/\/download.microsoft.com\/download\/E\/8\/E\/E8EEB394-7F42-4963-A2D8-29559B738298\/VS2008ExpressWithSP1ENUX1504728.iso\">Microsoft Visual Studio 2008 Express (with SP1)<\/a><\/em><\/li>\n<li>Python 3.x?\u00a0Use\u00a0<a href=\"http:\/\/go.microsoft.com\/?linkid=9709969\"><em>Microsoft Visual Studio 2010 Express<\/em><\/a>, then update with <em><a href=\"http:\/\/www.microsoft.com\/en-us\/download\/details.aspx?id=4422\">Visual Studio 2010 Express SP1<\/a><\/em><\/li>\n<\/ul>\n<p>Now\u00a0install the appropriate Windows SDK(s):<\/p>\n<p style=\"padding-left: 30px;\">You&#8217;ll be selecting one of two types of ISO based on the <em>OS of your build machine<\/em><\/p>\n<ul>\n<li>Running 64-bit Windows? Select GRMSDKX_EN_DVD.iso<\/li>\n<li>Running 32-bit Windows? Select GRMSDK_EN_DVD.iso<\/li>\n<li>(e.g., I&#8217;m running 64-bit Windows so I installed the 64-bit ISO to build both x86 <em>and<\/em> x64 targets)<\/li>\n<\/ul>\n<p style=\"padding-left: 30px;\">Get one or both\u00a0SDKs depending on the\u00a0version(s) of Python you&#8217;re targeting:<\/p>\n<ul>\n<li>Python 2.x? Use <a href=\"www.microsoft.com\/en-us\/download\/details.aspx?id=18950\" target=\"_blank\">Microsoft Windows SDK 7.0 for Windows 7 and .NET Framework 3.5 SP1 (ISO)<\/a><\/li>\n<li>Python 3.x?\u00a0Use\u00a0<a href=\"www.microsoft.com\/en-us\/download\/details.aspx?id=8442\" target=\"_blank\">Microsoft Windows SDK 7.1 for Windows 7 and .NET Framework 4 (ISO)<\/a><\/li>\n<\/ul>\n<p>Note: Windows 7 and above can open ISOs much like a ZIP file &#8211; extract it and run setup. You can skip the documentation and samples, and note that if you have newer versions of certain tools installed it will ask if you want to deprecate them (just say no).<\/p>\n<p>If you installed Visual Studio 2010, you should grab <em><a href=\"http:\/\/support.microsoft.com\/kb\/2519277\">the post-install KB2519277\u00a0fix for the compilers<\/a><\/em> as well. Run Windows Update to get\u00a0topped off with patches.<\/p>\n<p><strong>Problems installing the SDK?<\/strong>\u00a0It can be quite a pain sometimes&#8230; I encountered this on one of the machines I was setting up for this. First, rebooting can actually help, if you haven&#8217;t done so in a while or if\u00a0something else got installed\/updated in the interim.\u00a0Try <a href=\"http:\/\/social.msdn.microsoft.com\/Forums\/windowsdesktop\/en-US\/6e6c8a17-1666-42fa-9b5b-dfc21845d2f9\/error-installing-windows-7-sdk-71-with-vs2008-vs2010-premium-on-win-7-32bit?forum=windowssdk\" target=\"_blank\">removing the MS VC++ 2010 redistributables<\/a> (via Programs and Features) and reinstalling it again. If you have VS 2010 you&#8217;ll notice the compilers specifically fail to install &#8211; because\u00a0you&#8217;ve already got compilers!<\/p>\n<p>You can use the SDK command prompt shortcuts as they were created. Here&#8217;s what those shortcuts look like on my setup:<\/p>\n<ul>\n<li>Python 2.x:<\/li>\n<li>\n<pre>cmd.exe \/E:ON \/V:ON \/T:0E \/K \"C:\\Program Files\\Microsoft SDKs\\Windows\\v7.0\\Bin\\SetEnv.cmd\"<\/pre>\n<\/li>\n<\/ul>\n<ul>\n<li>Python 3.x:<\/li>\n<li>\n<pre>cmd.exe \/E:ON \/V:ON \/T:0E \/K \"C:\\Program Files\\Microsoft SDKs\\Windows\\v7.1\\Bin\\SetEnv.cmd\"<\/pre>\n<\/li>\n<\/ul>\n<p>After starting the SDK console, you need to select the target\u00a0build of interest (x86 = 32-bit, x64 = 64-bit). Here, I select the x64 release environment:<\/p>\n<pre>setenv \/x64 \/release\r\nset DISTUTILS_USE_SDK=1<\/pre>\n<p><em>After running these commands the text colors in the console should change from yellow (signifying &#8220;debug&#8221; target mode) to green (signifying &#8220;release&#8221; target mode)<\/em><\/p>\n<p>At this point (within the SDK\u00a0command prompt!) we can build those tricky binary extensions ourselves or use pip (or pip3.4) to build and install them.<\/p>\n<hr \/>\n<p>&nbsp;<\/p>\n<p><strong>Example time:<\/strong> Let&#8217;s build the\u00a0<a href=\"https:\/\/www.dlitz.net\/software\/pycrypto\/\" target=\"_blank\">pycrypto<\/a>\u00a0extension for Python 2.7 and\/or 3.4! (This is\u00a0particularly useful\u00a0as finding the binary is notoriously difficult.)<\/p>\n<p>First, download the source tarball from the website and extract it somewhere useful.<\/p>\n<p>I want to build the Python 2.7 version&#8230; Start the SDK 7.0 environment\u00a0as discussed earlier and switch to the folder you extracted the source code to, e.g.:<\/p>\n<pre> cd \/d %USERPROFILE%\\Desktop\\pycrypto-2.6.1<\/pre>\n<p>Thoroughly remove the previous build artifacts to ensure a clean build (if you don&#8217;t you can get some odd problems, and unfortunately the &#8220;clean&#8221; target doesn&#8217;t always work as you expect it to).<\/p>\n<pre>rmdir \/q \/s build dist<\/pre>\n<p>Run the build for Python 2.7<\/p>\n<pre>setenv \/x64 \/release\r\nset DISTUTILS_USE_SDK=1\r\nC:\\Python27\\python.exe setup.py build\r\nC:\\Python27\\python.exe setup.py bdist --format=wininst<\/pre>\n<p>(I\u00a0used the &#8220;wininst&#8221; format above to create setup executables\u00a0like you get at the Unofficial Windows Binaries site mentioned earlier &#8211; I tried the msi\u00a0format and it was less forgiving IMHO.)<\/p>\n<p>Now I want to build the Python 3.4 version&#8230; Start the SDK 7.1 environment\u00a0as discussed earlier and switch to the folder where the code is. Then run the build for Python 3.4:<\/p>\n<pre>setenv \/x64 \/release\r\nset DISTUTILS_USE_SDK=1\r\nC:\\Python34\\python.exe setup.py build\r\nC:\\Python34\\python.exe setup.py bdist --format=wininst<\/pre>\n<p>I now have two easily-installed artifacts:<\/p>\n<pre>.\\dist\\pycrypto-2.6.1.win-amd64-py2.7.exe\r\n.\\dist\\pycrypto-2.6.1.win-amd64-py3.4.exe<\/pre>\n<p>And that&#8217;s all there is to it!<\/p>\n<p>(In an upcoming post I&#8217;ll go through a practical example of creating an extension using Cython.)<\/p>\n<hr \/>\n<p><em>(With gratitude to the <a title=\"Cython extension guide\" href=\"https:\/\/github.com\/cython\/cython\/wiki\/64BitCythonExtensionsOnWindows\" target=\"_blank\">Cython wiki on building extensions in Windows<\/a>, where I finally found a build framework that worked!)<\/em><\/p>\n<!-- wpsso rrssb get buttons: buttons on archive option not enabled -->\n","protected":false},"excerpt":{"rendered":"<p>I am a proponent\u00a0of not rebuilding binaries when possible (thanks to Gohlke&#8217;s Unofficial Windows Binaries for Python Extension Packages\u00a0site and the Python\u00a0wheels), but there are many times I need\u00a0to rebuild <a href=\"https:\/\/www.falatic.com\/index.php\/120\/a-guide-to-building-python-2-x-and-3-x-extensions-for-windows\" class=\"more-link\">[&hellip;]<\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"Layout":"","footnotes":"","_links_to":"","_links_to_target":""},"categories":[86],"tags":[76,110,100,109,117],"class_list":["entry","author-marty","has-more-link","post-120","post","type-post","status-publish","format-standard","category-software-and-hardware-development","tag-build","tag-extensions","tag-python","tag-setup","tag-windows"],"_links":{"self":[{"href":"https:\/\/www.falatic.com\/index.php\/wp-json\/wp\/v2\/posts\/120","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.falatic.com\/index.php\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.falatic.com\/index.php\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.falatic.com\/index.php\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/www.falatic.com\/index.php\/wp-json\/wp\/v2\/comments?post=120"}],"version-history":[{"count":0,"href":"https:\/\/www.falatic.com\/index.php\/wp-json\/wp\/v2\/posts\/120\/revisions"}],"wp:attachment":[{"href":"https:\/\/www.falatic.com\/index.php\/wp-json\/wp\/v2\/media?parent=120"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.falatic.com\/index.php\/wp-json\/wp\/v2\/categories?post=120"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.falatic.com\/index.php\/wp-json\/wp\/v2\/tags?post=120"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}