-
Notifications
You must be signed in to change notification settings - Fork 38
Task 3, libSMCE console #51
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: master
Are you sure you want to change the base?
Conversation
Added SMCE_Client, a terminal interface for libSMCE.
Implemented a way to handle more then one input, to make it possible for example sending message
NOT WORKING! KNOWN BUG.
Move SMCE_Client to its own folder, created a CMakeLists that installs SMCE_Client.exe and copys the SMCE.dll from the path of enviroment variable SMCE_ROOT.
Added GPIO functionality to libSMCE client
Fixed bugg with recompile causing thread to crash. Added termcolor library to set color for uart messages. Added mute for uart messages.
Added functionality to set Arduino root folder Added functionality to set SMCE_RESOURCE at runtime
Added so incoming uart messages can be written to a file instead of console. Set at start by setting the start argument -u or --file to true.
Codecov Report
@@ Coverage Diff @@
## master #51 +/- ##
===========================================
+ Coverage 40.08% 63.26% +23.18%
===========================================
Files 33 82 +49
Lines 1497 2986 +1489
===========================================
+ Hits 600 1889 +1289
- Misses 897 1097 +200
Continue to review full report at Codecov.
|
AeroStun
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This code is barely readable; reformat it (ClangFormat is your friend).
Also the general conditional complexity in main tends to be overwhelming; try factorizing it out using lookup tables, functions, etc...
| ) | ||
|
|
||
|
|
||
| add_library (objSMCE OBJECT) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Superfluous change
| include/SMCE/SketchConf.hpp | ||
| include/SMCE/internal/BoardDeviceSpecification.hpp | ||
| ) | ||
|
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Superfluous change
client/CMakeLists.txt
Outdated
| ) | ||
| FetchContent_MakeAvailable(Termcolor Lyra) | ||
|
|
||
| include_directories(${PROJECT_SOURCE_DIR}/src) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Never use global include_directories; see target_include_directories for a pure alternative
| target_include_directories (${PROJECT_NAME} PUBLIC | ||
| "${termcolor_SOURCE_DIR}/include/termcolor" | ||
| "${lyra_SOURCE_DIR}/include/lyra" | ||
| ) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I would be incredibly surprised that the termcolor::termcolor and bfg::Lyra targets don't already provide those directories in their interface properties
client/README.md
Outdated
| To be able to build SMCE_client, the enviroment variable SMCE_ROOT needs to point to a current installed release of libSMCE. | ||
| These can be found under releases on git. Or it can be build directly from the source code with the commands below. | ||
| These should be ran in the libSMCE folder. | ||
| ```shell | ||
| cmake -S . -B build/ | ||
| cmake --build build/ | ||
| cmake --build build/ --config Release | ||
| cmake --install build/ --prefix <path to installation folder> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
These instructions are both wrong and misplaced; this README is in a subfolder of the libSMCE project, so it stands to reason that readers have already read the top-level README
client/SMCE_Client.cpp
Outdated
|
|
||
| }else if (input.starts_with("-ra ")){ | ||
| bool read = true; | ||
| int index_pin = stoi(input.substr(3)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
const-incorrect
client/SMCE_Client.cpp
Outdated
|
|
||
| }else if (input.starts_with("-rd ")){ | ||
| bool read = true; | ||
| int index_pin = stoi(input.substr(3)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
const-incorrect
client/src/UartToFile.cpp
Outdated
| @@ -0,0 +1,28 @@ | |||
| #include <UartToFile.hpp> | |||
| #include <ctime> | |||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Use <chrono>'s stuff
client/src/UartToFile.cpp
Outdated
| #include <fstream> | ||
| #include <iostream> | ||
|
|
||
| using namespace std; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If you are trying to give me a heart attack, this is definitely the way to go
| int uart_to_file(std::string message, std::string path){ | ||
| ofstream file; | ||
| file.open(path, std::ios_base::app); | ||
| file << get_time() +": " +message + "\n"; | ||
| file.close(); | ||
| return 0; | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Opening/closing a file every time you need to write to it should be a definition of inefficiency.
RuthgerD
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Focus on parting everything into components, just constantly ask yourself, "how would I test this", "could someone reuse this code as a library" and stuff like that.
| - Sketch path: Relative or absolute path to the sketch to run | ||
|
|
||
| ### Start arguments | ||
| -f,--fqbn <fqbn> -> <fqbn> = Fully qualified board name |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
just a note in general, fqbn is basically deprecated, so I would default this parameter
| std::string get_time(){ | ||
| time_t currentTime; | ||
| struct tm *localTime; | ||
|
|
||
| time( ¤tTime ); | ||
| localTime = localtime( ¤tTime ); | ||
|
|
||
| int hour = localTime->tm_hour; | ||
| int min = localTime->tm_min; | ||
| int sec = localTime->tm_sec; | ||
| return(to_string(hour)+":"+to_string(min)+":"+to_string(sec)); | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this use the way better library:
https://en.cppreference.com/w/cpp/chrono#Clocks
client/src/UartToFile.cpp
Outdated
| #include <fstream> | ||
| #include <iostream> | ||
|
|
||
| using namespace std; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
using std is a bad practice
| int uart_to_file(std::string message, std::string path){ | ||
| ofstream file; | ||
| file.open(path, std::ios_base::app); | ||
| file << get_time() +": " +message + "\n"; | ||
| file.close(); | ||
| return 0; | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this is a highly specifically named module and a highly specifically named function name even though all it does write to a file. I would generalize this, also, this is one of the cases where you might want to keep the file open for the duration of the program as constantly opening a file is not very nice.
client/SMCE_Client.cpp
Outdated
| void print_help(const char* argv0){ | ||
| std::cout << "Usage: " << argv0 << " <fully-qualified-board-name> <path-to-sketch>" << std::endl; | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
stuff like this can just be in the main function
client/SMCE_Client.cpp
Outdated
| print_menu(); | ||
|
|
||
| }else if (input == "-p"){ //pause or resume | ||
| if(!suspended){ |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
better read the state from the board instead of keeping track of it yourself
client/SMCE_Client.cpp
Outdated
| }else if (input == "-rc"){ //recompile | ||
| std::cout << "Recompiling.." << std::endl; | ||
| t_lock.lock(); // aquire lock before recompiling, so uart_listener is forced to wait | ||
| compile_and_start(sketch,toolchain,board,arduino_root_dir); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
a function like this just makes things opaque imo, why not have a compile function and a start function that you just calls after each other? they dont need to be composed.
client/SMCE_Client.cpp
Outdated
| std::cout << "Complete" << std::endl; | ||
|
|
||
| }else if (input.starts_with("-m ")){ //send message on uart | ||
| std::string message = input.substr(3); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
needless clone
client/SMCE_Client.cpp
Outdated
| if(!apin.exists()){ | ||
| std::cout << "Pin does not exist!" << std::endl; | ||
| write=false; | ||
| } | ||
| if(!apin.can_write()){ | ||
| std::cout << "Can't write to pin!" << std::endl; | ||
| write=false; | ||
| } | ||
| if(write){ | ||
| apin.write(value); | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
if () else if() else { ::write }
client/SMCE_Client.cpp
Outdated
| if(value == 0){ | ||
| apin.write(false); | ||
| }else if(value == 1){ | ||
| apin.write(true); | ||
| }else{ | ||
| std::cout << "Value must be 0 or 1 for digital pins" << std::endl; | ||
| } |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
tbh apin.write(value > 0), it works like this internally as well
client/SMCE_Client.cpp
Outdated
| static std::atomic_bool mute_uart = false; | ||
| static std::mutex t_lock; | ||
| //Listen to the uart input from board, writes what it read to terminal | ||
| void uart_listener(smce::VirtualUart uart,bool file_write,std::string path){ |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
yeah as discussed, taking the VirtualUart by value and reusing it across recompilations is completely wrong and likely reads invalid memory
Focused on the smaller problems from the pull request review. Still has several bugs / changes that needs to be done.
| }else if (input.starts_with("-rd ")){ | ||
| bool read = true; | ||
| int index_pin = stoi(input.substr(3)); | ||
| }else if (!pin.can_read()) { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Just because the board cannot read does not mean the user should not be able to see the value
| std::cout << "Pin does not exist!" << std::endl; | ||
| read=false; | ||
| } | ||
| if(!pin.can_read()){ | ||
| }else if (!pin.can_read()) { | ||
| std::cout << "Can't read from pin!" << std::endl; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Same as above
| } else if (input == "-q") { // power off and quit | ||
| std::cout << "Quitting..." << std::endl; | ||
| run_threads = false; | ||
| board.stop(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Board::stop may fail
We are aware that the code is in need of refactoring, but we are not sure how we should go about it and also what to prioritize.