From 321d92b043fddb60cd13bffb55dc0d31e8d038d0 Mon Sep 17 00:00:00 2001 From: Andrej Babic Date: Fri, 6 Jul 2018 15:17:14 +0200 Subject: [PATCH] Rename SF to Bernina format --- impl/sf_bernina/BerninaFormat.cpp | 105 ++++++++++++++++++++++++++ impl/sf_bernina/Makefile | 36 +++++++++ impl/sf_bernina/bernina_h5_writer.cpp | 69 +++++++++++++++++ 3 files changed, 210 insertions(+) create mode 100644 impl/sf_bernina/BerninaFormat.cpp create mode 100644 impl/sf_bernina/Makefile create mode 100644 impl/sf_bernina/bernina_h5_writer.cpp diff --git a/impl/sf_bernina/BerninaFormat.cpp b/impl/sf_bernina/BerninaFormat.cpp new file mode 100644 index 0000000..527535b --- /dev/null +++ b/impl/sf_bernina/BerninaFormat.cpp @@ -0,0 +1,105 @@ +#include +#include + +#include "config.hpp" +#include "H5Format.hpp" + +using namespace std; +using s_ptr = shared_ptr; + +class BerninaFormat : public H5Format +{ + shared_ptr> input_value_type = NULL; + shared_ptr> default_values = NULL; + shared_ptr> dataset_move_mapping = NULL; + shared_ptr file_format = NULL; + + public: + ~BerninaFormat(){}; + + BerninaFormat() + { + // Input values definition type. + // Which type should be the parameters you receive over the REST api. + input_value_type.reset( + new unordered_map({ + {"general/created", NX_DATE_TIME}, + {"general/user", NX_CHAR}, + {"general/process", NX_CHAR}, + {"general/instrument", NX_CHAR} + })); + + // Default values used in the file format. + default_values.reset(new std::unordered_map({})); + + // After format has been writen, where to move the raw datasets. + dataset_move_mapping.reset(new std::unordered_map( + { + {config::raw_image_dataset_name, "data/JF4.5M/data"}, + {"pulse_id", "data/JF4.5M/pulse_id"}, + {"frame", "data/JF4.5M/frame"}, + {"is_good_frame", "data/JF4.5M/is_good_frame"}, + {"missing_packets_1", "data/JF4.5M/missing_packets_1"}, + {"missing_packets_2", "data/JF4.5M/missing_packets_2"}, + {"daq_recs", "data/JF4.5M/daq_recs"}, + {"daq_rec", "data/JF4.5M/daq_rec"}, + {"framenum_diff", "data/JF4.5M/framenum_diff"}, + {"pulse_ids", "data/JF4.5M/pulse_ids"}, + {"framenums", "data/JF4.5M/framenums"}, + {"pulse_id_diff", "data/JF4.5M/pulse_id_diff"}, + {"module_number", "data/JF4.5M/module_number"}, + })); + + // Definition of the file format. + file_format.reset( + new h5_parent("", EMPTY_ROOT, { + s_ptr(new h5_group("general", { + s_ptr(new h5_dataset("created", "general/created", NX_DATE_TIME)), + s_ptr(new h5_dataset("user", "general/user", NX_CHAR)), + s_ptr(new h5_dataset("process", "general/process", NX_CHAR)), + s_ptr(new h5_dataset("instrument", "general/instrument", NX_CHAR)), + })), + + s_ptr(new h5_group("data", { + s_ptr(new h5_group("JF4.5M", {})) + })) + })); + } + + const h5_parent& get_format_definition() const override + { + return *file_format; + } + + const unordered_map& get_default_values() const override + { + return *default_values; + } + + void add_calculated_values(unordered_map& values) const override + { + // No calculated values. + } + + void add_input_values(unordered_map& values, + const unordered_map& input_values) const override + { + // Input value mapping is 1:1. + for (const auto& input_value : input_values) { + const auto& name = input_value.first; + const auto& value = input_value.second; + + values[name] = value; + } + } + + const std::unordered_map& get_input_value_type() const override + { + return *input_value_type; + } + + const unordered_map& get_dataset_move_mapping() const override { + return *dataset_move_mapping; + } + +}; diff --git a/impl/sf_bernina/Makefile b/impl/sf_bernina/Makefile new file mode 100644 index 0000000..5600183 --- /dev/null +++ b/impl/sf_bernina/Makefile @@ -0,0 +1,36 @@ +SRC_DIR = . +OBJ_DIR = ./obj +BIN_DIR = ./bin +MKDIR = mkdir -p + +CPP = g++ +CPPFLAGS = -Wall -Wfatal-errors -fPIC -pthread -std=c++11 -I../../src -I${CONDA_PREFIX}/include +LDLIBS = -L../../bin -L${CONDA_PREFIX}/lib -L/usr/lib64 -lcpp_h5_writer -lzmq -lhdf5 -lhdf5_hl -lhdf5_cpp -lhdf5_hl_cpp -lboost_system -lboost_regex -lboost_thread -lpthread +LDLIBS_TEST = -lgtest_main -lgtest + +HEADERS = $(wildcard $(SRC_DIR)/*.hpp) +SRCS = $(wildcard $(SRC_DIR)/*.cpp) +OBJS = $(patsubst $(SRC_DIR)/%.cpp, $(OBJ_DIR)/%.o, $(SRCS)) + +bernina: lib all + +lib: + $(MAKE) -C ../../ lib + +all: build_dirs bernina_h5_writer + +debug: CPPFLAGS += -DDEBUG_OUTPUT -g +debug: bernina + +bernina_h5_writer: $(OBJS) + $(CPP) $(LDFLAGS) -o $(BIN_DIR)/bernina_h5_writer $(OBJS) $(LDLIBS) + +$(OBJ_DIR)/%.o: $(SRC_DIR)/%.cpp + $(CPP) $(CPPFLAGS) $(LDLIBS) -c -o $@ $< + +build_dirs: + $(MKDIR) $(OBJ_DIR) $(BIN_DIR) + +clean: + rm -rf $(OBJ_DIR) $(BIN_DIR) + $(MAKE) -C ../../ clean \ No newline at end of file diff --git a/impl/sf_bernina/bernina_h5_writer.cpp b/impl/sf_bernina/bernina_h5_writer.cpp new file mode 100644 index 0000000..858527a --- /dev/null +++ b/impl/sf_bernina/bernina_h5_writer.cpp @@ -0,0 +1,69 @@ +#include +#include +#include + +#include "config.hpp" +#include "WriterManager.hpp" +#include "ZmqReceiver.hpp" +#include "ProcessManager.hpp" + +#include "BerninaFormat.cpp" + +int main (int argc, char *argv[]) +{ + if (argc != 7) { + cout << endl; + cout << "Usage: sf_cpp_h5_writer [connection_address] [output_file] [n_frames]"; + cout << " [rest_port] [user_id] [bsread_address]" << endl; + cout << "\tconnection_address: Address to connect to the stream (PULL). Example: tcp://127.0.0.1:40000" << endl; + cout << "\toutput_file: Name of the output file." << endl; + cout << "\tn_frames: Number of images to acquire. 0 for infinity (until /stop is called)." << endl; + cout << "\trest_port: Port to start the REST Api on." << endl; + cout << "\tuser_id: uid under which to run the writer. -1 to leave it as it is." << endl; + cout << "\tbsread_address: HTTP address of the bsread REST api." << endl; + cout << endl; + + exit(-1); + } + + string connect_address = string(argv[1]); + string output_file = string(argv[2]); + int n_frames = atoi(argv[3]); + int rest_port = atoi(argv[4]); + int user_id = atoi(argv[5]); + string bsread_rest_address = string(argv[6]); + + if (user_id != -1) { + writer_utils::set_process_id(user_id); + } + + writer_utils::create_destination_folder(output_file); + + BerninaFormat format; + WriterManager manager(format.get_input_value_type(), output_file, n_frames); + + auto header_values = shared_ptr>(new unordered_map { + {"pulse_id", HeaderDataType("uint64")}, + {"frame", HeaderDataType("uint64")}, + {"is_good_frame", HeaderDataType("uint64")}, + {"daq_rec", HeaderDataType("int64")}, + + {"pulse_id_diff", HeaderDataType("int64", 6)}, + {"framenum_diff", HeaderDataType("int64", 6)}, + + {"missing_packets_1", HeaderDataType("uint64", 6)}, + {"missing_packets_2", HeaderDataType("uint64", 6)}, + {"daq_recs", HeaderDataType("uint64", 6)}, + + {"pulse_ids", HeaderDataType("uint64", 6)}, + {"framenums", HeaderDataType("uint64", 6)}, + + {"module_number", HeaderDataType("uint64", 6)} + }); + + ZmqReceiver receiver(connect_address, config::zmq_n_io_threads, config::zmq_receive_timeout, header_values); + + ProcessManager::run_writer(manager, format, receiver, rest_port); + + return 0; +} \ No newline at end of file