https://www.cnblogs.com/flhang/p/10591639.html
PYTHON C++混合编程笔记(一)- VS2017 编译 python 2.7
0x00 前言
最近想把一些经验和笔记分享出来,也便于自己查询和复习。
0x01 环境准备
1) 下载python 最新2.7.16源代码
https://www.python.org/ftp/python/2.7.16/Python-2.7.16.tar.xz
2) VS2017
0x02 外部库下载
1)命令行进入到解压目录的PCbuild,如X:\Python-2.7.16\PCbuild
2)运行get_externals.bat,下载外部库,如图所示

0x03 编译
1)打开PCbuild目录的pcbuild.sln,根据需要选择后点“确定”,如图所示:

2)先选择python、pythoncore的win32 debug 版本测试编译,如图所示:

3)编译失败,需要修改相关标识符

4)timezone改为_timezone , daylight改为daylight , tzname改为tzname后,重新编译
1 #ifdef PYOS_OS2
2 PyModule_AddIntConstant(m, "timezone", _timezone);
3 #else /* !PYOS_OS2 */
4 PyModule_AddIntConstant(m, "timezone", _timezone);
5 #endif /* PYOS_OS2 */
6 #ifdef HAVE_ALTZONE
7 PyModule_AddIntConstant(m, "altzone", altzone);
8 #else
9 #ifdef PYOS_OS2
10 PyModule_AddIntConstant(m, "altzone", _timezone-3600);
11 #else /* !PYOS_OS2 */
12 PyModule_AddIntConstant(m, "altzone", _timezone -3600);
13 #endif /* PYOS_OS2 */
14 #endif
15 PyModule_AddIntConstant(m, "daylight", _daylight);
16 PyModule_AddObject(m, "tzname",
17 Py_BuildValue("(zz)", _tzname[0], _tzname[1]));
5)编译仍然失败,如下图所示:

6)找到pythoncore 工程的posixmodule.c , 修改_PyVerify_fd如下
/* This function emulates what the windows CRT does to validate file handles */
int
_PyVerify_fd(int fd)
{
// const int i1 = fd >> IOINFO_L2E;
// const int i2 = fd & ((1 << IOINFO_L2E) - 1);
// static int sizeof_ioinfo = 0;
// /* Determine the actual size of the ioinfo structure,
// * as used by the CRT loaded in memory
// */
// if (sizeof_ioinfo == 0 && __pioinfo[0] != NULL) {
// sizeof_ioinfo = _msize(__pioinfo[0]) / IOINFO_ARRAY_ELTS;
// }
// if (sizeof_ioinfo == 0) {
// /* This should not happen... */
// goto fail;
// }
// /* See that it isn't a special CLEAR fileno */
// if (fd != _NO_CONSOLE_FILENO) {
// /* Microsoft CRT would check that 0<=fd<_nhandle but we can't do that. Instead
// * we check pointer validity and other info
// */
// if (0 <= i1 && i1 < IOINFO_ARRAYS && __pioinfo[i1] != NULL) {
// /* finally, check that the file is open */
// my_ioinfo* info = (my_ioinfo*)(__pioinfo[i1] + i2 * sizeof_ioinfo);
// if (info->osfile & FOPEN) {
// return 1;
// }
// }
// }
//fail:
// errno = EBADF;
//a call to _get_osfhandle with invalid fd sets errno to EBADF
if (_get_osfhandle(fd) == INVALID_HANDLE_VALUE)
return 0;
else
return 1;
return 0;
}
7)再次编译,编译成功。

8)根据需要选择相应库进行编译
0x04 后记
C++ 调用python的工程中, 如果是debug必须使用debug版本的python,如果是release必须使用release版本编译的python,包括所有库的lib,debug必须使用***_d.lib。