diff --git a/src/media/audio/audiorecorder.cpp b/src/media/audio/audiorecorder.cpp
index 06ec53e3408ced93f9a5c2417e25f108c5998531..2058d55862bf233deb5fb6a91c537b5c9304f568 100644
--- a/src/media/audio/audiorecorder.cpp
+++ b/src/media/audio/audiorecorder.cpp
@@ -2,6 +2,7 @@
  *  Copyright (C) 2004-2015 Savoir-faire Linux Inc.
  *
  *  Author: Alexandre Savard <alexandre.savard@savoirfairelinux.com>
+ *  Author: Guillaume Roguez <guillaume.roguez@savoirfairelinux.com>
  *
  *  This program is free software; you can redistribute it and/or modify
  *  it under the terms of the GNU General Public License as published by
@@ -21,74 +22,70 @@
 #include "audiorecorder.h"
 #include "audiorecord.h"
 #include "ringbufferpool.h"
-#include "logger.h"
+#include "audiobuffer.h"
 
 #include <chrono>
+#include <thread>
 #include <sstream>
-#include <unistd.h>
+#include <algorithm> // std::min
 
 namespace ring {
 
-int AudioRecorder::count_ = 0;
-
-AudioRecorder::AudioRecorder(AudioRecord  *arec, RingBufferPool &rbp)
-    : recorderId_(), ringBufferPool_(rbp), arecord_(arec), running_(false)
-    , thread_()
+static constexpr std::size_t BUFFER_LENGTH {10000};
+static constexpr std::chrono::milliseconds SLEEP_TIME {20};
+
+AudioRecorder::AudioRecorder(AudioRecord* arec, RingBufferPool& rbp)
+    : ringBufferPool_(rbp)
+    , buffer_(new AudioBuffer(BUFFER_LENGTH, ringBufferPool_.getInternalAudioFormat()))
+    , arecord_(arec)
+    , thread_(
+        [this] { return true; },
+        [this] { process(); },
+        [] {})
 {
-    ++count_;
-
-    std::string id("processid_");
+    std::string id("processd_");
 
     // convert count into string
     std::string s;
     std::ostringstream out;
-    out << count_;
+    out << nextProcessID();
     s = out.str();
 
     recorderId_ = id.append(s);
 }
 
-AudioRecorder::~AudioRecorder()
+unsigned
+AudioRecorder::nextProcessID() noexcept
 {
-    running_ = false;
-
-    if (thread_.joinable())
-        thread_.join();
+    static unsigned id = 0;
+    return ++id;
 }
 
-void AudioRecorder::init() {
-    if (!arecord_->isRecording()) {
+void
+AudioRecorder::init() {
+    if (!arecord_->isRecording())
         arecord_->setSndFormat(ringBufferPool_.getInternalAudioFormat());
-    }
 }
 
-void AudioRecorder::start()
+void
+AudioRecorder::start()
 {
-    if (running_) return;
-    running_ = true;
-    thread_ = std::thread(&AudioRecorder::run, this);
+    if (thread_.isRunning())
+        return;
+    thread_.start();
 }
 
-/**
- * Reimplementation of run()
- */
-void AudioRecorder::run()
+void
+AudioRecorder::process()
 {
-    static const size_t BUFFER_LENGTH = 10000;
-    static const std::chrono::milliseconds SLEEP_TIME(20); // 20 ms
-
-    AudioBuffer buffer(BUFFER_LENGTH, ringBufferPool_.getInternalAudioFormat());
-
-    while (running_) {
-        const size_t availableSamples = ringBufferPool_.availableForGet(recorderId_);
-        buffer.resize(std::min(availableSamples, BUFFER_LENGTH));
-        ringBufferPool_.getData(buffer, recorderId_);
+    auto availableSamples = ringBufferPool_.availableForGet(recorderId_);
+    buffer_->resize(std::min(availableSamples, BUFFER_LENGTH));
+    ringBufferPool_.getData(*buffer_, recorderId_);
 
-        if (availableSamples > 0)
-            arecord_->recData(buffer);
+    if (availableSamples > 0)
+        arecord_->recData(*buffer_);
 
-        std::this_thread::sleep_for(SLEEP_TIME);
-    }
+    std::this_thread::sleep_for(SLEEP_TIME);
 }
 
 } // namespace ring
diff --git a/src/media/audio/audiorecorder.h b/src/media/audio/audiorecorder.h
index 9878ff1d7b4ddfb7411c97e53d2c8f26d067708f..e9688227f630dc59c818bf706406b65eab7db0f0 100644
--- a/src/media/audio/audiorecorder.h
+++ b/src/media/audio/audiorecorder.h
@@ -1,7 +1,8 @@
 /*
  *  Copyright (C) 2004-2015 Savoir-faire Linux Inc.
  *
- *  Alexandre Savard <alexandre.savard@savoirfairelinux.com>
+ *  Author: Alexandre Savard <alexandre.savard@savoirfairelinux.com>
+ *  Author: Guillaume Roguez <guillaume.roguez@savoirfairelinux.com>
  *
  *  This program is free software; you can redistribute it and/or modify
  *  it under the terms of the GNU General Public License as published by
@@ -18,52 +19,49 @@
  *  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301 USA.
  */
 
-#ifndef AUDIORECORDER_H_
-#define AUDIORECORDER_H_
+#pragma once
 
+#include "threadloop.h"
 #include "noncopyable.h"
 
-#include <thread>
-#include <atomic>
 #include <string>
+#include <memory>
 
 namespace ring {
 
 class RingBufferPool;
 class AudioRecord;
+class AudioBuffer;
 
 class AudioRecorder {
+public:
+    AudioRecorder(AudioRecord* arec, RingBufferPool& rbp);
 
-    public:
-        AudioRecorder(AudioRecord  *arec, RingBufferPool &rbp);
-        ~AudioRecorder();
-        std::string getRecorderID() const {
-            return recorderId_;
-        }
+    std::string getRecorderID() const noexcept {
+        return recorderId_;
+    }
 
-        /**
-         * Set the record to the current audio format.
-         * Should be called before start() at least once.
-         */
-        void init();
+    /**
+     * Set the record to the current audio format.
+     * Should be called before start() at least once.
+     */
+    void init();
 
-        /**
-         * Call to start recording.
-         */
-        void start();
+    /**
+     * Call to start recording.
+     */
+    void start();
 
-    private:
-        NON_COPYABLE(AudioRecorder);
-        void run();
+private:
+    NON_COPYABLE(AudioRecorder);
+    static unsigned nextProcessID() noexcept;
+    void process();
 
-        static int count_;
-        std::string recorderId_;
-        RingBufferPool &ringBufferPool_;
-        AudioRecord *arecord_;
-        std::atomic<bool> running_;
-        std::thread thread_;
+    std::string recorderId_;
+    RingBufferPool& ringBufferPool_;
+    std::unique_ptr<AudioBuffer> buffer_;
+    AudioRecord* arecord_;
+    ThreadLoop thread_;
 };
 
 } // namespace ring
-
-#endif