-
Notifications
You must be signed in to change notification settings - Fork 3.5k
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
Work on support relations in lua profiles #4438
Conversation
very nice to see work on relation support :-) |
@@ -284,7 +361,7 @@ void Sol2ScriptingEnvironment::InitContext(LuaScriptingContext &context) | |||
"id", | |||
&osmium::Node::id, | |||
"version", | |||
&osmium::Way::version); | |||
&osmium::Node::version); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Good catch!
This version have some problems:
|
Great to see this moving forward! As a first use-case we should pass on cardinal directions from the route relation onto it's containing way members. For now we're good with concatenating the route's cardinal direction (North, South, ..) onto the way's ref property. In future versions (probably v6) we might want to reconsider this and properly split it off into own properties: #3304. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM! Please add some feature tests with test profiles to show how data will look on Lua side.
Argument | Description | ||
---------|------------------------------------------------------- | ||
profile | The configuration table you returned in `setup`. | ||
node | The input relation to process (read-only). |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
node
-> relation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
namespace detail | ||
{ | ||
|
||
inline const char * checkedString(const char * str) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
is it used somewhere? pls remove if will not be used
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
done
include/util/osm_id_typed.hpp
Outdated
namespace util | ||
{ | ||
|
||
class OsmIDTyped |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Just as an alternative you can use union
as
union OsmIDTyped
{
OsmIDTyped(std::uint64_t id, std::uint8_t type) : detail{id, type} {}
std::uint64_t hash;
std::uint64_t GetID() const { return detail.id; }
std::uint8_t GetType() const { return detail.type; }
private:
struct
{
std::uint64_t id : 56;
std::uint8_t type;
} detail;
};
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've think about this. And decide that it's not normal for OSRM (haven't seen union in project). If it good, i can do that.
for (const auto &result : parsed_buffer->resulting_restrictions) | ||
{ | ||
extractor_callbacks->ProcessRestriction(result); | ||
} | ||
}); | ||
|
||
/* Main trick that we can use the same pipeline. It just receive relation objects |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Another trick is to use HOF that returns a function that captures a reader as
Reader reader1, reader2;
auto make_buffer_reader = [](Reader& reader) {
return [&reader]() { reader.bark(); };
};
make_buffer_reader(reader1)();
make_buffer_reader(reader2)();
and use on-stack allocated readers.
So pipelines will be
{
osmium::io::Reader reader(input_file, osmium::osm_entity_bits::relation,...);
tbb::parallel_pipeline(tbb::task_scheduler_init::default_num_threads() * 1.5,
make_buffer_reader(reader) & buffer_transform & buffer_storage_relation);
}
{
osmium::io::Reader reader(input_file, osmium::osm_entity_bits::node | osmium::osm_entity_bits::way,,...);
tbb::parallel_pipeline(tbb::task_scheduler_init::default_num_threads() * 1.5,
make_buffer_reader(reader) & buffer_transform & buffer_storage);
}
It also can be n
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
yeah, that also was an idea. But there are some code that request reader before: ed5e00f#diff-edf14d92e413123a2b940ab0b8491ffbR298
This approach is much cleaner for me. But it can be implemented if we will create another reader to get header info.
osmium::item_type GetItemType() const { return item_type; } | ||
osmium::object_id_type GetId() const { return id; } | ||
|
||
util::OsmIDTyped ref() const { return util::OsmIDTyped(id, std::uint8_t(item_type)); } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
conversion of osmium::item_type to std::uint8_t
must be a hidden in OsmIDTyped
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You talk about store std::uint8_t
instead of osmium::item_type
or something else?
id = member.ref(); | ||
} | ||
|
||
const char* GetRole() const { return role.c_str(); } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
you don't need accessor function with pubic data members , it is better to pass references to sol and set r/o access as sol::readonly( &RelationMemberWrap::role )
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Then it would be a problem:
relation:id() -- used for nodes and ways before
member:role() -- will be similar
-- instead of
member:role
"members", [](const osmium::Relation &rel) | ||
{ | ||
std::vector<RelationMemberWrap> members(rel.members().size()); | ||
size_t i = 0; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
std::copy(...)
of rel.members() to memeber?
@@ -276,6 +288,71 @@ void Sol2ScriptingEnvironment::InitContext(LuaScriptingContext &context) | |||
"version", | |||
&osmium::Way::version); | |||
|
|||
struct RelationMemberWrap |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Why not to expose osmium::RelationMember
directly to avoid copying role strings?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Because it has deleted a lot of constructors and operators. So it doesn't compiles with sol.
I've tried for example:
context.state.new_usertype<osmium::Relation>("Relation",
"get_value_by_key",
&get_value_by_key<osmium::Relation>,
"id",
&osmium::Relation::id,
"version",
&osmium::Relation::version,
"members",
[](const osmium::Relation &rel) {
return sol::as_table(rel.members());
});
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The wrapper can be removed return sol::as_table(rel.members());
should work well
@@ -1 +1 @@ | |||
n1 v1 dV c1 t2014-01-01T00:00:00Z i1 utest T x1.02 y1.02 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This must be reverted
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can't do that until will be fixed in master. It create this one automatically with git on any rebase. So moved it to a separate commit, that will be removed on fixed master
rebase
docs/profiles.md
Outdated
@@ -130,7 +130,7 @@ Attribute | Type | Notes | |||
barrier | Boolean | Is it an impassable barrier? | |||
traffic_lights | Boolean | Is it a traffic light (incurs delay in `process_turn`)? | |||
|
|||
## process_way(profile, way, result) | |||
### process_way(profile, way, result) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
form the code process_way
has the 4th relations
argument but here it is not mentioned
Should it be may be optional ? I feel we need some sort of sync here with location-dependent tags, that I would like to see optional. So we can add an additional positional argument that will hold a table with optional data items.
This will save from bumping api version every time when a new piece of data will be added to lua callback functions.
@oxidase have test features of Or need more and if yes, then where to place them? |
@deniskoronchik test looks good, somehow i missed it during review |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Basic approach LGTM - only one minor comment for the OSMIDTyped class.
@deniskoronchik If you think there's a good reason not to make the type
field an enum, then it's OK to not change it, but please add a code comment describing what the type
field represents.
@deniskoronchik Can you please add an entry to CHANGELOG.md
, then I think this is good to merge.
include/util/osm_id_typed.hpp
Outdated
inline HashType Hash() const { return (std::uint64_t(id) | std::uint64_t(type) << 56); } | ||
|
||
std::uint64_t GetID() const { return id; } | ||
std::uint8_t GetType() const { return type; } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think it would be good to do what osmium does here and make type
an enum. We should have an explicit mapping from the osmium::item_type
enum values to our own internal values.
osmium::item_type GetItemType() const { return item_type; } | ||
osmium::object_id_type GetId() const { return id; } | ||
|
||
util::OsmIDTyped ref() const { return util::OsmIDTyped(id, std::uint8_t(item_type)); } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is the other side to my comment on OsmIDTyped
- I think we should be very explicit about what values we store here. Something like:
switch(item_type) {
case osmium::item_type.node:
return util::OsmIDTyped(id, osrm::extractor::OSMIDType.NODE);
case osmium::item_type.way:
return util::OsmIDTyped(id, osrm::extractor::OSMIDType.WAY);
default:
throw util::exception("some error message");
}
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Note that simply appending onto the ways’ |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM! I still think that most of c++ wrappers can be removed, because sol2 is really great library and can create such wrappers invisible. Also it reduces copying data c++ -> lua -> c++
I can attach a patch or commit later a cleanup
@@ -366,6 +499,45 @@ void Sol2ScriptingEnvironment::InitContext(LuaScriptingContext &context) | |||
sol::property([](const ExtractionWay &way) { return way.backward_restricted; }, | |||
[](ExtractionWay &way, bool flag) { way.backward_restricted = flag; })); | |||
|
|||
struct ExtractionRelationData |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The wrapper is not really needed. sol2 understands lambda return types:
context.state.new_usertype<ExtractionRelation>(
"ExtractionRelation",
sol::meta_function::new_index,
[](ExtractionRelation &rel, const RelationMemberWrap &member) -> ExtractionRelation::AttributesMap& {
return rel.GetMember(member.ref());
},
sol::meta_function::index,
[](ExtractionRelation &rel, const RelationMemberWrap &member) -> ExtractionRelation::AttributesMap& {
return rel.GetMember(member.ref());
},
"restriction",
sol::property([](const ExtractionRelation &rel) { return rel.is_restriction; },
[](ExtractionRelation &rel, bool flag) { rel.is_restriction = flag; }));
below
} | ||
|
||
namespace osrm | ||
{ | ||
namespace extractor | ||
{ | ||
|
||
class RelationsContainerWrap |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The wrapper is not needed and can be removed. Also context.state.new_usertype<RelationsContainerWrap>( ...
can be removed. Relations can be forwarded to lua as
node_function(profile_table, node, result, sol::as_table(relations));
...
way_function(profile_table, way, result, sol::as_table(relations));sol::as_table(relations)
ExtractionRelation::AttributesMap &attrs; | ||
}; | ||
|
||
context.state.new_usertype<RelationsContainerWrap>( |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Not needed
sol::meta_function::index, | ||
[](const RelationsContainerWrap &rel, size_t index) { return rel.GetAttributes(index); }); | ||
|
||
context.state.new_usertype<ExtractionRelationData>( |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
not needed
context.state.new_usertype<ExtractionRelation>( | ||
"ExtractionRelation", | ||
sol::meta_function::new_index, | ||
[](ExtractionRelation &rel, const RelationMemberWrap &member) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
add -> ExtractionRelation::AttributesMap&
return ExtractionRelationData(rel.GetMember(member.ref())); | ||
}, | ||
sol::meta_function::index, | ||
[](ExtractionRelation &rel, const RelationMemberWrap &member) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
add add
-> ExtractionRelation::AttributesMap&``
@@ -276,6 +288,71 @@ void Sol2ScriptingEnvironment::InitContext(LuaScriptingContext &context) | |||
"version", | |||
&osmium::Way::version); | |||
|
|||
struct RelationMemberWrap |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The wrapper can be removed return sol::as_table(rel.members());
should work well
@deniskoronchik @TheMarex i have removed Lua 5.1 support because ThePhD/sol2#302 makes relations wrapping too complicated and requires copying of members for every node/way. ATM windows build failed, because it requires Lua 5.1 -> 5.2 update. |
Pool instance has been removed from Reader ctor parameters list in PR Project-OSRM#4438, presumably unintentionally. It is required to prevent potential deadlock during Pool shutdown as explained in PR Project-OSRM#4452.
Pool instance has been removed from Reader ctor parameters list in PR Project-OSRM#4438, presumably unintentionally. It is required to prevent potential deadlock during Pool shutdown as explained in PR Project-OSRM#4452.
Pool instance has been removed from Reader ctor parameters list in PR Project-OSRM#4438, presumably unintentionally. It is required to prevent potential deadlock during Pool shutdown as explained in PR Project-OSRM#4452.
Issue
#482
Tasklist
process_relation
function into luaprocess_way
andprocess_node