1 /******************************************************************************
2 * Copyright (c) 2011, Michael P. Gerlek (mpg@flaxen.com)
3 *
4 * All rights reserved.
5 *
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following
8 * conditions are met:
9 *
10 *     * Redistributions of source code must retain the above copyright
11 *       notice, this list of conditions and the following disclaimer.
12 *     * Redistributions in binary form must reproduce the above copyright
13 *       notice, this list of conditions and the following disclaimer in
14 *       the documentation and/or other materials provided
15 *       with the distribution.
16 *     * Neither the name of Hobu, Inc. or Flaxen Geo Consulting nor the
17 *       names of its contributors may be used to endorse or promote
18 *       products derived from this software without specific prior
19 *       written permission.
20 *
21 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
22 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
23 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
24 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
25 * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
26 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
27 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
28 * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
29 * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
30 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
31 * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY
32 * OF SUCH DAMAGE.
33 ****************************************************************************/
34 
35 #pragma once
36 
37 #include <pdal/PointTable.hpp>
38 #include <pdal/PointView.hpp>
39 #include <pdal/Options.hpp>
40 #include <pdal/Log.hpp>
41 
42 #include <vector>
43 #include <string>
44 
45 namespace pdal
46 {
47 
48 struct QuickInfo;
49 class Stage;
50 class StageFactory;
51 
52 struct StageCreationOptions
53 {
54     std::string m_filename;
55     std::string m_driver;
56     Stage *m_parent;
57     Options m_options;
58     std::string m_tag;
59 };
60 
61 class PDAL_DLL PipelineManager
62 {
63     FRIEND_TEST(json, tags);
64 public:
65     struct ExecResult
66     {
ExecResultpdal::PipelineManager::ExecResult67         ExecResult() : m_mode(ExecMode::None), m_count(0)
68         {}
ExecResultpdal::PipelineManager::ExecResult69         ExecResult(ExecMode mode, point_count_t count) :
70             m_mode(mode), m_count(count)
71         {}
72 
73         ExecMode m_mode;
74         point_count_t m_count;
75     };
76 
77     PipelineManager(point_count_t streamLimit = 10000);
78     ~PipelineManager();
79 
setProgressFd(int fd)80     void setProgressFd(int fd)
81         { m_progressFd = fd; }
82 
83     void readPipeline(std::istream& input);
84     void readPipeline(const std::string& filename);
85 
86     // Use these to manually add stages into the pipeline manager.
87     Stage& addReader(const std::string& type);
88     Stage& addFilter(const std::string& type);
89     Stage& addWriter(const std::string& type);
90 
91     // These add stages, hook dependencies and set necessary options.
92     // They're preferable to the above as they're more flexible and safer.
93     Stage& makeReader(const std::string& inputFile, std::string driver);
94     Stage& makeReader(const std::string& inputFile, std::string driver,
95         Options options);
96     Stage& makeReader(StageCreationOptions& opts);
97 
98     Stage& makeFilter(const std::string& driver);
99     Stage& makeFilter(const std::string& driver, Options options);
100     Stage& makeFilter(const std::string& driver, Stage& parent);
101     Stage& makeFilter(const std::string& driver, Stage& parent,
102         Options options);
103     Stage& makeFilter(StageCreationOptions& ops);
104 
105     Stage& makeWriter(const std::string& outputFile, std::string driver);
106     Stage& makeWriter(const std::string& outputFile, std::string driver,
107         Options options);
108     Stage& makeWriter(const std::string& outputFile, std::string driver,
109         Stage& parent);
110     Stage& makeWriter(const std::string& outputFile, std::string driver,
111         Stage& parent, Options options);
112     Stage& makeWriter(StageCreationOptions& ops);
113 
114     // Return the first leaf stage of a pipeline, or nullptr if the pipeline
115     // is empty.
getStage() const116     Stage* getStage() const
117     {
118         const auto& llist = leaves();
119         return llist.size() ? llist[0] : nullptr;
120     }
121 
122     // Set the log to be available to stages.
123     void setLog(const LogPtr& log);
124 
125     QuickInfo preview() const;
126     void prepare() const;
127     ExecResult execute(ExecMode mode);
128     point_count_t execute();
129     void executeStream(StreamPointTable& table);
130     void validateStageOptions() const;
131     bool pipelineStreamable() const;
132     bool hasReader() const;
133 
134     // Get the resulting point views.
views() const135     const PointViewSet& views() const
136         { return m_viewSet; }
137 
138     // Get the point table data.
pointTable() const139     PointTableRef pointTable() const
140         { return m_table; }
141 
142     MetadataNode getMetadata() const;
commonOptions()143     Options& commonOptions()
144         { return m_commonOptions; }
stageOptions()145     OptionsMap& stageOptions()
146         { return m_stageOptions; }
147     std::vector<Stage *> roots() const;
148     std::vector<Stage *> leaves() const;
149     void replace(Stage *sOld, Stage *sNew);
150 
stages() const151     const std::vector<Stage *> stages() const
152         { return m_stages; }
153     void destroyStage(Stage *s = nullptr);
154 
155 private:
156     void setOptions(Stage& stage, const Options& addOps);
157     Options stageOptions(Stage& stage);
158 
159     std::unique_ptr<StageFactory> m_factory;
160     std::unique_ptr<SimplePointTable> m_tablePtr;
161     PointTableRef m_table;
162     std::unique_ptr<FixedPointTable> m_streamTablePtr;
163     StreamPointTable& m_streamTable;
164     Options m_commonOptions;
165     OptionsMap m_stageOptions;
166     PointViewSet m_viewSet;
167     std::vector<Stage*> m_stages; // stage observer, never owner
168     int m_progressFd;
169     std::istream *m_input;
170     LogPtr m_log;
171 
172     PipelineManager& operator=(const PipelineManager&); // not implemented
173     PipelineManager(const PipelineManager&); // not implemented
174 };
175 typedef std::unique_ptr<PipelineManager> PipelineManagerPtr;
176 
177 } // namespace pdal
178