Skip to content

Commit

Permalink
working, added readme
Browse files Browse the repository at this point in the history
  • Loading branch information
memsharded committed Apr 26, 2016
1 parent f50c3c5 commit 7c24a69
Show file tree
Hide file tree
Showing 5 changed files with 163 additions and 0 deletions.
4 changes: 4 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -26,3 +26,7 @@
*.exe
*.out
*.app

build/
.idea
*~
14 changes: 14 additions & 0 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
cmake_minimum_required(VERSION 2.8)

project(four_c)

if(EXISTS ${CMAKE_CURRENT_SOURCE_DIR}/build/conanbuildinfo.cmake) #Clion, with conanbuildinfo.cmake in build folder
include(${CMAKE_CURRENT_SOURCE_DIR}/build/conanbuildinfo.cmake)
else()
include(${CMAKE_BINARY_DIR}/conanbuildinfo.cmake) # Not CLion
endif()
conan_basic_setup()

add_compile_options(-std=c++11)
add_executable(timer timer.cpp)
target_link_libraries(timer ${CONAN_LIBS})
100 changes: 100 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,100 @@
# Example how to build a C++ project using Clang (in Linux, Ubuntu), CMake, CLion and Conan

This project is able to build a C++ app that depends on Poco and Boost libraries.
It will use Conan to install both libraries and their transitive dependencies.

Typical linux development uses gcc compiler, and many of the conan packages already have pre-built binaries
for gcc. This guide shows how to built them with Clang.

## Setup

This example has been developed and tested in Ubuntu 14.04

Install Clang compiler:

```bash
$ sudo apt-get install clang-3.6
```

Ensure that you have a CMake > 3.0 version in your path, install it otherwise.

```bash
$ cmake --version
```

Install conan (the simplest way is using python/pip):

```bash
$ pip install conan
```

Make a clone of this project:

```bash
$ git clone https://github.com/memsharded/four-c-example.git
$ cd four-c-example
$ mkdir build && cd build
```

## Installing dependencies with Conan

Typically, the package maintainers in conan creates package binaries for the most used and mainstream platforms, and some package binaries as those for clang in linux might be missing for some packages. Then, the --build option has to be specify to build the package binaries from sources locally.

First, we have to make sure that we are using the Clang compiler, so packages that are being built are built with the right compiler and do not fallback to use the gcc compiler. Some conan packages might be able to check that the correct compiler is being used, and warn otherwise (e.g. if using cmake), but other packages would simply fail to build, like boost, that requires "clang++" to be on the path (there might be other ways to do it with bjam files, but are a bit more complicated and current conan package does not support it):

```bash
//for packages using cmake and unix makefiles
$ export CC=clang-3.6
$ export CXX=clang++-3.6
// For boost to work
$ sudo ln -s /usr/bin/clang++-3.6 /usr/bin/clang++
```

Now we are ready to install all the dependencies. It is retrieving and building Boost, Poco and its
transitive dependencies, like OpenSSL and Zlib, so you might want to go and grab a coffe...

```bash
$ conan install .. -s compiler=clang -s compiler.version=3.6 --build
```

## Building with CMake

Given that we have already defined the environment variables, it is easy to build the project with cmake:

```bash
$ cmake .. -DCMAKE_BUILD_TYPE=Release
$ cmake --build .
$ bin/timer
Callback called after 249 milliseconds.
Callback called after 749 milliseconds.
Callback called after 1250 milliseconds.
Callback called after 1750 milliseconds.
Callback called after 2250 milliseconds.
Callback called after 2750 milliseconds.
true
false
```

## Developing with CLion

There are two ways to launch CLion:
1. If you run the clion.sh launch script within your terminal, then it will get your terminal exported
environment variables, and it will be ready to run

2. If you run clion from a desktop launcher or any other mean, it will not use your environment variables
and then it will typically detect and use the system gcc, which will end in conan raising an error, as the
configuration and dependencies have been set to use clang. To define the correct compiler you can do:
1. Go to Menu->File->Settings->Build, Execution, Deployment->CMake
2. Add to "CMake options": -D CMAKE_C_COMPILER=clang-3.6 -D CMAKE_CXX_COMPILER=clang++-3.6
3. Press OK
4. Go to Menu->Invalidate Cache/Restart, so CLion is able to process it properly


When you are done, you can already use Run menu to build and launch the timer example.


NOTES:

- You can go to the console any time to "conan install" the dependencies you need, or when you change settings
- I am working on a wrapper to launch conan from cmake, which might further ease this process and provide an
improved workflow with CLion
6 changes: 6 additions & 0 deletions conanfile.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
[requires]
Poco/1.6.1@lasote/stable
Boost/1.60.0@memsharded/stable

[generators]
cmake
39 changes: 39 additions & 0 deletions timer.cpp
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
#include "Poco/Timer.h"
#include "Poco/Thread.h"
#include "Poco/Stopwatch.h"

#include <boost/regex.hpp>
#include <string>
#include <iostream>

using Poco::Timer;
using Poco::TimerCallback;
using Poco::Thread;
using Poco::Stopwatch;

class TimerExample{
public:
TimerExample(){ _sw.start();}

void onTimer(Timer& timer){
std::cout << "Callback called after " << _sw.elapsed()/1000 << " milliseconds." << std::endl;
}
private:
Stopwatch _sw;
};

int main(int argc, char** argv){
TimerExample example;
Timer timer(250, 500);
timer.start(TimerCallback<TimerExample>(example, &TimerExample::onTimer));

Thread::sleep(3000);
timer.stop();

std::string s = "[email protected]", s2="bademail";
boost::regex expr{"\\b[a-zA-Z0-9._%-]+@[a-zA-Z0-9.-]+\\.[a-zA-Z]{2,4}\\b"};
std::cout << std::boolalpha << boost::regex_match(s, expr) << '\n';
std::cout << std::boolalpha << boost::regex_match(s2, expr) << '\n';

return 0;
}

0 comments on commit 7c24a69

Please sign in to comment.