Given the below makefile:
TARGET = _example.pyd
OFILES = example.obj example_wrap.obj
HFILES =
CC = cl
CXX = cl
LINK = link
CPPFLAGS = -DNDEBUG -DUNICODE -DWIN32 -I. -Id:\virtual_envs\py351\include
CFLAGS = -nologo -Zm200 -Zc:wchar_t- -FS -Zc:strictStrings -O2 -MD -W3 -w44456 -w44457 -w44458
CXXFLAGS = -nologo -Zm200 -Zc:wchar_t- -FS -Zc:strictStrings -D_HAS_EXCEPTIONS=0 -O2 -MD -W3 -w34100 -w34189 -w44996 -w44456 -w44457 -w44458 -wd4577
LFLAGS = /LIBPATH:. /NOLOGO /DYNAMICBASE /NXCOMPAT /DLL /MANIFEST /MANIFESTFILE:$(TARGET).manifest /SUBSYSTEM:WINDOWS /INCREMENTAL:NO
LIBS = /LIBPATH:d:\virtual_envs\py351\libs python35.lib
.SUFFIXES: .c .cpp .cc .cxx .C
{.}.cpp{}.obj::
$(CXX) -c $(CXXFLAGS) $(CPPFLAGS) -Fo @<<
$<
<<
{.}.cc{}.obj::
$(CXX) -c $(CXXFLAGS) $(CPPFLAGS) -Fo @<<
$<
<<
{.}.cxx{}.obj::
$(CXX) -c $(CXXFLAGS) $(CPPFLAGS) -Fo @<<
$<
<<
{.}.C{}.obj::
$(CXX) -c $(CXXFLAGS) $(CPPFLAGS) -Fo @<<
$<
<<
{.}.c{}.obj::
$(CC) -c $(CFLAGS) $(CPPFLAGS) -Fo @<<
$<
<<
all: $(TARGET)
$(OFILES): $(HFILES)
$(TARGET): $(OFILES)
$(LINK) $(LFLAGS) /OUT:$(TARGET) @<<
$(OFILES) $(LIBS)
<<
mt -nologo -manifest $(TARGET).manifest -outputresource:$(TARGET);2
install: $(TARGET)
@if not exist d:\virtual_envs\py351\Lib\site-packages mkdir d:\virtual_envs\py351\Lib\site-packages
copy /y $(TARGET) d:\virtual_envs\py351\Lib\site-packages\$(TARGET)
clean:
-del $(TARGET)
-del *.obj
-del *.exp
-del *.lib
-del $(TARGET).manifest
test:
python runme.py
I'd like to improve a couple of things here:
I've read a little bit of the docs talking about Makefiles but I'm still pretty much confused. How could I achieve this?
Right now I'm using a hacky solution like swig -python -c++ whatever_file.i && nmake
, that's of course it's not ideal at all
REFERENCES
Achieving this inside visual studio IDE is quite easy following these steps but I'd like to use this makefile inside SublimeText, that's why I'm quite interested on knowing how to have a proper Makefile
Producing any kind of target from any kind of source, that's the essence of a makefile:
.i.cpp:
swig -python -c++ $<
This elegance will, however, break with nmake
( as opposed to GNU make
) if the .cpp
file is missing because nmake
doesn't try to chain inference rules through a missing link .
Moreover, it will break silently and "build" from stale versions of the files that are later in the build chain (which includes the resulting executable) if they are present.
Possible kludges workarounds here (save for ditching nmake
, of course) are:
invoke nmake
multiple times, first, to generate all files that are an intermediate steps between two inference rules (which can in turn require multiple invocations if they are generated from one another), and then for the final targets
This requires an external script which can very well be another makefile. Eg: move the current Makefile
to main_makefile
and create a new Makefile
with commands for the main target like this:
python -c "import os,os.path,subprocess; subprocess.check_call(['nmake', '/F', 'main_makefile'] +[os.path.splitext(f)[0]+'.cpp' for f in os.listdir('.') if os.path.isfile(f) and f.endswith('.i')])" nmake /F main_makefile
do not rely solely on inference rules but have an explicit rule for each .cpp
to be produced (that's what CMake does btw)
this asks for the relevant part of Makefile to be autogenerated. That part can be !INCLUDE
'd, but still, external code is needed to do the generation before nmake
gets to work on the result. Example code (again, in Python):
import os,os.path,subprocess for f in os.listdir('.') if os.path.isfile(f) and f.endswith('.i'): print '"%s": "%s"'%(os.path.splitext(f)[0]+'.cxx',f) #quotes are to allow for special characters, # see https://msdn.microsoft.com/en-us/library/956d3677.aspx #command is not needed, it will be added from the inferred rule I gave # in the beginning, see http://www.darkblue.ch/programming/Namke.pdf, p.41 (567)
I have solved this using CMake and this translates directly to using autoconf
and automake
and thereby makefiles.
The idea is to introduce the following variable
DEPENDENCIES = `swig -M -python -c++ -I. example.i | sed 's/\//g'`
and make your target depend on this. The above generates a list of dependencies of all headers and .i
files your SWIG interface file may include.
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.