In my previous question I've asked, I touched the parallel_for subject from ppl.h provided by Microsoft.
But shortly after I've realized that by using it one makes his application unportable (if I'm right it is specific to Microsoft (the ppl.h header)).
In my opinion this breaks very important aspect of programming in C++ - portability, and I'm just not prepare to do it.
So my questions are:
1. Am I right in saying that using parallel_for from ppl makes your code unportable (by unportable I mean that it cannot be compiled by other compiler than the one from MS)
2. Am I right in saying that if on later stage I want to provide UI (done in Qt) for the application I'm working on at the momment, using parallel_for in my code will be an obstruction which would mean that either I'll replace parallel_for with some other (portable) alternative or I won't be able to do UI in Qt and core in VS?
3. What are the (portable) alternatives to ppl?
You may want to consider Intel's Thread Building Blocks. Unlike OpenMP, TBB actually uses C++, rather than simply compiling under a C++ compiler (ie: being a C library that can compile as C++). It has many of the things you see in PPL, but it is cross-platform.
There is also Boost.Thread, which is C++ (though not quite as direct as TBB is), and it is cross-platform.
The people working on the Casablanca project have been making a portable version of PPL, called PPLX. It's licensed under an Apache 2.0 license.
They previously have said they are working closely together with the PPL team to keep both versions in sync feature and bugfix wise (see last post in this thread).
Whether you use PPL or TBB (or HPX) ... something very similar is going to be standardised. For instance see: http://www.open-std.org/jtc1/sc22/wg21/docs/papers/2015/n4411.pdf
Am I right in saying that using
parallel_for from ppl makes your code
unportable (by unportable I mean that
it cannot be compiled by other
compiler than the one from MS)
Unportable if you switch the platform itself. May be portable on Windows, if you want to use other compilers. But know that PPL is part of Concurrency Runtime, which is placed in MSVCRT100.DLL, and you need to link to this (or statically link, without needing DLL at runtime). I am not sure how this can be done with other compilers/linkers, but I do believe it is doable.
Am I right in saying that if on later
stage I want to provide UI (done in
Qt) for the application I'm working on
at the momment, using parallel_for in
my code will be an obstruction which
would mean that either I'll replace
parallel_for with some other
(portable) alternative or I won't be
able to do UI in Qt and core in VS
You can write your core-framework in using PPL/VC++, and other GUI counterpart in QT/other-compiler. For this just make a DLL which would use PPL, and your GUI application would use the DLL. I do believe you understand what I mean here. This also reduces burden from your head about portability (on Windows).
What are the (portable) alternatives to ppl?
Many, but I prefer using PPL on Windows/VC++. You may consider using Intel's TBB. OpenMP is troublesome, and doesn't give advantages as compared to TBB/ConcRT
Related
I am a beginner of c++ parallel computing. However, my project requires that I would need to use c++98 (stdlibc++) for it. I search online and it seems most of the tutorials is based on c++11 thread. I noted that boost_thread is an implementation for c++98 but there seems to be much less available tutorial. So I would like to ask what is the best way for me to learn and implement parallel computing for my project.
Eventually, my project would require calculations based on hundreds of cores and computing nodes. Would multi-threading be sufficient or do I have to use Boost_MPI? Thank you.
If you are limited to c++98 that means that you won't have all the thread managing and locking mechanisms as part of the language.
Therefore you will have to implement them by yourself based on available OS APIs.
There are different APIs for Windows and Linux.
Here is an example of C++ wrapper for Linux pthread library.
And this is an example of C++ wrapper for Windows Threads.
So your project won't be portable unless you create (or find somewhere) a class which hides these libraries behind a common interface under which it implements the same logic for Windows and Linux differed by #ifdef WINDOWS / #ifdef LINUX.
Regarding
what is the best way for me to learn and implement parallel computing
for my project.
There is no a correct answer for this. Look for some basic Multi Threading tutorials. Try to implement few simple programs (before you move to a big project) and come back when you face difficulties with more specific questions.
I have heard about boost but never used it so I can't provide any feedback on that. But again, you need to ask specific question. You can provide some specific requirements from your project and ask question based on them.
Anyway dive into boost documentation, you can find there threads related libraries (also pay attention for boost usage license).
I'm not sure the way I'm organising my library is the most elegant way to organise it. I'm mainly concerned about making all the code that I type compile/run for all systems that I'm targeting (keeping it portable), and also keeping it up-to-date for every system.
For example:
I'm not sure using __declspec(dllexport/dllimport) would be used for Mac or Linux. I assume that it's not, but I don't know what the equivalent is for Mac/Linux is. Or another example might be calling specific Operating System functions, which I try to avoid. However, things such as: measuring how long something takes to happen*, in a precise manner, does require me to call OS specific functions.
*as in getting the user's time precisely (down to micro/milli-seconds).
The systems that I am currently (perhaps more in the future) aiming for is Mac, Windows and Linux. But testing that the code compiles (and runs correctly) for every system just seems like a waste of time. As currently, the way I'm proposing to do it, requires me to make a separate project for every system. i.e. I create a Visual Studio Project for Windows, an Xcode project for Mac, and use the command line for Linux or use some other IDE.
Okay, so my main problems with the way I organise things are:
1. Time Consumption, as in creating the projects for all systems and keeping each indiviual project, for each system up-to-date.
2. Knowledge on all IDE's/Compilers that I require to use
Please note, I've never really used* Linux before, I'm thinking about switching. The only problem that I'm concerned about is finding the right tools for me to use with it, and finding the right Distro that would suit me, for what I need. I would really appreciate if someone that is experienced with Linux could guide me, or give me some advice whether to switch or not.
I really like Visual Studio, and it's been my main IDE for quite a while now. I'm just not sure if I want to ditch Visual Studio or not, for Linux; as I don't know if the tools that are available for Linux can do what Visual Studio can or not. What I mean is, it being as user friendly as Visual Studio is. I'm afraid to learn how to use Linux's tools, I'm just not sure if it's worth doing so. Time isn't a major factor on this library, I have plenty of time, I'm fairly young and determined to program as my career in the future.
*I have used it before, but I've never replaced it for Windows.
I am currently hosting all my source code for my project on BitBucket, but at the moment, I only have the RAW code on my repo. There is no project files or any other tool to compile it with, just the code and a readme file. I was thinking of using Makefiles, since they seem popular. But I've never made a Makefile before, don't get me wrong, I am willing to learn. I'm just not really sure where to start. I've heard that people use CMake to create portable libraries, such as SFML and Ogre3D. I've built a couple of libraries with CMake, but I have no clue on how to actually make my own library with it to make my project/make files. Should I learn and incorporate CMake with my library, or is there a better option available?
EDIT:
I'm not aiming to write a library for actual Software that uses a GUI. I'm mainly aimed to write games.
1 - Boost. Boost will help your portability more than you can imagine. Its only real sticking point is, believe it or not, OS X.
2 - Use CMake. It integrates with Visual Studio project files as the build tool, and you can put most of your different-platform compilation voodoo in there.
3 - If you're seriously writing a portable library, consider writing it in C/writing a C wrapper, or making it header-only, or providing the source-code. Making it a shared or statically linkable library does not mean that it will play nice. Name mangling leads to inconsistencies that will blow your mind.
4 - Always be explicit about the number of bits in each variable.
5 - use git. It'll allow you to setup a crappy local server for a repository very easy and get very fast transfers of the kind of huge changes MSVC will make annoyingly
There are a lot more best-practices that can be discussed about cross-platform development. All of that advice isn't applicable in every case; I have a very code-heavy Linux/Windows library that I code almost exclusively in MSVC2k10 and mostly build/test for in Linux, and it is nowhere close to header-only.
EDIT in response to comments:
git was suggested because I find it very easy to use and manage locally. I've use svn before and liked it, I won't really endorse any others, but there are probably plenty of fine ones.
To expound on point 3,
A C wrapper would make it so that anyone anywhere could use your library - FORTRAN developers, Ruby, even Java.
Otherwise you generally have to have similar compiler versions to link properly and it will only link to other C++ code, outside the case of DLLs, and there are still versioning issues. It's one of the stupidest problems in C++ left over, check "name mangling" on Wikipedia. There is a reason widely-used libraries are written in C or have C wrappers, such as libz, openssl etc.
There are other advantages to it. Exception propagation across dynamic libraries is non-existent; with static libraries it can be inconsistent or non-existent.
You'll find that the most widely-used C++ libraries are mostly header-only, like Boost. A header-only library solves many problems by putting all the code directly into a project in a relatively intuitive way, and modern compilers can still optimize away much (but certainly not all) of the extra compile time associated with it.
With all this said, it is certainly possible to do without a C wrapper or header-only, it is just annoying and very troublesome. DLL hell and its Linux equivalents still exist.
You also asked about Boost. That depends. If you're distributing the sourcecode then you certainly must distribute Boost with your code/have people install it. Having people install libraries in order to compile other libraries or use programs is common practice. Think of how specific versions of DirectX come with games for an example.
However if you are distributing binary versions of your library, statically linking against Boost will eliminate any need to include it as long as you are careful to keep Boost headers out of the outward-facing parts of your library. This is where you start seeing things like void * pointers inside C++ headers; an unfortunate side-effect of some of the shortcomings of C++ compilation and library distribution unfortunately.
CMake is a good choice. You can learn to use it. Read a tutorial:
http://www.cmake.org/cmake/help/cmake_tutorial.html
But, if your targets are Linux and Windows only. It is probably OK, in your case (small/average first multi-platform project), to maintain 2 separate build systems.
On Linux, Use Make. It is standard and has a very good reference manual:
http://www.gnu.org/software/make/manual/make.html
On Windows. Use your IDE project file, be it Visual, DevC++ or other. That is the simplest way to go.
Most important, make it easy to test your library/software on different platforms. Install a virtual machine on your desktop. Or at least compile your library into Cygwin.
Once you are here come back on stackoverflow and we will help !
Personally I'd leverage a framework like Qt, because it is quite portable, it does abstract a lot of OS functionality (files, timing, threads, networking), and you get a decent, free IDE (Qt Creator) that is also portable and runs on Windows, OS X and any Unix flavor that runs Qt. It'd give you the lowest barrier to entry. Qt Creator can leverage the Visual Studio compiler and the CDB debugger if they are available.
You do not need to use OpenGL to use Qt, in fact you're not bound to any particular graphics subsystem. Qt only "uses" OpenGL in Qt 5 for the Qt Quick 2 graphics backend. It's not needed for Qt 4, nor for Qt Quick 1 (even in Qt 5!).
You can use any 2D or 3D framework you fancy to push images and other content to the screen. What Qt is good at is creating the kind of 2D imagery that is often needed in games - menus, configuration screens, HUDs, etc. There's a lot of controls and drawing primitives that Qt makes easy to leverage for your purposes.
Qt also lets you use a reasonably powerful model-view and networking frameworks, thus you'd be able to reasonably easily generate server or client lists that update in real time.
There'd need to be a small amount of shim code between Qt and DirectX, of course. On the output side, you typically end up with a QImage in Qt, and then use DirectX, SDL, OpenGL, etc. to push it to the screen. On the input side, you need to call qApp->processEvents() within your main game loop, and you will need to post user input events from DirectX etc. to Qt's event queue using qApp->postEvent(...). This would be only needed if, say, DirectX main loop consumes all Windows messages and won't let standard winapi/win32 code (Qt's windows event dispatcher) see them. I haven't deal with DirectX much, so others feel free to chime in with details, of course.
With the advent of threading facilities in the STL for the new C++ standard (C++0x), will it be better to change existing code that is using POSIX threading or even Windows threading to use STL threading?
You could always hedge your bets... write your own simple threading API that is just featureful enough to do what your application needs to be done, and change your code to target your threading API only. Then you can implement the internals of your custom threading API using Windows or Posix or STL or whatever, and change the implementation whenever you need to without having to touch your entire codebase each time.
By doing it that way, you could start with the STL implementation, and then if it turns out that e.g. Windows has a difficult-to-resolve problem using that, you could just include an alternate Windows-API implementation inside my_threading_api.cpp (inside of an #ifdef WIN32) and you'd be back in business.
A great deal will depend on how much you care about portability, and how much you're taking advantage of features your native API may provide that the standard library doesn't. The standard library threading is sufficiently similar to POSIX that (at least offhand) I can't think of much you'd gain by staying with POSIX (and due to the similarity, porting to use the standard library should usually be pretty easy).
Windows threading is enough different that you're more likely to run into something that will be non-trivial to port to using the standard library, and even at best porting will probably be non-trivial.
Don't change unless you really need it. I assume that your existing code is working well.
There's no telling how long it will be before the C++0x library features are commonly supported, so the answer might well depend on how tied to a particular compiler you might want to be.
You might also want to consider a framework or library that works on top of the native or C++0x library implementation, such as Boost Threads or the Intel Threading Building Blocks and let that library handle the details of whether it's using C++0x features or platform APIs.
It depends.
C++0x threading isn't widely supported yet (I think GCC implements it, but MSVC doesn't, and I don't know when they're planning to add that support, but I might suspect they consider it a low priority feature)
If your code works as it is, why change it?
For new C++ applications, and assuming compiler support, I'd go with C++0x threads, simply because they're standard, and it's a much nicer API than either Win32 or POSIX threads.
I have a C# prototype that is heavily data parallel, and I've had extremely successful order of magnitude speed ups using the Parallel.For construct in .NETv4. Now I need to write the program in native code, and I'm wondering what my options are. I would prefer something somewhat portable across various operating systems and compilers, but if push comes to shove, I can go with something Windows/VC++.
I've looked at OpenMP, which looks interesting, but I have no idea whether this is looked upon as a good solution by other programmers. I'd also love suggestions for other portable libraries I can look at.
If you're happy with the level of parallelism you're getting from Parallel.For, OpenMP is probably a pretty good solution for you -- it does roughly the same kinds of things. There's also work and research being done on parallelized implementations of the algorithms in the standard library. Code that uses the standard algorithms heavily can gain from this with even less work.
Some of this is done using OpenMP, while other is using hand-written code to (attempt to) provide greater benefits. In the long term, we'll probably see more of the latter, but for now, the OpenMP route is probably a bit more practical.
If you're using Parallel.For in .Net 4.0, you should also look at the Parallel Pattern Library in VS2010 for C++; many things are similar and it is library based.
If you need to run on another platform besides Windows the PPL is also implemented in Intel's Thread Building Blocks which has an open source version.
Regarding the other comment on similarities / differences vs. .Net 4.0, the parallel loops in the PPL (parallel_for, parallel_for_each, parallel_invoke) are virtually identical to the .Net 4.0 loops. The task model is slightly different, but should be straightforward.
You should check out Intel's Thread Building Blocks. Visual Studio 2010 also offers a Concurrency Runtime native. The .NET 4.0 libraries and the ConcRT are designed very similarly, if not identically.
if you want something that is versatile, as in portable across various OS and environments, it would be very difficult to not to consider Java. And they are very similar to C# so it be a very easy transition.
Unless you want to pull out your ninja scalpel and wanting to make your code extremely efficient, I would say java over VC++ or C++.
Been doing mostly Java and smattering of .NET for last five years and haven't written any significant C or C++ during that time. So have been away from that scene for a while.
If I want to write a C or C++ program today that does some multi-threading and is source code portable across Windows, Mac OS X, and Linux/Unix - is PThread a good choice?
The C or C++ code won't be doing any GUI, so won't need to worry with any of that.
For the Windows platform, I don't want to bring a lot of Unix baggage, though, in terms of unix emulation runtime libraries. Would prefer a PThread API for Windows that is a thin-as-possible wrapper over existing Windows threading APIs.
ADDENDUM EDIT:
Am leaning toward going with
boost:thread - I also want to be able
to use C++ try/catch exception
handling too. And even though my
program will be rather minimal and not
particularly OOPish, I like to
encapsulate using class and namespace
- as opposed to C disembodied functions.
Well, pthreads is the old posix standard for writing threaded programs. Its the lowest level threading routines, so its a good choice for cross-platform threading.
However, there are alternatives:
boost::thread - an STL style
threading library
Intel's Thread
Building Blocks
OpenMP -
both these are a higher-level way of
writing threaded apps without needing
to do any threading calls.
As the latter are all fully supported on all platforms, (pthreads requires a bit of compiler settings as its only part of Windows posix subsystem, unless you want to use Pthreads-w32), then perhaps the latter ones are a better choice. boost::threads are more like a threading library, the other 2 are high-level ways of achieving parallelism without needing to code 'threads', they allow you to write loops that run concurrently automatically (subject to common-sense conditions)
Boost::thread is not a C compatible library though.
edit: cross-platform abilities of the above:
Intel TBB is cross-platform (Windows*,
Linux*, and Mac OS* X), supports
32-bit and 64-bit applications and
works with Intel, Microsoft and GNU
compilers.
OpenMP depends on the compiler you want to use, but GCC and/or Intel compilers have supported OpenMP Windows, Linux and MacOS.
If you need your code to be truly portable then it may be best to stay away from the various libraries that scatter the internet. At some point you'll find a platform they don't support and will then have to create your own branch.
This is also not a hard problem to solve and can be a good exercise for creating cross-platform code.
I'd suggest you create a class, e.g. CThread, that has separate .cpp implementations for each platform and a pure-virtual execute() function that is called after your thread is constructed/run.
That allows all of your thread-creation and sleep/shutdown/priority code to be implemented using the most appropriate API for the platform. You may also need a header (e.g. ThreadTypes.h) that contains defines/typedefs for each platform.
E.g.
// ThreadTypes.h
#if defined(PLATFORM_WIN) || defined(PLATFORM_XBOX)
typedef DWORD ThreadID
#elif defined(PLATFORM_PS3)
// etc etc
#endif
This is how I have written all my cross-platform threading code for platforms such as PC/PS2/PS3/360/Wii. It is also a good pattern to follow for things like mutex's and semaphores, which if you have threads you're certain to need at some point :)
Nope, pthreads aren't normally available on Windows. (There are a few attempts at implementing it, but it's not supported by the OS directly, at least.)
If you're writing C++, Boost is, as usual, the answer. Boost.Thread has a portable (and safer) threading library.
In C, the simplest solution is probably to wrap write a common wrapper for both pthreads and the Windows threading API.
I will bet on ZThread
Simple API, easier to use than PThreads and FREE
Have a look at ting also:
http://code.google.com/p/ting/
It is cross platform between Windows and Linux. No Mac OS support yet.