Skip to content

Collective Perception Service - Core #251

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Draft
wants to merge 24 commits into
base: master
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
24 commits
Select commit Hold shift + click to select a range
7087481
Add .nedfolders file for use with OMNeT++ IDE
m-wegner Jul 18, 2018
4c27f48
Ignore files autogenerated by OMNeT++ IDE / CDT
m-wegner Jul 18, 2018
b429fff
Let EnvmodPrinter also print TraCI ID
kenog Sep 27, 2018
898e1f3
envmod: add CarIdentityRegistrant for registering a Car without V2X in
hagau Feb 28, 2018
f4c06aa
envmod: add PlainVehicle for envmod
hagau Jul 10, 2018
d9b9ea9
VehicleMiddleware: set stationId to node index
hagau Feb 20, 2019
5859213
CarIdentityRegistrant: add host module to identity
hagau Feb 22, 2019
6e061ae
CarIdentityRegistrant: update signal name
hagau May 3, 2019
c18c5c9
Fix ItsG5BaseService multi-stage initialization
sodevel Sep 28, 2020
9274c2c
Add default CMake build directory to .gitignore
sodevel Sep 28, 2020
0b7d5a7
Add patch for patching vanetza's ASN.1 CPM definitions to use the 32bit
hagau Sep 29, 2020
152b6d3
Automatically patch vanetza CPM definitions when building
hagau Oct 2, 2020
76a470b
Allow for disabling vanetza CPM definition patching
hagau Oct 5, 2020
dd77579
Ignore QT Environment files and Cmdenv Log files of scenario runs
sodevel Jan 8, 2021
e2677e9
Add Clang-Format configuration
sodevel Jan 8, 2021
89c24b2
Update Clang-Format configuration to prevent some unwanted reformatting
sodevel Jan 13, 2021
ad4e4d7
Add support for Compound Module based Services
sodevel Jan 14, 2021
7fa25ef
Update Clang-Format configuration
sodevel Jan 17, 2021
ff31591
Lock EnvironmentModelObject weak_ptr only once
sodevel Feb 6, 2021
2173d89
Use the CAM defined StationID type as key type
sodevel Feb 6, 2021
907aea7
Add getter for CAM's
sodevel Feb 6, 2021
c5f5584
Update Clang-Format configuration
sodevel Feb 6, 2021
9a224f9
Add method to return all stored CAM entries
sodevel Feb 21, 2021
d4d8698
Adapt core to upstream TraCI API changes
sodevel Jun 6, 2022
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
33 changes: 33 additions & 0 deletions .clang-format
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
---
BasedOnStyle: Google
AccessModifierOffset: -4
AlignAfterOpenBracket: AlwaysBreak
AlignEscapedNewlines: DontAlign
AllowShortBlocksOnASingleLine: Empty
AllowShortFunctionsOnASingleLine: InlineOnly
AllowShortIfStatementsOnASingleLine: Never
BreakBeforeBraces: Linux
BreakInheritanceList: AfterColon
BreakConstructorInitializers: AfterColon
ColumnLimit: 160
ConstructorInitializerIndentWidth: 4
ContinuationIndentWidth: 4
IncludeBlocks: Regroup
IncludeCategories:
- Regex: '^".*\.h.?.?"'
Priority: 1
SortPriority: 1
- Regex: '^<.*\.h.?.?>'
Priority: 2
SortPriority: 2
- Regex: '^<.*'
Priority: 3
SortPriority: 3
- Regex: '.*'
Priority: 4
SortPriority: 4
IndentPPDirectives: BeforeHash
IndentWidth: 4
KeepEmptyLinesAtTheStartOfBlocks: true
MaxEmptyLinesToKeep: 2
...
11 changes: 11 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -1,8 +1,19 @@
ansible/*.retry
scenarios/**/*.pyc
scenarios/*/results/*
scenarios/*/.cmdenv-log
scenarios/*/.qtenvrc
scenarios/*/.tkenvrc
src/artery/messages/*_m.cc
src/artery/messages/*_m.h
www/
.vagrant/

# OMNeT++ IDE / Eclipse CDT auto-generated files
.cproject
.oppbuildspec
.project
.settings

# CMake default directories
build/
3 changes: 3 additions & 0 deletions .nedfolders
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
src/artery
src/artery/envmod
src/traci
37 changes: 37 additions & 0 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,43 @@ endif()
set(BUILD_SHARED_LIBS ON CACHE INTERNAL "Cached for propagation to sub-projects with older CMake versions")

check_git_submodule(PATH extern/vanetza REQUIRED_FILES CMakeLists.txt)

option(PATCH_VANETZA_CPM "Patch vanetza CPM definitions" ON)

if (PATCH_VANETZA_CPM)
# patch vanetza CPM definitions to support 32bit objectIDs
execute_process(COMMAND patch --dry-run -p1 -s -i ${PROJECT_SOURCE_DIR}/vanetza_asn1_cpm_32bit-objectID.patch
WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}/extern/vanetza
OUTPUT_FILE /dev/null
RESULT_VARIABLE VANETZA_PATCH_TEST)
if(VANETZA_PATCH_TEST EQUAL 0)
# actually patch vanetza
message(STATUS "patching vanetza CPM definitions")
execute_process(COMMAND patch -p1 -s -i ${PROJECT_SOURCE_DIR}/vanetza_asn1_cpm_32bit-objectID.patch
WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}/extern/vanetza
RESULT_VARIABLE VANETZA_PATCH_SUCCESS)
if(VANETZA_PATCH_SUCCESS EQUAL 0)
message(STATUS "vanetza CPM definitions successfully patched")
elseif()
message(STATUS "patching vanetza CPM definitions failed -- manual intervention necessary")
endif()
else()
execute_process(COMMAND patch --dry-run -R -p1 -s -i ${PROJECT_SOURCE_DIR}/vanetza_asn1_cpm_32bit-objectID.patch
WORKING_DIRECTORY ${PROJECT_SOURCE_DIR}/extern/vanetza
OUTPUT_FILE /dev/null
RESULT_VARIABLE VANETZA_PATCH_TEST_REVERSE)
if(VANETZA_PATCH_TEST_REVERSE EQUAL 0)
# patch already applied
message(STATUS "vanetza CPM definitions patch already applied")
else()
message(STATUS "testing patch integrity by applying vanetza CPM defintions patch in reverse failed -- manual intervention necessary")
endif()
endif()
elseif()
message(STATUS "vanetza CPM patching disabled")
endif()


set(VANETZA_INSTALL ON)
add_subdirectory(${PROJECT_SOURCE_DIR}/extern/vanetza)
mark_as_advanced(BUILD_BENCHMARK BUILD_CERTIFY BUILD_SOCKTAP BUILD_TESTS BUILD_USING_CONAN)
Expand Down
32 changes: 27 additions & 5 deletions src/artery/application/ItsG5BaseService.cc
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@

#include "artery/application/ItsG5Service.h"
#include "artery/application/Middleware.h"
#include "artery/utility/InitStages.h"
#include <inet/common/ModuleAccess.h>
#include <omnetpp/clog.h>
#include <cassert>
Expand Down Expand Up @@ -75,14 +76,35 @@ cModule* ItsG5BaseService::findHost()
return inet::findContainingNode(m_middleware);
}

void ItsG5BaseService::initialize()
int ItsG5BaseService::numInitStages() const
{
Middleware* middleware = dynamic_cast<Middleware*>(getParentModule());
if (middleware == nullptr) {
throw cRuntimeError("Middleware not found");
return (InitStages::Prepare + 1);
}

void ItsG5BaseService::initialize(int stage)
{
if (stage == InitStages::Prepare) {
// If this service is part of a Compound Module the Middleware is its grand parent
auto* parent = getParentModule();
if (!parent->getModuleType()->isSimple()) {
parent = parent->getParentModule();
}
Middleware* middleware = dynamic_cast<Middleware*>(parent);
if (middleware == nullptr) {
throw cRuntimeError("Middleware not found");
}

m_middleware = middleware;
}

m_middleware = middleware;
// To prevent that derived classes need to be aware of the multi-stage initialization of this base class
// call the plain initialize() method at stage 0. This way for these derived classes it is sufficient
// to just override this method if they don't perform multi-stage initialization themself, however if
// they also perform multi-stage initialization they need to take into account the required stages
// of this base class.
if (stage == 0) {
initialize();
}
}

void ItsG5BaseService::finish()
Expand Down
4 changes: 3 additions & 1 deletion src/artery/application/ItsG5BaseService.h
Original file line number Diff line number Diff line change
Expand Up @@ -76,7 +76,9 @@ class ItsG5BaseService :
const std::set<TransportDescriptor>& getTransportDescriptors() const { return m_listeners; }

protected:
void initialize() override;
int numInitStages() const override;
using omnetpp::cSimpleModule::initialize;
void initialize(int stage) override;
void finish() override;
void request(const vanetza::btp::DataRequestB&, std::unique_ptr<vanetza::DownPacket>, const NetworkInterface* = nullptr);
void indicate(const vanetza::btp::DataIndication&, std::unique_ptr<vanetza::UpPacket>, const NetworkInterface&) override;
Expand Down
9 changes: 4 additions & 5 deletions src/artery/application/LocalDynamicMap.cc
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ void LocalDynamicMap::dropExpired()
{
const auto now = omnetpp::simTime();
for (auto it = mCaMessages.begin(); it != mCaMessages.end();) {
if (it->second.expiry < now) {
if (it->second.expiry() < now) {
it = mCaMessages.erase(it);
} else {
++it;
Expand All @@ -51,14 +51,13 @@ void LocalDynamicMap::dropExpired()
unsigned LocalDynamicMap::count(const CamPredicate& predicate) const
{
return std::count_if(mCaMessages.begin(), mCaMessages.end(),
[&predicate](const std::pair<const StationID, AwarenessEntry>& map_entry) {
const Cam& cam = map_entry.second.object.asn1();
return predicate(cam);
[&predicate](const AwarenessEntries::value_type& map_entry) {
return predicate(map_entry.second.cam());
});
}

LocalDynamicMap::AwarenessEntry::AwarenessEntry(const CaObject& obj, omnetpp::SimTime t) :
expiry(t), object(obj)
mExpiry(t), mObject(obj)
{
}

Expand Down
32 changes: 20 additions & 12 deletions src/artery/application/LocalDynamicMap.h
Original file line number Diff line number Diff line change
Expand Up @@ -4,9 +4,9 @@
#include "artery/application/CaObject.h"
#include <omnetpp/simtime.h>
#include <vanetza/asn1/cam.hpp>
#include <cstdint>
#include <functional>
#include <map>
#include <memory>

namespace artery
{
Expand All @@ -16,28 +16,36 @@ class Timer;
class LocalDynamicMap
{
public:
using StationID = uint32_t;
using Cam = vanetza::asn1::Cam;
using CamPredicate = std::function<bool(const Cam&)>;

LocalDynamicMap(const Timer&);
void updateAwareness(const CaObject&);
void dropExpired();
unsigned count(const CamPredicate&) const;

private:
struct AwarenessEntry
class AwarenessEntry
{
public:
AwarenessEntry(const CaObject&, omnetpp::SimTime);
AwarenessEntry(AwarenessEntry&&) = default;
AwarenessEntry& operator=(AwarenessEntry&&) = default;

omnetpp::SimTime expiry;
CaObject object;
omnetpp::SimTime expiry() const { return mExpiry; }
const Cam& cam() const { return mObject.asn1(); }
std::shared_ptr<const Cam> camPtr() const { return mObject.shared_ptr(); }

private:
omnetpp::SimTime mExpiry;
CaObject mObject;
};

using AwarenessEntries = std::map<StationID_t, AwarenessEntry>;

LocalDynamicMap(const Timer&);
void updateAwareness(const CaObject&);
void dropExpired();
unsigned count(const CamPredicate&) const;
const AwarenessEntries& allEntries() const { return mCaMessages; }

private:
const Timer& mTimer;
std::map<StationID, AwarenessEntry> mCaMessages;
AwarenessEntries mCaMessages;
};

} // namespace artery
Expand Down
15 changes: 14 additions & 1 deletion src/artery/application/Middleware.cc
Original file line number Diff line number Diff line change
Expand Up @@ -110,7 +110,20 @@ void Middleware::initializeServices(int stage)
module->scheduleStart(simTime());
// defer final module initialisation until service is attached to middleware

ItsG5BaseService* service = dynamic_cast<ItsG5BaseService*>(module);
// Like the Simple Module case uses the C++ class to determine if the module does
// implement a service search for the first matching Submodule that implements a service
// in the Compound Module case
ItsG5BaseService* service = nullptr;
if (!module_type->isSimple()) {
for (cModule::SubmoduleIterator it(module); !it.end(); ++it) {
service = dynamic_cast<ItsG5BaseService*>(*it);
if (service) {
break;
}
}
} else {
service = dynamic_cast<ItsG5BaseService*>(module);
}
if (service) {
unsigned ports = 0;
unsigned channels = 0;
Expand Down
9 changes: 8 additions & 1 deletion src/artery/application/VehicleMiddleware.cc
Original file line number Diff line number Diff line change
Expand Up @@ -29,12 +29,19 @@ void VehicleMiddleware::initialize(int stage)
findHost()->subscribe(MobilityBase::stateChangedSignal, this);
initializeVehicleController(par("mobilityModule"));
initializeStationType(mVehicleController->getVehicleClass());

auto path = findHost()->getFullPath();
auto i0 = path.find("[");
auto i1 = path.find("]");
auto stationId = std::stoul(path.substr(i0+1, i1-i0-1));
mVehicleDataProvider.setStationId(stationId);

getFacilities().register_const(&mVehicleDataProvider);
mVehicleDataProvider.update(getKinematics(*mVehicleController));

Identity identity;
identity.traci = mVehicleController->getVehicleId();
identity.application = Identity::randomStationId(getRNG(0));
identity.application = mVehicleDataProvider.getStationId();
mVehicleDataProvider.setStationId(identity.application);
emit(Identity::changeSignal, Identity::ChangeTraCI | Identity::ChangeStationId, &identity);
}
Expand Down
1 change: 1 addition & 0 deletions src/artery/envmod/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
add_artery_feature(envmod
CarIdentityRegistrant.cc
EnvironmentModelObject.cc
GlobalEnvironmentModel.cc
LocalEnvironmentModel.cc
Expand Down
49 changes: 49 additions & 0 deletions src/artery/envmod/CarIdentityRegistrant.cc
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
#include "artery/envmod/CarIdentityRegistrant.h"
#include "artery/utility/IdentityRegistry.h"
#include "artery/traci/VehicleMobility.h"
#include "inet/common/ModuleAccess.h"


namespace artery
{

Define_Module(CarIdentityRegistrant)

void CarIdentityRegistrant::initialize()
{
initializeIdentity();
registerIdentity();
}

void CarIdentityRegistrant::initializeIdentity()
{
auto parent = this->getParentModule();
auto mobility = dynamic_cast<VehicleMobility*>(parent->getSubmodule("mobility", -1));
if (!mobility) {
throw omnetpp::cRuntimeError("no suitable mobility module found");
}
auto controller = mobility->getVehicleController();

auto traciId = controller->getVehicleId();

auto path = parent->getFullPath();
auto i0 = path.find("[");
auto i1 = path.find("]");
auto stationId = std::stoul(path.substr(i0+1, i1-i0-1));

mIdentity.host = parent;
mIdentity.application = stationId;
mIdentity.traci = traciId;
}

void CarIdentityRegistrant::registerIdentity()
{
emit(artery::IdentityRegistry::updateSignal, &mIdentity);
}

void CarIdentityRegistrant::finish()
{
emit(artery::IdentityRegistry::removeSignal, &mIdentity);
}

} // namespace artery
21 changes: 21 additions & 0 deletions src/artery/envmod/CarIdentityRegistrant.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
#include "artery/utility/Identity.h"
#include <omnetpp/csimplemodule.h>


namespace artery
{

class CarIdentityRegistrant : public omnetpp::cSimpleModule
{
protected:
void initialize() override;
void finish() override;

private:
artery::Identity mIdentity;

void initializeIdentity();
void registerIdentity();
};

} // namespace artery
9 changes: 9 additions & 0 deletions src/artery/envmod/CarIdentityRegistrant.ned
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
package artery.envmod;

simple CarIdentityRegistrant
{
parameters:
@class(CarIdentityRegistrant);
@signal[IdentityUpdated](type=artery::Identity);
@signal[IdentityRemoved](type=artery::Identity);
}
18 changes: 18 additions & 0 deletions src/artery/envmod/PlainVehicle.ned
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
package artery.envmod;

import artery.inet.PlainVehicle;
import artery.envmod.CarIdentityRegistrant;

module PlainVehicle extends artery.inet.PlainVehicle
{
parameters:
@display("i=blocki/process;is=vs");
@labels(node);

submodules:
carIdentityRegistrant: CarIdentityRegistrant {
parameters:
@display("p=53,300");
}

}
Loading