33#include < iostream>
44#include < cstring>
55#include < algorithm>
6-
6+ # include < set >
77#include " operations.h"
8-
8+ # include < iomanip >
99
1010using namespace CppCAN ::can_parse;
1111
@@ -22,63 +22,91 @@ static std::string CHECKFRAME_ACTION = "checkframe";
2222static std::string PRINTFRAME_ACTION = " printframe" ;
2323
2424void showUsage (std::ostream& ostrm, char * program_name) {
25- ostrm << " Usage: " << program_name << " [ACTION] <path/to/file>" << std::endl;
25+ ostrm << " Usage: " << program_name << " [ACTION [ARGUMENTS] ] <path/to/file>" << std::endl;
2626 ostrm << " When no action is specified, defaults to " << PRINTFRAME_ACTION << std::endl;
2727 ostrm << " Possible actions: " << std::endl;
28- ostrm << " \t " << PRINTFRAME_ACTION << " \t Print the content of the CAN database" << std::endl;
29- ostrm << " \t " << CHECKFRAME_ACTION << " \t Check different properties of the CAN database" << std::endl;
28+ ostrm << " \t " << std::left << std::setw (22 ) << (PRINTFRAME_ACTION + " [CAN ID]" ) << " Print the content of the CAN database" << std::endl;
29+ ostrm << " \t " << std::setw (22 ) << " " << " if CAN ID is specified, prints the details of the given frame" << std::endl;
30+ ostrm << " \t " << std::setw (22 ) << (CHECKFRAME_ACTION + " [CAN ID]" ) << " Check different properties of the CAN database" << std::endl;
31+ ostrm << " \t " << std::setw (22 ) << " " << " if CAN ID is specified, print the check details of the given frame" << std::endl;
3032 ostrm << " Currently supported formats: DBC" << std::endl;
3133}
3234
3335
34- std::tuple<CanParseAction, std::string> extractAction (int argc, char ** argv) {
36+ std::tuple<CanParseAction, std::string, uint32_t > extractAction (int argc, char ** argv) {
3537 std::vector<std::string> args (argv + 1 , argv + argc); // +1 so we ignore the executable name
3638
3739 CanParseAction action = None;
3840 std::string src_file;
41+ uint32_t detail_frame = 0 ;
3942
4043 if (args.size () < 1 ) {
4144 throw CppCAN::can_parse::CanParseException (" Not enough arguments" );
4245 }
4346
44- size_t i = 0 ;
47+ std::set<std::string> options;
48+
49+ bool check_action = true ;
50+ bool check_args = false ;
4551 for (const std::string& arg : args) {
4652 // First argument, we check for potential actions
47- if (i++ == 0 ) {
53+ if (arg.size () > 0 && arg[0 ] == ' -' ) {
54+ options.insert (arg);
55+ continue ;
56+ }
57+ else if (check_action) {
4858 if (arg == CHECKFRAME_ACTION) {
4959 action = CheckAll;
60+ check_args = true ;
61+ check_action = false ;
5062 continue ;
5163 }
5264 else if (arg == PRINTFRAME_ACTION) {
5365 action = PrintAll;
66+ check_args = true ;
67+ check_action = false ;
5468 continue ;
5569 }
56- }
57-
58- // Check for options
59- if (arg.size () > 0 && arg[0 ] == ' -' ) {
60- if (arg == " -h" || arg == " --help" ) {
61- action = Help;
70+ else {
71+ action = PrintAll;
72+ check_action = false ;
6273 }
6374 }
64- // This is a file path (for now)
65- else {
66- src_file = arg;
75+ else if (check_args) {
76+ check_args = false ;
77+
78+ try {
79+ detail_frame = std::stoul (arg);
80+ action = static_cast <CanParseAction>(static_cast <int >(action) + 1 );
81+ continue ;
82+ } catch (const std::logic_error& e) {
83+ // The argument is not related ....
84+ // Probably a file name, we stick to PrintAll/CheckAll
85+ }
6786 }
87+
88+ // At this point, nothing has matched. The only valid thing that this could be
89+ // is the file name of the database to parse.
90+ src_file = arg;
91+ }
92+
93+ if (options.count (" -h" ) > 0 || options.count (" --help" )) {
94+ action = Help;
6895 }
6996
7097 if (action != Help && src_file.size () == 0 )
7198 throw CppCAN::can_parse::CanParseException (" No source file specified" );
7299
73- return std::make_tuple (action != None ? action : PrintAll, src_file);
100+ return std::make_tuple (action != None ? action : PrintAll, src_file, detail_frame );
74101}
75102
76103int main (int argc, char ** argv) {
77104 std::string src_file;
78105 CanParseAction action;
106+ uint32_t detail_frame;
79107
80108 try {
81- std::tie (action, src_file) = extractAction (argc, argv);
109+ std::tie (action, src_file, detail_frame ) = extractAction (argc, argv);
82110 }
83111 catch (const CanParseException& e) {
84112 std::cerr << " Invalid use of the program: " << e.what () << std::endl;
@@ -102,6 +130,7 @@ int main(int argc, char** argv) {
102130 return 2 ;
103131 }
104132
133+ std::cout << (detail_frame == 0 ? " Print all" : " Print CAN ID " + std::to_string (detail_frame)) << std::endl;
105134 switch (action) {
106135 case PrintAll:
107136 print_all_frames (db);
@@ -116,7 +145,7 @@ int main(int argc, char** argv) {
116145 break ;
117146
118147 default :
119- std::cerr << " Acton not implemented yet." << std::endl;
148+ std::cerr << " Action not implemented yet." << std::endl;
120149 return 3 ;
121150 }
122151 return 0 ;
0 commit comments