blob: 98b8c66937b598a27fdf79fa1e938a76a8489276 [file] [log] [blame]
// Copyright (C) 2014 BMW Group
// Author: Lutz Bichler (lutz.bichler@bmw.de)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
#include <chrono>
#include <condition_variable>
#include <iomanip>
#include <iostream>
#include <sstream>
#include <thread>
#include <vsomeip/vsomeip.hpp>
#include "sample-ids.hpp"
class service_sample {
public:
service_sample(bool _use_tcp)
: app_(vsomeip::runtime::get()->create_application()),
is_registered_(false),
use_tcp_(_use_tcp),
offer_thread_(std::bind(&service_sample::run, this)),
notification_thread_(std::bind(&service_sample::notify, this)) {
}
void init() {
std::lock_guard < std::mutex > its_lock(mutex_);
app_->init();
app_->register_message_handler(
SAMPLE_SERVICE_ID, SAMPLE_INSTANCE_ID, SAMPLE_METHOD_ID,
std::bind(&service_sample::on_message, this, std::placeholders::_1));
app_->register_event_handler(
std::bind(&service_sample::on_event, this, std::placeholders::_1));
blocked_ = true;
condition_.notify_one();
}
void start() {
app_->start();
}
void offer() {
VSOMEIP_INFO << "Offering service.";
//std::lock_guard < std::mutex > its_lock(notification_mutex_);
app_->offer_service(SAMPLE_SERVICE_ID, SAMPLE_INSTANCE_ID);
notification_blocked_ = true;
//condition_.notify_one();
}
void stop_offer() {
VSOMEIP_INFO << "Stop offering service.";
app_->stop_offer_service(SAMPLE_SERVICE_ID, SAMPLE_INSTANCE_ID);
notification_blocked_ = false;
}
void update() {
static std::shared_ptr<vsomeip::payload> its_payload =
vsomeip::runtime::get()->create_payload();
static vsomeip::byte_t its_data[1000];
static uint32_t its_size = 0;
its_size++;
for (uint32_t i = 0; i < its_size; ++i)
its_data[i] = (i % 256);
its_payload->set_data(its_data, its_size);
VSOMEIP_INFO << "Updating event to " << its_size << " bytes.";
app_->set(SAMPLE_SERVICE_ID, SAMPLE_INSTANCE_ID, SAMPLE_EVENT_ID,
its_payload);
}
void on_event(vsomeip::event_type_e _event) {
VSOMEIP_INFO << "Application " << app_->get_name() << " is "
<< (_event == vsomeip::event_type_e::REGISTERED ?
"registered." : "deregistered.");
if (_event == vsomeip::event_type_e::REGISTERED) {
if (!is_registered_) {
is_registered_ = true;
}
} else {
is_registered_ = false;
}
}
void on_message(std::shared_ptr<vsomeip::message> &_request) {
VSOMEIP_INFO << "Received a message with Client/Session [" << std::setw(4)
<< std::setfill('0') << std::hex << _request->get_client() << "/"
<< std::setw(4) << std::setfill('0') << std::hex
<< _request->get_session() << "]";
std::shared_ptr<vsomeip::message> its_response = vsomeip::runtime::get()
->create_response(_request);
std::shared_ptr<vsomeip::payload> its_payload = vsomeip::runtime::get()
->create_payload();
std::vector<vsomeip::byte_t> its_payload_data;
for (std::size_t i = 0; i < 120; ++i)
its_payload_data.push_back(i % 256);
its_payload->set_data(its_payload_data);
its_response->set_payload(its_payload);
app_->send(its_response, true, use_tcp_);
}
void run() {
std::unique_lock < std::mutex > its_lock(mutex_);
while (!blocked_)
condition_.wait(its_lock);
bool is_offer(true);
while (true) {
if (is_offer)
offer();
else
stop_offer();
std::this_thread::sleep_for(std::chrono::milliseconds(10000));
is_offer = !is_offer;
}
}
void notify() {
while (true) {
//std::unique_lock < std::mutex > its_lock(notification_mutex_);
//while (!notification_blocked_)
// notification_condition_.wait(its_lock);
//while (notification_blocked_) {
std::this_thread::sleep_for(std::chrono::milliseconds(500));
if (notification_blocked_) update();
//}
}
}
private:
std::shared_ptr<vsomeip::application> app_;
bool is_registered_;
bool use_tcp_;
std::thread offer_thread_;
std::mutex mutex_;
std::condition_variable condition_;
bool blocked_;
std::thread notification_thread_;
std::mutex notification_mutex_;
std::condition_variable notification_condition_;
bool notification_blocked_;
};
int main(int argc, char **argv) {
bool use_tcp = false;
std::string tcp_enable("--tcp");
std::string udp_enable("--udp");
for (int i = 1; i < argc; i++) {
if (tcp_enable == argv[i]) {
use_tcp = true;
break;
}
if (udp_enable == argv[i]) {
use_tcp = false;
break;
}
}
service_sample its_sample(use_tcp);
its_sample.init();
its_sample.start();
return 0;
}