I have a lot folders from sources which contents .cpp and .h files. Each folder contains CMakeLists.txt file except folders which contents .h headers files. I see the several ways.
The first way is consist from take advantage of add_library(myLib1 STATIC /link/to/sources/somefile.cpp /link/to/sources/interfaces/somefile.h). But in this way I will have a lot strings when is't good way, I think. Because I have very more files, which are interconnected.
The same way, with that exception when use set(HEADERS /link1 /link2 ....) and set(SOURCES /link3 ...) and than add_library(myLib ${HEADERS} ${SOURCES}).
I think than both the ways is't do properly. I don't know how I can connect the folder with library into my project, because if include this using the above methods it's will take a long time and is't beautiful
Related
I am generating a STATIC library on Linux with the name myLi using CMake, but apart from myLib.a I would like to generate one big blob of .o (OBJECT) file that contains everything in it (all the sources/object files), but I can't figure out how to do it with CMake (with makefile it's easy done). I have tried the following:
set(${SOURCE_FILES} src/file1.cpp src/file2.cpp .. )
add_library(myLib OBJECT ${SOURCE_FILES})
target_link_libraries(myLib PRIVATE ${LIBS_THAT_REQUIRED})
add_library(FinalLibrary STATIC $<TARGET_OBJECTS:myLib> ...)
I would expect to find myLib.o blob somewhere, but I can't figure out how I can generate it.
Any thoughts?
TL;DR: you can't, what you describe is not an object file, and your interest in producing such an artifact is probably misplaced.
How to generate and export one big OBJECT .o library blob from CMake instead of STATIC .a library
Object files are not among the targets that CMake provides for defining. They are of course produced incidentally in the process of building program and library targets, but they are not an end goal. You might be able to set them up as custom targets, but substantially no one does this.
And they do not do it because there is nothing anyone typically wants to do with an object file that you cannot do with a static library containing that object file, or containing multiple object files that jointly contain the same content. There are, however, one or two things that you can do with a library that you cannot do directly with an object file.
I would like to generate one big blob of .o (OBJECT) file that contains everything in it (all the sources/object files)
That's not what an object file is. An object file is the result of compiling one translation unit (roughly, one source file plus any headers / included files / whatever), and it does not contain source.
And I have no idea what you have in mind to do with such a thing. An archive of the unbuilt source is potentially interesting. One or more programs or libraries built from the source is potentially interesting. An installation package containing some or all of the above is potentially interesting. But the intermediate object files are not interesting, except as stepping stones on a path to one of the others, and none of the aggregates I just listed are object files.
I would expect to find myLib.o blob somewhere, but I can't figure out how I can generate it.
I have no idea why you would expect that unless the library were built from a single source file (which seems not to be the case for you). And if it were built from a single source file then I expect that you would have been able to find the corresponding object file. Which would not contain source, unless possibly in the form of debug information.
A static library is a container for object files. They are created by compiling some number of source files to object files, then putting those object files into the library. (From which they also can be extracted, at least with many common library formats.) There is no other intermediate involved in creating one.
To get a one big object file you need to compile a one big source file. C/C++ sources can be concatenated before the compilation and this is called a Unity build.
Why is it recommended to add sources to a list first, rather than directly to the executable?
PROJECT( helloworld )
SET( hello_SRCS hello.cpp )
ADD_EXECUTABLE( hello ${hello_SRCS} )
Why not just skip the SET line altogether?
I have seen this practice often enough to also think that it’s considered a good practice. For example, if you use the CLion IDE (which actually uses CMakeLists.txt as its project structure file), you’ll see that when you create a new project it creates a SOURCE_FILES variable by default.
One reason I can think of as to why this is a good practice is that if you want to build the same files into several targets. For example, you might want to have both static and shared binaries for your lib, so if you have a SOURCE_FILES var you just have to write something like:
add_library(myLibStatic STATIC ${SOURCE_FILES})
add_library(myLibShared SHARED ${SOURCE_FILES})
Over time my CMakeLists.txt files have grown by the addition of dozens of self functions and definitions. I would like to split these into their own file so as to simplify reuse in other projects and make the CMakeLists.txt file more readable.
currently I use a superdir CMakeLists.txt but I feel there has to be a better solution then that... something similar to \input in latex? or include in c++ for that matter
Ideas?
CMake has its own include command which allows you to bring additional CMake code into play, with variables in the included file still in the scope of the including CMakeList file (unlike add_subdirectory for example). Its effect should be as though you had pasted the contents of the included file into the CMakeList file at the point of the include.
My company has a bunch of Fortran code. Traditionally, we compiled the code we needed into a .dll and called that .dll when we needed a calculation done. We are now trying to create an iPad app, which unfortunately means we can't just call a .dll anymore.
One of my coworkers have managed to make a simple Command Line Tool project, where we call a Fortran file to write "Hello, World" in the debugger. However, when I try to get it to work on view based iPad app, I get a bunch of linker errors saying the symbols I'm using cannot be found. I know that the Command Line Tool uses a .cpp file to actually run the Fortran, and I've seen many threads concerning calling .cpp files in an app, but all the ones I've seen are outdated, directly contradict each other, and their fixes don't work for me.
My question is, is there a more direct way to call Fortran straight from a .m file? If not, what do I have to do to take the working Command Line Tool and get it into an app?
UPDATE 1: following the tutorials posted in the comments, I have been able to create a .o file from my Fortran code. I can do a File-Add Files to add it in easily enough, but now how do I actually call it?
UPDATE 2: Okay, baby steps. I found out you can make a .a static library (I'll call it "new_library") from .o files ("source_file.o") using the Terminal command ar crv new_library.a source_file.o (you can do it for multiple .o files by just adding source_file2.o source_file3.o for as many .o files as you want - NOTE: make sure you use cd to get to the folder where the .o files are located). I'm pretty sure Xcode will work with .a files, but it seems a .h file is still needed to let the other files in the project (like the view controllers) make calls to what's in the .a file. I know I can make a new .a file from Xcode itself (New Project -> iOS -> Framework & Library -> Cocoa Touch Static Library), but when I've done it that way in the past, I just write normal .m and .h files, and when I build the new library it just mashes all the .m files into 1 .a. When I want to use the code in that .a in another project, I just import the .a and all the .h files into the new project, and I can call the methods in the .a file just as if I had imported all the separate .m files. So the next question is, do I still need a .h when my .a is made with the terminal instead of Xcode? If so, how would I make a Fortran header file? If not, how do I call my Fortran code in the .a?
Let's try to sum up things:
You need a FORTRAN cross compiler that can produce ARM code. GCC is probably a good choice. But you will need to build it yourself from the source downloads.
Compile your FORTRAN code and put it into a static library. This task is perform outside XCode, probably from the command line.
Write C header files for those FORTRAN routines that you wand to call directly from C. You might want to look at Fortran and C/C++ mixed programming or Tutorial: Using C/C++ and Fortran together. These pages explain how to map the C data types to FORTRAN data types and vice versa.
Add the C header files and the static library to the XCode project.
Import the C header files into your Objective-C files (.m) where required and call the FORTRAN routines as if they were C functions.
Build the iOS app with XCode.
I wonder what is the more appropriate structure for a Objective-C project (a project that have more than ten classes...).
Code source
I put each class declaration and implementation respectively in a .h and .m files. Moreover I organize these files within a tree of folders. I don't want to have all my source files in a single folder. Is it the best approach for such project?
Building
What is the best approach to build Objective-C applications? I see that using makefile is possible but it seems that you need to specify all involved source files... Is it possible to have something to simply configure all source files for the build?
Packaging
What is the way to package the application in order to provide it as a library?
Thanks very much for your help!
Thierry
Code source
Putting relevant .h and .m files together in a subdirectory is fine. If you want the traditional Unix source layout, then put these subfolders into a directory named src, let your makefile build the library and intermediate object fiels into a filder named bld and put your Makefile in the top level directory, along with a LICENSE, a README and a CHANGELOG file.
Building
Using Makefile syntax, you can let Make build all source files into one library. Google a Makefile tutorial, but I can tell you that you probably want is something like
OBJECTS = $(patsubst %.o, %.m, $(wildcard Helpers/*.m))
OBJECTS += $(patsubst %.o, %.m, $(wildcard Network/*.m))
OBJECTS += $(patsubst %.o, %.m, $(wildcard External/*.m))
etc.
Packaging
I don't really understand this part of your question. How do you want to release it? You can distribute the source, and put into a tar(.gz or .bz2)ball. Or upload it to GitHub. Or build the source for some platforms, and make a DEB or RPM package out of the builds. It's difficult to tell in general, as every platform has something else (and not very specific) as convention.