From 70f1522fa18e18a8599f68752b58aca46b4ad240 Mon Sep 17 00:00:00 2001 From: fedepell Date: Fri, 21 Dec 2018 06:16:08 +0100 Subject: [PATCH] protoc: handle extra taskgen and out of project include directories --- .../protoc/increcurse/increc/message.proto | 2 ++ playground/protoc/increcurse/wscript | 4 ++- .../othermod/deep/inc/message_inc_tl.proto | 11 +++++++ waflib/extras/protoc.py | 33 ++++++++++++++++--- 4 files changed, 45 insertions(+), 5 deletions(-) create mode 100644 playground/protoc/othermod/deep/inc/message_inc_tl.proto diff --git a/playground/protoc/increcurse/increc/message.proto b/playground/protoc/increcurse/increc/message.proto index 4dbfd1a2..f65198dc 100644 --- a/playground/protoc/increcurse/increc/message.proto +++ b/playground/protoc/increcurse/increc/message.proto @@ -1,6 +1,7 @@ package udp.tc.tests; import "message_inc.proto"; +import "message_inc_tl.proto"; option java_package ="com.udp.tc.tests"; option java_outer_classname= "MessageProtos"; @@ -12,4 +13,5 @@ message Message { required int32 test = 1; optional uint32 blah = 2; required IncludeMe custom = 3; + required IncludeMeFromTop customfromtop = 4; } diff --git a/playground/protoc/increcurse/wscript b/playground/protoc/increcurse/wscript index 226009a7..d94d5c65 100644 --- a/playground/protoc/increcurse/wscript +++ b/playground/protoc/increcurse/wscript @@ -6,4 +6,6 @@ def build(bld): features = 'py', name = 'pbpyrec', source = ['increc/message.proto'], - protoc_includes = ['increc']) + protoc_includes = ['increc', 'othermod/deep/inc'], + protoc_extincludes = ['/usr/include/pblib', '/usr/share/protos'] + ) diff --git a/playground/protoc/othermod/deep/inc/message_inc_tl.proto b/playground/protoc/othermod/deep/inc/message_inc_tl.proto new file mode 100644 index 00000000..6a17dac2 --- /dev/null +++ b/playground/protoc/othermod/deep/inc/message_inc_tl.proto @@ -0,0 +1,11 @@ +package udp.tc.tests; + +option java_package = "com.udp.tc.tests"; +option java_outer_classname = "MessageInc"; +option cc_generic_services = false; +option java_generic_services = false; +option py_generic_services = false; + +message IncludeMeFromTop { + required int32 testext = 1; +} diff --git a/waflib/extras/protoc.py b/waflib/extras/protoc.py index a367f4f3..3d410218 100644 --- a/waflib/extras/protoc.py +++ b/waflib/extras/protoc.py @@ -67,6 +67,13 @@ Example for Java: protoc_includes = ['inc']) # for protoc to search dependencies +Protoc includes passed via protoc_includes are either relative to the taskgen +or to the project and are searched in this order. + +Include directories external to the waf project can also be passed to the +extra by using protoc_extincludes + + protoc_extincludes = ['/usr/include/pblib'] Notes when using this tool: @@ -82,7 +89,7 @@ Notes when using this tool: """ class protoc(Task): - run_str = '${PROTOC} ${PROTOC_FL:PROTOC_FLAGS} ${PROTOC_ST:INCPATHS} ${PROTOC_ST:PROTOC_INCPATHS} ${SRC[0].bldpath()}' + run_str = '${PROTOC} ${PROTOC_FL:PROTOC_FLAGS} ${PROTOC_ST:INCPATHS} ${PROTOC_ST:PROTOC_INCPATHS} ${PROTOC_ST:PROTOC_EXTINCPATHS} ${SRC[0].bldpath()}' color = 'BLUE' ext_out = ['.h', 'pb.cc', '.py', '.java'] def scan(self): @@ -104,7 +111,17 @@ class protoc(Task): if 'py' in self.generator.features or 'javac' in self.generator.features: for incpath in getattr(self.generator, 'protoc_includes', []): - search_nodes.append(self.generator.path.find_node(incpath)) + incpath_node = self.generator.path.find_node(incpath) + if incpath_node: + search_nodes.append(incpath_node) + else: + # Check if relative to top-level for extra tg dependencies + incpath_node = self.generator.bld.path.find_node(incpath) + if incpath_node: + search_nodes.append(incpath_node) + else: + raise Errors.WafError('protoc: include path %r does not exist' % incpath) + def parse_node(node): if node in seen: @@ -126,7 +143,7 @@ class protoc(Task): parse_node(node) # Add also dependencies path to INCPATHS so protoc will find the included file for deppath in nodes: - self.env.append_value('INCPATHS', deppath.parent.bldpath()) + self.env.append_unique('INCPATHS', deppath.parent.bldpath()) return (nodes, names) @extension('.proto') @@ -223,10 +240,18 @@ def process_protoc(self, node): if incpath_node: incdirs.append(incpath_node.bldpath()) else: - raise Errors.WafError('protoc: include path %r does not exist' % incpath) + # Check if relative to top-level for extra tg dependencies + incpath_node = self.bld.path.find_node(incpath) + if incpath_node: + incdirs.append(incpath_node.bldpath()) + else: + raise Errors.WafError('protoc: include path %r does not exist' % incpath) tsk.env.PROTOC_INCPATHS = incdirs + # Include paths external to the waf project (ie. shared pb repositories) + tsk.env.PROTOC_EXTINCPATHS = getattr(self, 'protoc_extincludes', []) + # PR2115: protoc generates output of .proto files in nested # directories by canonicalizing paths. To avoid this we have to pass # as first include the full directory file of the .proto file