Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 6 years ago.
Improve this question
This may seem a bit ridiculous to ask, but I'm struggling to find a good system for this. Are there any standardized systems for storing and organizing third party development libraries? I'm plagued with OCD and consider myself to be a "neat-freak," so I tend to use tons of directories/subdirectories for organizing items, but since I'm a newer developer, I just recently started dabbling with 3rd party libraries and I'm not sure how to go about organizing them. I would use a ton of folders and make a huge hierarchy, but doing that may result in some extremely long absolute paths in the #includes of my source code. Any suggestions?
Third party libraries can go anywhere you want, as long as you make sure that both the compiler and the compiled program can find the files that they need. So you can go wild with organizing your files in whatever you want, as long as you make sure that you tell this to the compiler and the compiled program.
Exactly how to do this depends on the IDE (integrated development environment) that you are using. I use visual studio, so the exact terminology might be different if you use something else. In visual studio, you have to go to the properties of your project to do this.
For the header files of your external libraries, go to Configuration Properties > C/C++ > General and click on "Additional Include Directories". If you edit the value of this field, you can add the paths to the include directory of your external library, which should hold all the header files of the external library. By using the Macros that Visual Studio provides, you can make these paths relative, so that you don't have to do this all over whenever you move your project. Make sure you don't remove "%(AdditionalIncludeDirectories)". Also make sure that the selected configuration and platform at the top of the window match the configuration and platform for which you are trying to compile. Using the macros you can set this up for all the configurations and platforms simultaneously, which is a bit harder but it will save you time in the long run. An example from one of my projects:
$(SolutionDir)dependencies\SDL2_image-2.0.1\include;$(SolutionDir)dependencies\SDL2-2.0.5\include;%(AdditionalIncludeDirectories)
For the library files, you need to go to Configuration Properties > Linker > General and click on "Additional Library Directories". Edit this value to add the paths to the lib folders of your external libraries. You can again use macros here.
$(SolutionDir)dependencies\SDL2-2.0.5\lib\x64;$(SolutionDir)dependencies\SDL2_image-2.0.1\lib\x64;%(AdditionalLibraryDirectories)
Next, go to Configuration Properties > Linker > Input and edit "Additional Dependencies" to add the names of the .lib files that you need. Just the filenames this time, you don't need the path here. An example from one of my projects:
SDL2main.lib;SDL2.lib;SDL2_image.lib;%(AdditionalDependencies)
Finally, you need to make sure that your compiled program can find the .dll files of your external libraries. For this you can mess around with system variables like PATH and so on, but I don't recommend that. I prefer to use a Post-Build Event. An event like this is basically a sequence of command line commands that are carried out after your program has been compiled. You can add this event by going to Configuration Properties > Build Events > Post-Build Event and editing "Command Line". An example of what you can put here, from one of my projects, is shown below:
copy /Y "$(SolutionDir)dependencies\SDL2_image-2.0.1\lib\$(PlatformTarget)\*.dll" "$(TargetDir)*.dll"
copy /Y "$(SolutionDir)dependencies\SDL2-2.0.5\lib\$(PlatformTarget)\SDL2.dll" "$(TargetDir)SDL2.dll"
xcopy /Y /S /E /I "$(SolutionDir)assets" "$(TargetDir)assets"
Note that I use macros again: $(SolutionDir), $(PlatformTarget), $(TargetDir) are replaced by the solution directory, platform target and the target directory respectively for each combination of Configuration and Platform.
You have 2 options:
Use system-installed libraries (and headers), tell compiler where to find them.
Use a folder in your project (use folder ./external to store external sources, e.g. ./external/boost-asio for Boost ASIO library), download sources when initializing the project (I prefer to use git submodules to download external sources), and build them with your project.
CMAKE is a build tool which can help you in achieving both.
Either way, as jtbandes wrote, don't use absolute paths.
Related
Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 2 years ago.
Improve this question
I have coded an app in c++ using the SFML library. I configured it into code blocks to run the program. Let's say I now want to send this app to my friend, what's the best way I can do this so that he doesn't have to go through downloading a lot of stuff to run it?
I am using the MinGW compiler.
Create an installer or package. For example; On RedHat Linux you'd want to create a RPM package. On Windows you want to create a MSI file. Whatever you do, the package you create should bundle up everything your application needs to run and put it into the correct location(s) on the target system. This includes your executable but also any libraries you use (including your compilers runtime libraries).
In most cases just shipping your .exe and all of its dependancies is enough.
In some cases you may also need to ship other files needed to run the application like configuration files, images, icons...
You can use copypedeps with the -r flag from https://github.com/brechtsanders/pedeps to copy your .exe along with its dependancy .dll files into an empty folder.
Then you can just zip everything in that folder and send it to somebody who can just unzip it an run the .exe.
Or you can make a proper installer to distribute the same files.
Your program needs some .dlls to run: some are the system ones, some are shipped with the compiler, and some come from the libraries you use (SFML). You need to ship all those .dlls (except the system ones) with your .exe, and they should be in the same directory.
It doesn't really matter if you make a proper installer or send your friend a zip archive. (If it's an archive, they might have to manually extract it before running the .exe.)
The question is how to figure out which .dlls to ship. There are several approaches:
Open the console, cd to where your .exe is, do set PATH= and try running the executable by typing its name. Since the compiler installation is no longer in the PATH, it shouldn't see the .dlls in there, and it should complain about them being missing. After you provide one .dll, it will ask for the next one.
A more civilized approach is to use a tool like ntdll to list all .dlls your app uses. Then copy them, ignoring the system ones (located in C:\Windows or subdirectories).
Note that both approaches rely on there being no extraneous .dlls in C:\Windows or subdirectories; some poorly written installers like to put their own .dlls in there. To check for that, make a list of all .dlls that come with your compiler (they should be in the same directory as the gcc.exe), and the ones that come from your libraries (SFML). Then look for the .dlls with the same name in C:\Windows and subdirectories, and if you find any, remove them.
Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 7 years ago.
Improve this question
I'm a Python developer with some background in another language such as Ruby.
In both language, dependency is managed by package manager automatically, such as pip or gem. Anyone could install such dependency by calling pip install -r requirements.txt, and it will install the necessary dependency via Python Package Index. Although, there has been an option to build the dependency manually from the source and install into the project, it is not a recommended process, and I have not done it.
I notice that C++ unfortunately have different nature in how dependency is being resolved for some reason. (e.g. different compiler flavor, compiler parameters, platforms, etc...)
At the moment, I am learning C++ using VS2015. and I have been stumbled again and again upon these library dependencies matter. With VS2015, there is a dependency package manager like python, and it is NuGet. However, not every library is available in NuGet, in fact, there are a lot of library developed independent from its IDE.
First I'm trying to use Boost. There is a manual on how to build the project, but I'm not sure what I need. Do I need to build from source? or Perhaps I just need a library that has been readily available?
Same reason for another library that I found. (e.g. QT, yaml-cpp, googletest, etc..)They only have a document how to build, instead of how to install as dependency.
And Ultimately, I will need to use lots of 3rd party library to be more productive. So, here's some of my questions that are very related.
How do C++ developer normally include 3rd party library into their project (the flow of installation 3rd party library)?
Do I have to build from source everytime I want to include? or perhaps you just need the header file which you could just copy and paste into your project directory?
I'm working in team (git), do each of my team need to build the dependency manually? Can it be automate such that the process of including new library is transparent for everyone?
Or perhaps, I don't really understand what specific question do I need
to ask. But why it is so painful to reuse library in C++?
Do I miss some fundamental understanding of C++ environement?
I'm not sure how much relevance it is, but CMake as a build tool that most library uses to build their project. Do I really need to build these library project?
More Questions:
After building some libraries, some of them generate static library .lib or dynamic library .dll to be included into the project. So is it correct to copy these generated library in our project? Should this be committed into the source version control? Some libraries are very large, and we don't want to maintain it. Yet we need the entire team to get the library transparently.
I understand you situation quite well. You cannot see the forest because too many trees are standing in your way...
Let me get one thing clear before I start to address your specific questions:
Generally speaking, dependencies in C++ are not more complicated than in Python.
The command pip install -r requirements.txt will establish an internet connection and download the necessary libraries and files from a repository server to fulfill the requirements. Under the Linux operating system (Ubuntu) the command: sudo apt-get install libboost-all-dev installs all required dependencies for boost. This is possible because there is a whole environment with servers that hold source-code as well as libraries and binaries that work together with the client programs (apt-get) that use it. This is exactly the same thing that the authors of pip have done for microsoft windows. microsoft themselves have never done this at the operating system level. They always left that to the programmer. NuGet is microsofts attempt to make-up for past mistakes.
Having this out of the way, let me address your questions:
It depends on the size of the 3rd party library. Small libraries like pugixml can be included as source in the source tree of your project. Bigger libraries like boost are better included as binary object code (library objects). Not all libraries do have binaries available to download (boost has), so you might be required to build from source. Bear in mind that all binaries are required to be built with exact the same compiler that you use in your project. The general steps to include it in your VS-Project:
Get the distribution files (either build from source or download and install binaries)
Add include paths to your Project:
Project > "projectname" properties > Configuration Properties > C/C++ > General > Additional Include Directories
Add paths to libraries:
Project > "projectname" properties > Configuration Properties > Linker > Input > Additional Dependencies.
No. You normally just use the header file. But it's better to add the path of the library into your project instead of copying the header file, because some projects (boost) have a huge hierarchy of header files.
It is a good idea that each member of your team has the same development environment with the same set of libraries installed. There are tools for this task: Chocolatey builds on top of NuGet and is therefore windows-affine. Vagrant deals with virtual boxes ands thus offers cross-platform development environments.
But more important is a decent source-control-management system. If you don't already use one - start using one Today!. This is the main collaboration-tool. It can really save your neck if you loose a developer machine.
There is another dependency problem: We've only addressed the development dependencies above. There is the problem of deployment dependencies:
your customers will need the libraries (*.dll files) that you have used for the development. You will need to package them as well into your deployment package (Installer). This is another issue which is probably already answered on SO.
Qt: if you start using Qt, I'd suggest that you start using their development environment Qt-Creator. This will automatically handle all dependencies. It will automatically detect the Visual Studio Compiler that you have installed, and use it. The IDE is quite close to Visual Studio.
CMake: No, it is not always required to use CMake to build a library project, some also include Makefiles. Others use CMake to produce Makefiles. "Follow the instructions" is the best advice I can give here.
Update 2015-10-24: paragraph point three reworked
How do C++ developer normally include 3rd party library into their
project (the flow of installation 3rd party library)?
It depends... There are a lot of ways, how to redistribute C++ libraries.
Do I have to build from source everytime I want to include? or perhaps
you just need the header file which you could just copy and paste into
your project directory?
For now, most C++ libraries contains two parts: binaries + header files. But often, there are a lot of problems, if compiler version of library is different with your compiler.
I'm working in team, do each of my team need to build the dependency
manually? Can it be automate such that the process of including new
library is transparent for everyone?
It depents on your team guidelines. You can choose what you want.
Or perhaps, I don't really understand what specific question do I need
to ask. But why it is so painful to reuse library in C++?
Because of some legacy of C. And because C++ is low-level language in compare with python/java/c#. C++ is supported by a lot of different platforms, including embedded. And ofter, it is not possible to install complex runtime on this platforms. So there are no mechanism to transparently link a "modules" in runtime.
Hopefully, there will be a normal support of modules in C++17 standard. And Microsoft will provide a technology preview of modules in C++ in MSVC 2015 update 1.
Do I miss some fundamental understanding of C++ environement?
Yes, I propose you to read about compiling and linking in C/C++. This two things are often come together, but they are different.
First, that you should mind: code in C/C++ is splitted in two parts: declaration (.h files) and implementation (.cpp files). .CPP files are compiled into binaries. .H files just declares an interfaces.
I am attempting to use the new VS2015 precompiled header refactoring tool. When I launch it, it pops up a message saying:
To improve recommendations, add third party library paths to the
'Exclude Directories' property under VC++ Directories (in the Project
Properties dialog).
I'm not clear on precisely what a directory is being excluded from if I list it here. All the MSDN help text has to say about it is:
Directories not to search when checking for build dependencies
That helps a little, but I'm still not completely sure about what functionality I will gain/lose if I list something here. Something like, say, boost (which the message from the pch tool seems to be suggesting). Can anyone say exactly what this setting does?
The general idea is that every time you hit 'Build' the IDE (or msbuild more specifically) has to check all the dependencies to see which cpp files need to be rebuilt. If you have a large project and many headers (boost being a good example) then this may have to check for thousands of headers (because each header also needs to have its dependencies checked).
If you have a third party library such as boost which is only updated very rarely then you can add the path to the Exclude box so that the dependency checker won't bother checking any of those libraries. However, if you do update the library at some point, or make a small change to it then you will have to manually rebuild all projects that relied on it, because you have told the build system not to do it for you.
In practice I've never found it to be a problem, even with a few MLOC project and a boost installation, especially if you're building with an SSD. If you're on older hardware then it may be worth using, but I think it may cause problems when you inevitably forget to rebuild dependent projects.
I find myself doing a lot of library including and juggling in recent projects with code::blocks- and I'm looking to improve my efficiency.
Currently, since I'm doing work with curl, zlib, wxwidgets, and other libraries, it takes quite some time to append the list after the initial project creation (even if I used a template).
Here's quick peek at a working project with all of the library files and how I'm including them:
Now to the two part question:
How can I quickly add several library files at once, in the correct order? (the order is evidently quite important)
How do .a files translate into "other linker options", in other words, can I simply include the search directory and use something like lwxmsw32u_core instead of including ...>\libwxmsw32u_core.a?
Alright, so there's a simple solution, the project file for code::blocks is quite mundane, a light XML implementation- you can very easily copy libraries (in the correct order) from one project to another by editing the plain text of the .cbp file.
Closed. This question is opinion-based. It is not currently accepting answers.
Want to improve this question? Update the question so it can be answered with facts and citations by editing this post.
Closed 3 years ago.
Improve this question
This questions concerns mostly Unix/Linux style C++ development. I see that many C++ libraries store their header files in a "include" folder and source files in an "src" folder. For the sake of conformance I adopted this in my own code. But it is not clear to me whether this should be done for application code as well. I've seen a few cases where a flat directory structure is used for that. What would be the recommended approach?
I also separate them, but not strictly on the extension, but on the access of the file.
Suppose you have a module that manages customer information and uses 2 classes to do this: Customer, CustomerValidityChecker.
Also suppose that other parts in your application only need to know about the Customer class, and that the CustomerValidityChecker is only used by the Customer class to perform some checking.
Based on these assumptions I store the files like this:
Public folder (or include folder):
customer.h
Private folder (or source folder):
customer.cpp
customervaliditychecker.h
customervaliditychecker.cpp
That way, it becomes immediately clear for callers of your module which parts are accessible (public) and which parts aren't.
We have a build system that auto-generates our makefiles. One thing it does is recursively descend any subdirectories and build them as libraries, linking them together with the main directory's objects to make the application. (In practice, these "subdirectories" are usually symbolic links.) Libraries are static unless the directory name ends in ".so". One thing that's nice about this is that a full build of our system, which has many executables, doesn't have to repeatedly compile the common libraries.
However, as a result of this, there's no separation of headers and sources. And it has never been a problem. Honestly, I think it's better this way because headers and source files have commonality of location, and you can grab a directory and know you got everything you need to use it. It also works great with Subversion's "externals" feature, and similar features in other VCSs.
One last place where an include/src separation fails is if you use any code generators, such as flex, bison, or gengetopts. Figuring out where these tools should put their outputs so they get built is tricky if you've spread things out.
It makes sense to separate them for shared libraries because they may be distributed in a compiled form without the source. I've seen projects that separate out "public" headers (headers that may be accessed from code outside your project or library) while leaving "private" headers and source files in the same directory. I think it's good to use a consistent approach whether you're writing shared library or application level code because you never know when you may want to turn something that you've written at the application level into a lower level library that is shared by multiple projects.
A lot depends on the size of project involved. Up to a few dozen files or so, keeping them in one directory tends to be more convenient. For a bigger application that includes hundreds or thousands of files, you start to look for ways to separate them (though in the projects I've worked on, it was done more on functional lines than src/include). In between those, it's probably open to question.
I don't do this; there seems little advantage in it. Since headers tend to have a different extension from source files, you can have your editor show them separately if you really feel the need -- Visual Studio does this by default, but I disable it since I prefer seeing them together
Bottom Line: sources and headers that are still changing go in /src. Code that has crystallised should go in /lib & /include (actually you could keep all .libs and their .hs in /lib).
Keep own sources and headers together, provided they are (a) specific to this project or (b) have not yet been factored out as a shared library.
Once certain sources in the main project have been factored out as a (relatively stable) library, place the .a or .lib into /lib, and its public interface header into /include.
All third party libraries and their public interface headers also go into /lib & /include.
As others note, it is often more compatible for tools / IDEs to access .h/.c from one folder. But from an organisational view it can be useful to separate changing local code from stable lib code.
There is no clear advantage to either in my view. I finally decided to keep program and header files together because my editor (Visual SlickEdit) happens to provide additional referential features when they are not separated.
I almost always create include and src folders to split up my source code. I think it makes the folder less cluttered and files are easier to find in my IDE. But I think this is just a matter of taste.
Either method is valid. It depends on the coding style you want to follow how you do this.
I place include (header) and source files in the same directory (folder). I create different folders for different themes. I get frustrated when trying to find header files (while debugging and also for researching). In some shops, there are only two folders: source and includes. These directories tend to grow exponentially. Reusing code becomes a nightmare at best.
IMHO, I believe organizing by theme is better. Each theme folder should build into at least one library. Different projects can easily include the themes by searching or including the folders. The projects only need to include the libraries. Smart build engines can list the theme folders as dependencies. This speeds up the build process.
The theme organization also adds a bit of safety to the project. Accidental damage to files (such as removing the wrong ones or replacing with different versions) is reduced since files are located in different directories. Deletion of files in the "Person" folder will not affect files in the "Shape" folder.
This is just my opinion, Your Mileage May Vary.
We have a build system which use this rule. This build system is sconspiracy a set of scripts to configure SCons and dedicated to the C++ world. You can see an example which use this tools : fw4spl