操作系统:Windows 10
代码分析工具:Scientific.Toolworks.Understand.5.0
这篇是接着上一篇的,但是没有必然联系,上一篇地址:
https://mp.csdn.net/postedit/80779696
(1)Control_Thread
在control_thread.cc的controlThread这个类名上右键选择Cluster Callby,则出现该类的成员方法以及外部调用关系:
![](https://i-blog.csdnimg.cn/blog_migrate/12f03d3cea99e02779d0836ea260f09e.png)
注:在分析的时候,建议将utils/front-end-cal下的main.cc从工程移除,不然它会和主main.cc混淆。
在ControlThread类的init中:
void ControlThread::init()
{// Instantiates a control queue, a GNSS flowgraph, and a control message factory
control_queue_ = gr::msg_queue::make(0);
flowgraph_ = std::make_shared<GNSSFlowgraph>(configuration_, control_queue_);
control_message_factory_ = std::make_shared<ControlMessageFactory>();
...
}
这几句这工具分析不出来,我们可以知道,最重要的就是它实例化了一个GNSSFlowgraph。
![](https://i-blog.csdnimg.cn/blog_migrate/c1bdcb9aede728f8b70f34737f97747e.png)
将主线无关的东西隐去,可以得到:
这个GNSSBlockFactory是整个程序非常重要的一个类,单独解说。
(2)GNSSBlockFactory
之所以称之为Factory,是继承自GNURadio的说法,在这里批量制造模块。
它的构造函数是空的,里面一堆的东西都是为信号处理模块服务的。
其中最重要的函数是GetBlock:
std::unique_ptr<GNSSBlockInterface> GNSSBlockFactory::GetBlock(
std::shared_ptr<ConfigurationInterface> configuration,
std::string role,
std::string implementation, unsigned int in_streams,
unsigned int out_streams, gr::msg_queue::sptr queue)
{
std::unique_ptr<GNSSBlockInterface> block
...}
调用GetBlock的时候,其实是将配置文件里的implementation与已定义的算法模块名称逐个比较,如果有匹配项,则创建模块对象:
else if (implementation.compare("GPS_L1_CA_PCPS_Acquisition") == 0)
{
std::unique_ptr<GNSSBlockInterface> block_(new GpsL1CaPcpsAcquisition(configuration.get(), role, in_streams,
out_streams));
block = std::move(block_);
}
而三个特殊函数:GetAcqBlock、GetTrkBlock、GetTlmBlock,其实也是各做了一部分事情,就是比较implementation与Acq、Trk、Tlm模块名是否一致,一致则创建模块实例。
而谁来调用它呢?GetChannel_XX,事实上每个GetChannel_XX函数都调用了一遍这几个函数,最后return了一个channel对象:
std::unique_ptr<GNSSBlockInterface> pass_through_ = GetBlock(config, "Channel", "Pass_Through", 1, 1, queue);
std::unique_ptr<AcquisitionInterface> acq_ = GetAcqBlock(configuration, "Acquisition_1C" + appendix1, acq, 1, 0);
std::unique_ptr<TrackingInterface> trk_ = GetTrkBlock(configuration, "Tracking_1C"+ appendix2, trk, 1, 1);
std::unique_ptr<TelemetryDecoderInterface> tlm_ = GetTlmBlock(configuration, "TelemetryDecoder_1C" + appendix3, tlm, 1, 1);
这几句很关键,第一句GetBlock实现创建block_;
if (implementation.compare("Pass_Through") == 0)
{std::unique_ptr<GNSSBlockInterface> block_(new Pass_Through(configuration.get(), role, in_streams, out_streams));
block = std::move(block_);
}
第二句GetAcqBlock实现创建block_;
if (implementation.compare("GPS_L1_CA_PCPS_Acquisition") == 0)
{
std::unique_ptr<AcquisitionInterface> block_(new GpsL1CaPcpsAcquisition(configuration.get(), role, in_streams,
out_streams));
block = std::move(block_);
}
第三、四句类似。
那么问题来了,这个GetChannel_XX是哪里调用的呢?这里:
GetChannels(),它又是哪里调用的呢?事实上是GNSSFlowgraph的init调用的
通过对象block_factory_调用了几乎所有的成员函数,当然,GetChannel_XX是通过GetChannels调用的。