Cheetah - SKA - PSS - Prototype Time Domain Search Pipeline
SigProcWriterTest.cpp
1 /*
2  * The MIT License (MIT)
3  *
4  * Copyright (c) 2016 The SKA organisation
5  *
6  * Permission is hereby granted, free of charge, to any person obtaining a copy
7  * of this software and associated documentation files (the "Software"), to deal
8  * in the Software without restriction, including without limitation the rights
9  * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
10  * copies of the Software, and to permit persons to whom the Software is
11  * furnished to do so, subject to the following conditions:
12  *
13  * The above copyright notice and this permission notice shall be included in all
14  * copies or substantial portions of the Software.
15  *
16  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
19  * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20  * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
21  * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
22  * SOFTWARE.
23  */
24 #include "cheetah/sigproc/test/SigProcWriterTest.h"
25 #include "cheetah/sigproc/SigProcWriter.h"
26 #include "cheetah/sigproc/SigProcFileStream.h"
27 #include "cheetah/utils/JulianClock.h"
28 #include "pss/astrotypes/sigproc/FileReader.h"
29 #include "panda/test/TestDir.h"
30 #include <climits>
31 #include <algorithm>
32 #include "unistd.h"
33 
34 
35 namespace ska {
36 namespace cheetah {
37 namespace sigproc {
38 namespace test {
39 
40 
41 SigProcWriterTest::SigProcWriterTest()
42  : ::testing::Test()
43 {
44 }
45 
46 SigProcWriterTest::~SigProcWriterTest()
47 {
48 }
49 
50 void SigProcWriterTest::SetUp()
51 {
52 }
53 
54 void SigProcWriterTest::TearDown()
55 {
56 }
57 
58 TEST_F(SigProcWriterTest, test_write_read)
59 {
60  data::DimensionSize<data::Time> samples(20);
61  pss::astrotypes::units::Quantity<pss::astrotypes::units::Seconds, double> sample_interval(1.0 * pss::astrotypes::units::milliseconds);
62  // create a tmp directoy name
63  for(data::DimensionSize<data::Frequency> i(1); i<data::DimensionSize<data::Frequency>(9046); i+=data::DimensionSize<data::Frequency>(1024)) { // try different channel numbers
64  panda::test::TestDir tmp_dir;
65  ASSERT_NO_THROW(tmp_dir.create());
66  {
67  typename utils::JulianClock::time_point start_time(utils::julian_day(2458179.500000));
68  data::TimeFrequency<Cpu, uint8_t> tf1(samples, i);
69  tf1.start_time(static_cast<typename data::TimeFrequency<Cpu, uint8_t>::TimePointType>(start_time));
70  tf1.sample_interval(sample_interval);
71  data::TimeFrequency<Cpu, uint8_t> tf2(samples, i);
72  tf2.start_time(tf1.end_time() + tf1.sample_interval());
73  tf2.sample_interval(sample_interval);
74  SigProcWriter<> writer(tmp_dir.dir_name());
75  writer << tf1;
76  writer << tf2;
77  } // should flush buffers to OS on leaving scope
78  sync(); // ensure the OS actually writes to disc
79  auto it = boost::filesystem::directory_iterator(tmp_dir.path());
80  ASSERT_FALSE(it == boost::filesystem::directory_iterator());
81  Config config;
82  ASSERT_TRUE(boost::filesystem::exists(it->path()));
83  config.set_sigproc_files(it->path().native());
84  config.set_chunk_samples(3*samples); // should be reduced
85 
86  std::vector<boost::filesystem::path> files;
87  std::copy(it, boost::filesystem::directory_iterator(), std::back_inserter(files));
88  std::sort(files.begin(), files.end());
89  ASSERT_EQ(files.size(), 1);
90 
91  boost::filesystem::path file = files[0];
92  ASSERT_EQ(file.extension().string(), ".fil");
93  ASSERT_EQ(file.stem().string(), std::string("2018_03_02_00:00:00"));
94 
95  SigProcFileStream stream(config);
96  panda::DataManager<SigProcFileStream> chunk_manager(stream);
97  ASSERT_TRUE(stream.process()) << "channels=" << i; // expect to of tried opening a new file (and fail) to find the missing data
98  std::tuple<std::shared_ptr<data::TimeFrequency<Cpu, uint8_t>>> data = chunk_manager.next();
99  ASSERT_EQ(static_cast<std::size_t>(i), std::get<0>(data)->number_of_channels());
100  ASSERT_EQ(2*samples, std::get<0>(data)->number_of_spectra()) << "channel=" << i;
101  }
102 }
103 
104 template<typename NumRep>
105 void write_truncate_test()
106 {
107  data::DimensionSize<data::Time> samples(20);
108  data::DimensionSize<data::Time> samples_2(20);
109  data::DimensionSize<data::Frequency> freq(100);
110  pss::astrotypes::units::Quantity<pss::astrotypes::units::Seconds, double> sample_interval(1.0 * pss::astrotypes::units::milliseconds);
111  typename utils::JulianClock::time_point start_time(utils::julian_day(2458179.500000));
112 
113  panda::test::TestDir tmp_dir;
114  ASSERT_NO_THROW(tmp_dir.create());
115 
116  data::TimeFrequency<Cpu, NumRep> tf1(samples, freq);
117  tf1.start_time(static_cast<typename data::TimeFrequency<Cpu, NumRep>::TimePointType>(start_time));
118  tf1.sample_interval(sample_interval);
119  data::TimeFrequency<Cpu, NumRep> tf2(samples_2, freq);
120  tf2.start_time(tf1.end_time() + tf1.sample_interval());
121  tf2.sample_interval(sample_interval);
122 
123  // Case: chunk > max count
124  WriterConfig config;
125  config.max_count(samples-1);
126  config.dir(tmp_dir.dir_name());
127  SigProcWriter<> writer(config);
128  writer << tf1;
129  writer << tf2;
130  writer.flush();
131  sync(); // ensure the OS actually writes to disc
132 
133  auto it = boost::filesystem::directory_iterator(tmp_dir.path());
134  std::vector<boost::filesystem::path> files;
135  std::copy(it, boost::filesystem::directory_iterator(), std::back_inserter(files));
136  std::sort(files.begin(), files.end());
137  ASSERT_EQ(files.size(), 3);
138 
139  boost::filesystem::path file = files[0];
140  std::cout << "examining file: " << file.string() << "\n";
141  pss::astrotypes::sigproc::FileReader<> reader(file.string());
142  pss::astrotypes::sigproc::Header header1 = reader.header();
143  ASSERT_EQ((std::size_t)reader.dimension<data::Time>(), config.max_count());
144 
145  // examine second file
146  boost::filesystem::path file2 = files[1];
147  std::cout << "examining file: " << file2.string() << "\n";
148  reader.open(file2.string());
149  pss::astrotypes::sigproc::Header header2 = reader.header();
150 
151  ASSERT_EQ(header1, header2);
152  ASSERT_EQ((std::size_t)reader.dimension<data::Time>(), config.max_count());
153  // examine second file
154  boost::filesystem::path file3 = files[2];
155  reader.open(file3.string());
156  pss::astrotypes::sigproc::Header header3 = reader.header();
157 
158  ASSERT_EQ(header1, header3);
159  ASSERT_EQ((std::size_t)reader.dimension<data::Time>(), 2);
160 
161 }
162 
163 TEST_F(SigProcWriterTest, test_write_truncate_uint8_t)
164 {
165  write_truncate_test<uint8_t>();
166 }
167 
168 TEST_F(SigProcWriterTest, test_write_truncate_uint16_t)
169 {
170  write_truncate_test<uint16_t>();
171 }
172 
173 } // namespace test
174 } // namespace sigproc
175 } // namespace cheetah
176 } // namespace ska
Some limits and constants for FLDO.
Definition: Brdz.h:35