uni

University stuff
git clone git://git.christosmarg.xyz/uni-assignments.git
Log | Files | Refs | README | LICENSE

commit bb74152c4bdcc9a9ea91eb40b0bd0d08e0cfc970
parent 1b746a5e7e167289b406307286bf08fe103c32d6
Author: Christos Margiolis <christos@margiolis.net>
Date:   Thu, 27 May 2021 22:17:21 +0300

renplaced - with _

Diffstat:
Dc-os2/ex2/Makefile | 12------------
Dc-os2/ex2/ex1_1.c | 97-------------------------------------------------------------------------------
Dc-os2/ex2/ex3_server.c | 234-------------------------------------------------------------------------------
Dc-programming/5-arrays-pointers-files/minecurses/src/audio.h | 13-------------
Rc-data-structures/arrays_ex1.c -> c_data_structures/arrays_ex1.c | 0
Rc-data-structures/arrays_ex2.c -> c_data_structures/arrays_ex2.c | 0
Rc-data-structures/arrays_ex3.c -> c_data_structures/arrays_ex3.c | 0
Rc-data-structures/bintree.c -> c_data_structures/bintree.c | 0
Rc-data-structures/files_ex1.c -> c_data_structures/files_ex1.c | 0
Rc-data-structures/files_ex2.c -> c_data_structures/files_ex2.c | 0
Rc-data-structures/funcs_ex1.c -> c_data_structures/funcs_ex1.c | 0
Rc-data-structures/funcs_ex2.c -> c_data_structures/funcs_ex2.c | 0
Rc-data-structures/funcs_ex3.c -> c_data_structures/funcs_ex3.c | 0
Rc-data-structures/memalloc_ex1.c -> c_data_structures/memalloc_ex1.c | 0
Rc-data-structures/memalloc_ex2.c -> c_data_structures/memalloc_ex2.c | 0
Rc-data-structures/ptrs_ex1.c -> c_data_structures/ptrs_ex1.c | 0
Rc-data-structures/ptrs_ex2.c -> c_data_structures/ptrs_ex2.c | 0
Rc-data-structures/ptrs_ex3.c -> c_data_structures/ptrs_ex3.c | 0
Rc-data-structures/queue.c -> c_data_structures/queue.c | 0
Rc-data-structures/stack_list.c -> c_data_structures/stack_list.c | 0
Rc-os2/ex1/ex1.c -> c_os2/ex1/ex1.c | 0
Rc-os2/ex1/ex2.c -> c_os2/ex1/ex2.c | 0
Rc-os2/ex1/ex3.c -> c_os2/ex1/ex3.c | 0
Ac_os2/ex2/Makefile | 9+++++++++
Ac_os2/ex2/ex1_1.c | 128+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Ac_os2/ex2/ex1_2.c | 137+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Ac_os2/ex2/ex2.c | 198+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Rc-os2/ex2/ex3_client.c -> c_os2/ex2/ex3_client.c | 0
Ac_os2/ex2/ex3_server.c | 235+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Rc-os2/lab2_fifo.c -> c_os2/lab2_fifo.c | 0
Rc-os2/lab2_pipe.c -> c_os2/lab2_pipe.c | 0
Rc-parallel-computing/ex1/doc.pdf -> c_parallel_computing/ex1/doc.pdf | 0
Rc-parallel-computing/ex1/doc.tex -> c_parallel_computing/ex1/doc.tex | 0
Rc-parallel-computing/ex1/ex1.c -> c_parallel_computing/ex1/ex1.c | 0
Rc-parallel-computing/ex1/res/exmpl1.png -> c_parallel_computing/ex1/res/exmpl1.png | 0
Rc-parallel-computing/ex1/res/exmpl2.png -> c_parallel_computing/ex1/res/exmpl2.png | 0
Rc-parallel-computing/ex1/res/exmpl3.png -> c_parallel_computing/ex1/res/exmpl3.png | 0
Rc-parallel-computing/ex1/res/exmpl4.png -> c_parallel_computing/ex1/res/exmpl4.png | 0
Rc-parallel-computing/ex2/data -> c_parallel_computing/ex2/data | 0
Rc-parallel-computing/ex2/doc.pdf -> c_parallel_computing/ex2/doc.pdf | 0
Rc-parallel-computing/ex2/doc.tex -> c_parallel_computing/ex2/doc.tex | 0
Rc-parallel-computing/ex2/ex2.c -> c_parallel_computing/ex2/ex2.c | 0
Rc-parallel-computing/ex2/res/run1.png -> c_parallel_computing/ex2/res/run1.png | 0
Rc-parallel-computing/ex2/res/run2.png -> c_parallel_computing/ex2/res/run2.png | 0
Rc-parallel-computing/ex2/res/run3.png -> c_parallel_computing/ex2/res/run3.png | 0
Rc-programming/1-basic-elements/C1a-CORRECTED.c -> c_programming/1_basic_elements/C1a_correct.c | 0
Rc-programming/1-basic-elements/Cube-Sphere.c -> c_programming/1_basic_elements/Cube_Sphere.c | 0
Rc-programming/1-basic-elements/IO-Exercise.c -> c_programming/1_basic_elements/IO_Exercise.c | 0
Rc-programming/1-basic-elements/docs/assignment-1.odt -> c_programming/1_basic_elements/docs/assignment_1.odt | 0
Rc-programming/1-basic-elements/docs/assignment-1.pdf -> c_programming/1_basic_elements/docs/assignment_1.pdf | 0
Rc-programming/2-conditional-statements/docs/assignment-2.odt -> c_programming/2_conditional_statements/docs/assignment_2.odt | 0
Rc-programming/2-conditional-statements/docs/assignment-2.pdf -> c_programming/2_conditional_statements/docs/assignment_2.pdf | 0
Rc-programming/2-conditional-statements/int-comparison.c -> c_programming/2_conditional_statements/int_comparison.c | 0
Rc-programming/2-conditional-statements/quadratic-equation.c -> c_programming/2_conditional_statements/quadratic_equation.c | 0
Rc-programming/3-loops/docs/assignment-3.odt -> c_programming/3_loops/docs/assignment_3.odt | 0
Rc-programming/3-loops/docs/assignment-3.pdf -> c_programming/3_loops/docs/assignment_3.pdf | 0
Rc-programming/3-loops/int-calcs.c -> c_programming/3_loops/int_calcs.c | 0
Rc-programming/3-loops/shapes.c -> c_programming/3_loops/shapes.c | 0
Rc-programming/3-loops/sine-taylor.c -> c_programming/3_loops/sine_taylor.c | 0
Rc-programming/4-functions/docs/assignment-4.odt -> c_programming/4_functions/docs/assignment_4.odt | 0
Rc-programming/4-functions/docs/assignment-4.pdf -> c_programming/4_functions/docs/assignment_4.pdf | 0
Rc-programming/4-functions/docs/photos-diagrams/hanoi-end.png -> c_programming/4_functions/docs/photos_diagrams/hanoi_end.png | 0
Rc-programming/4-functions/docs/photos-diagrams/hanoi-start.png -> c_programming/4_functions/docs/photos_diagrams/hanoi_start.png | 0
Rc-programming/4-functions/docs/photos-diagrams/menu-diagram.drawio -> c_programming/4_functions/docs/photos_diagrams/menu_diagram.drawio | 0
Rc-programming/4-functions/docs/photos-diagrams/menu-diagram.png -> c_programming/4_functions/docs/photos_diagrams/menu_diagram.png | 0
Rc-programming/4-functions/docs/photos-diagrams/sct-diagram.drawio -> c_programming/4_functions/docs/photos_diagrams/sct_diagram.drawio | 0
Rc-programming/4-functions/docs/photos-diagrams/sct-diagram.jpg -> c_programming/4_functions/docs/photos_diagrams/sct_diagram.jpg | 0
Rc-programming/4-functions/hanoi-tower/Makefile -> c_programming/4_functions/hanoi_tower/Makefile | 0
Rc-programming/4-functions/hanoi-tower/src/hanoi-tower.c -> c_programming/4_functions/hanoi_tower/src/hanoi_tower.c | 0
Rc-programming/4-functions/menu/Makefile -> c_programming/4_functions/menu/Makefile | 0
Rc-programming/4-functions/menu/include/menu.h -> c_programming/4_functions/menu/include/menu.h | 0
Rc-programming/4-functions/menu/src/main.c -> c_programming/4_functions/menu/src/main.c | 0
Rc-programming/4-functions/menu/src/menu.c -> c_programming/4_functions/menu/src/menu.c | 0
Rc-programming/4-functions/sine-cos-taylor/Makefile -> c_programming/4_functions/sine_cos_taylor/Makefile | 0
Rc-programming/4-functions/sine-cos-taylor/include/sine-cos-taylor.h -> c_programming/4_functions/sine_cos_taylor/include/sine_cos_taylor.h | 0
Rc-programming/4-functions/sine-cos-taylor/src/main.c -> c_programming/4_functions/sine_cos_taylor/src/main.c | 0
Rc-programming/4-functions/sine-cos-taylor/src/sine-cos-taylor.c -> c_programming/4_functions/sine_cos_taylor/src/sine_cos_taylor.c | 0
Rc-programming/5-arrays-pointers-files/combinations/Makefile -> c_programming/5_arrays_ptrs_files/combinations/Makefile | 0
Rc-programming/5-arrays-pointers-files/combinations/include/arrhandler.h -> c_programming/5_arrays_ptrs_files/combinations/include/arrhandler.h | 0
Rc-programming/5-arrays-pointers-files/combinations/include/ccolors.h -> c_programming/5_arrays_ptrs_files/combinations/include/ccolors.h | 0
Rc-programming/5-arrays-pointers-files/combinations/include/combinations.h -> c_programming/5_arrays_ptrs_files/combinations/include/combinations.h | 0
Rc-programming/5-arrays-pointers-files/combinations/src/arrhandler.c -> c_programming/5_arrays_ptrs_files/combinations/src/arrhandler.c | 0
Rc-programming/5-arrays-pointers-files/combinations/src/combinations.c -> c_programming/5_arrays_ptrs_files/combinations/src/combinations.c | 0
Rc-programming/5-arrays-pointers-files/combinations/src/main.c -> c_programming/5_arrays_ptrs_files/combinations/src/main.c | 0
Rc-programming/5-arrays-pointers-files/combinations/txt/data.txt -> c_programming/5_arrays_ptrs_files/combinations/txt/data.txt | 0
Rc-programming/5-arrays-pointers-files/combinations/txt/data40.txt -> c_programming/5_arrays_ptrs_files/combinations/txt/data40.txt | 0
Rc-programming/5-arrays-pointers-files/combinations/txt/data49.txt -> c_programming/5_arrays_ptrs_files/combinations/txt/data49.txt | 0
Rc-programming/5-arrays-pointers-files/combinations/txt/data7.txt -> c_programming/5_arrays_ptrs_files/combinations/txt/data7.txt | 0
Rc-programming/5-arrays-pointers-files/docs/assignment-5.pdf -> c_programming/5_arrays_ptrs_files/docs/assignment_5.pdf | 0
Rc-programming/5-arrays-pointers-files/docs/assignment-5.tex -> c_programming/5_arrays_ptrs_files/docs/assignment_5.tex | 0
Rc-programming/5-arrays-pointers-files/fcombinations/Makefile -> c_programming/5_arrays_ptrs_files/fcombinations/Makefile | 0
Rc-programming/5-arrays-pointers-files/fcombinations/include/arrhandler.h -> c_programming/5_arrays_ptrs_files/fcombinations/include/arrhandler.h | 0
Rc-programming/5-arrays-pointers-files/fcombinations/include/ccolors.h -> c_programming/5_arrays_ptrs_files/fcombinations/include/ccolors.h | 0
Rc-programming/5-arrays-pointers-files/fcombinations/include/fcombinations.h -> c_programming/5_arrays_ptrs_files/fcombinations/include/fcombinations.h | 0
Rc-programming/5-arrays-pointers-files/fcombinations/src/arrhandler.c -> c_programming/5_arrays_ptrs_files/fcombinations/src/arrhandler.c | 0
Rc-programming/5-arrays-pointers-files/fcombinations/src/fcombinations.c -> c_programming/5_arrays_ptrs_files/fcombinations/src/fcombinations.c | 0
Rc-programming/5-arrays-pointers-files/fcombinations/src/main.c -> c_programming/5_arrays_ptrs_files/fcombinations/src/main.c | 0
Rc-programming/5-arrays-pointers-files/fcombinations/txt/data.txt -> c_programming/5_arrays_ptrs_files/fcombinations/txt/data.txt | 0
Rc-programming/5-arrays-pointers-files/fcombinations/txt/data40.txt -> c_programming/5_arrays_ptrs_files/fcombinations/txt/data40.txt | 0
Rc-programming/5-arrays-pointers-files/fcombinations/txt/data49.txt -> c_programming/5_arrays_ptrs_files/fcombinations/txt/data49.txt | 0
Rc-programming/5-arrays-pointers-files/fcombinations/txt/data7.txt -> c_programming/5_arrays_ptrs_files/fcombinations/txt/data7.txt | 0
Rc-programming/5-arrays-pointers-files/kcombinations/Makefile -> c_programming/5_arrays_ptrs_files/kcombinations/Makefile | 0
Rc-programming/5-arrays-pointers-files/kcombinations/include/arrhandler.h -> c_programming/5_arrays_ptrs_files/kcombinations/include/arrhandler.h | 0
Rc-programming/5-arrays-pointers-files/kcombinations/include/ccolors.h -> c_programming/5_arrays_ptrs_files/kcombinations/include/ccolors.h | 0
Rc-programming/5-arrays-pointers-files/kcombinations/include/kcombinations.h -> c_programming/5_arrays_ptrs_files/kcombinations/include/kcombinations.h | 0
Rc-programming/5-arrays-pointers-files/kcombinations/src/arrhandler.c -> c_programming/5_arrays_ptrs_files/kcombinations/src/arrhandler.c | 0
Rc-programming/5-arrays-pointers-files/kcombinations/src/kcombinations.c -> c_programming/5_arrays_ptrs_files/kcombinations/src/kcombinations.c | 0
Rc-programming/5-arrays-pointers-files/kcombinations/src/main.c -> c_programming/5_arrays_ptrs_files/kcombinations/src/main.c | 0
Rc-programming/5-arrays-pointers-files/kcombinations/txt/kdata.txt -> c_programming/5_arrays_ptrs_files/kcombinations/txt/kdata.txt | 0
Rc-programming/5-arrays-pointers-files/kcombinations/txt/kdata40.txt -> c_programming/5_arrays_ptrs_files/kcombinations/txt/kdata40.txt | 0
Rc-programming/5-arrays-pointers-files/kcombinations/txt/kdata49.txt -> c_programming/5_arrays_ptrs_files/kcombinations/txt/kdata49.txt | 0
Rc-programming/5-arrays-pointers-files/minecurses/Makefile -> c_programming/5_arrays_ptrs_files/minecurses/Makefile | 0
Rc-programming/5-arrays-pointers-files/minecurses/README.md -> c_programming/5_arrays_ptrs_files/minecurses/README.md | 0
Rc-programming/5-arrays-pointers-files/minecurses/log/scorelog.csv -> c_programming/5_arrays_ptrs_files/minecurses/log/scorelog.csv | 0
Rc-programming/5-arrays-pointers-files/minecurses/log/session.txt -> c_programming/5_arrays_ptrs_files/minecurses/log/session.txt | 0
Rc-programming/5-arrays-pointers-files/minecurses/res/detective-8bit.wav -> c_programming/5_arrays_ptrs_files/minecurses/res/detective_8bit.wav | 0
Rc-programming/5-arrays-pointers-files/minecurses/src/audio.c -> c_programming/5_arrays_ptrs_files/minecurses/src/audio.c | 0
Ac_programming/5_arrays_ptrs_files/minecurses/src/audio.h | 13+++++++++++++
Rc-programming/5-arrays-pointers-files/minecurses/src/gameplay.c -> c_programming/5_arrays_ptrs_files/minecurses/src/gameplay.c | 0
Rc-programming/5-arrays-pointers-files/minecurses/src/gameplay.h -> c_programming/5_arrays_ptrs_files/minecurses/src/gameplay.h | 0
Rc-programming/5-arrays-pointers-files/minecurses/src/main.c -> c_programming/5_arrays_ptrs_files/minecurses/src/main.c | 0
Rc-programming/5-arrays-pointers-files/minecurses/src/main.h -> c_programming/5_arrays_ptrs_files/minecurses/src/main.h | 0
Rc-programming/5-arrays-pointers-files/minecurses/src/minesweeper.c -> c_programming/5_arrays_ptrs_files/minecurses/src/minesweeper.c | 0
Rc-programming/5-arrays-pointers-files/minecurses/src/minesweeper.h -> c_programming/5_arrays_ptrs_files/minecurses/src/minesweeper.h | 0
Rc-programming/5-arrays-pointers-files/minecurses/src/navigation.c -> c_programming/5_arrays_ptrs_files/minecurses/src/navigation.c | 0
Rc-programming/5-arrays-pointers-files/minecurses/src/navigation.h -> c_programming/5_arrays_ptrs_files/minecurses/src/navigation.h | 0
Rc-programming/5-arrays-pointers-files/minecurses/src/outputs.c -> c_programming/5_arrays_ptrs_files/minecurses/src/outputs.c | 0
Rc-programming/5-arrays-pointers-files/minecurses/src/outputs.h -> c_programming/5_arrays_ptrs_files/minecurses/src/outputs.h | 0
Rc-programming/5-arrays-pointers-files/minecurses/src/settings.c -> c_programming/5_arrays_ptrs_files/minecurses/src/settings.c | 0
Rc-programming/5-arrays-pointers-files/minecurses/src/settings.h -> c_programming/5_arrays_ptrs_files/minecurses/src/settings.h | 0
Rc-programming/5-arrays-pointers-files/minecurses/src/wins.c -> c_programming/5_arrays_ptrs_files/minecurses/src/wins.c | 0
Rc-programming/5-arrays-pointers-files/minecurses/src/wins.h -> c_programming/5_arrays_ptrs_files/minecurses/src/wins.h | 0
Dcpp-oop/game/Engine.cc | 364-------------------------------------------------------------------------------
Rcpp-oop/1-fromctocpp/fromctocpp.cpp -> cpp_oop/1_fromctocpp/fromctocpp.cpp | 0
Rcpp-oop/2-classes/classes.cpp -> cpp_oop/2_classes/classes.cpp | 0
Rcpp-oop/3-operoverloading/Makefile -> cpp_oop/3_operoverloading/Makefile | 0
Rcpp-oop/3-operoverloading/src/course.cpp -> cpp_oop/3_operoverloading/src/course.cpp | 0
Rcpp-oop/3-operoverloading/src/course.hpp -> cpp_oop/3_operoverloading/src/course.hpp | 0
Rcpp-oop/3-operoverloading/src/main.cpp -> cpp_oop/3_operoverloading/src/main.cpp | 0
Rcpp-oop/3-operoverloading/src/student.cpp -> cpp_oop/3_operoverloading/src/student.cpp | 0
Rcpp-oop/3-operoverloading/src/student.hpp -> cpp_oop/3_operoverloading/src/student.hpp | 0
Rcpp-oop/4-inheritance/Makefile -> cpp_oop/4_inheritance/Makefile | 0
Rcpp-oop/4-inheritance/res/appdata.csv -> cpp_oop/4_inheritance/res/appdata.csv | 0
Rcpp-oop/4-inheritance/res/appdata_out.csv -> cpp_oop/4_inheritance/res/appdata_out.csv | 0
Rcpp-oop/4-inheritance/res/errlog.txt -> cpp_oop/4_inheritance/res/errlog.txt | 0
Rcpp-oop/4-inheritance/res/manfdata.csv -> cpp_oop/4_inheritance/res/manfdata.csv | 0
Rcpp-oop/4-inheritance/res/manfdata_out.csv -> cpp_oop/4_inheritance/res/manfdata_out.csv | 0
Rcpp-oop/4-inheritance/res/revs.csv -> cpp_oop/4_inheritance/res/revs.csv | 0
Rcpp-oop/4-inheritance/res/revs_out.csv -> cpp_oop/4_inheritance/res/revs_out.csv | 0
Rcpp-oop/4-inheritance/src/app.cpp -> cpp_oop/4_inheritance/src/app.cpp | 0
Rcpp-oop/4-inheritance/src/app.hpp -> cpp_oop/4_inheritance/src/app.hpp | 0
Rcpp-oop/4-inheritance/src/appsystem.cpp -> cpp_oop/4_inheritance/src/appsystem.cpp | 0
Rcpp-oop/4-inheritance/src/appsystem.hpp -> cpp_oop/4_inheritance/src/appsystem.hpp | 0
Rcpp-oop/4-inheritance/src/errlog.cpp -> cpp_oop/4_inheritance/src/errlog.cpp | 0
Rcpp-oop/4-inheritance/src/errlog.hpp -> cpp_oop/4_inheritance/src/errlog.hpp | 0
Rcpp-oop/4-inheritance/src/game.cpp -> cpp_oop/4_inheritance/src/game.cpp | 0
Rcpp-oop/4-inheritance/src/game.hpp -> cpp_oop/4_inheritance/src/game.hpp | 0
Rcpp-oop/4-inheritance/src/main.cpp -> cpp_oop/4_inheritance/src/main.cpp | 0
Rcpp-oop/4-inheritance/src/manufacturer.cpp -> cpp_oop/4_inheritance/src/manufacturer.cpp | 0
Rcpp-oop/4-inheritance/src/manufacturer.hpp -> cpp_oop/4_inheritance/src/manufacturer.hpp | 0
Rcpp-oop/4-inheritance/src/office.cpp -> cpp_oop/4_inheritance/src/office.cpp | 0
Rcpp-oop/4-inheritance/src/office.hpp -> cpp_oop/4_inheritance/src/office.hpp | 0
Rcpp-oop/4-inheritance/src/review.cpp -> cpp_oop/4_inheritance/src/review.cpp | 0
Rcpp-oop/4-inheritance/src/review.hpp -> cpp_oop/4_inheritance/src/review.hpp | 0
Rcpp-oop/5-spreadsheets/Makefile -> cpp_oop/5_spreadsheets/Makefile | 0
Rcpp-oop/5-spreadsheets/res/courses.csv -> cpp_oop/5_spreadsheets/res/courses.csv | 0
Rcpp-oop/5-spreadsheets/res/equivalencies.csv -> cpp_oop/5_spreadsheets/res/equivalencies.csv | 0
Rcpp-oop/5-spreadsheets/res/errlog.csv -> cpp_oop/5_spreadsheets/res/errlog.csv | 0
Rcpp-oop/5-spreadsheets/res/grades.csv -> cpp_oop/5_spreadsheets/res/grades.csv | 0
Rcpp-oop/5-spreadsheets/res/report.csv -> cpp_oop/5_spreadsheets/res/report.csv | 0
Rcpp-oop/5-spreadsheets/res/students.csv -> cpp_oop/5_spreadsheets/res/students.csv | 0
Rcpp-oop/5-spreadsheets/src/course.hpp -> cpp_oop/5_spreadsheets/src/course.hpp | 0
Rcpp-oop/5-spreadsheets/src/datahandler.cpp -> cpp_oop/5_spreadsheets/src/datahandler.cpp | 0
Rcpp-oop/5-spreadsheets/src/datahandler.hpp -> cpp_oop/5_spreadsheets/src/datahandler.hpp | 0
Rcpp-oop/5-spreadsheets/src/errlog.cpp -> cpp_oop/5_spreadsheets/src/errlog.cpp | 0
Rcpp-oop/5-spreadsheets/src/errlog.hpp -> cpp_oop/5_spreadsheets/src/errlog.hpp | 0
Rcpp-oop/5-spreadsheets/src/main.cpp -> cpp_oop/5_spreadsheets/src/main.cpp | 0
Rcpp-oop/5-spreadsheets/src/student.hpp -> cpp_oop/5_spreadsheets/src/student.hpp | 0
Rcpp-oop/5-spreadsheets/src/xstring.cpp -> cpp_oop/5_spreadsheets/src/xstring.cpp | 0
Rcpp-oop/5-spreadsheets/src/xstring.hpp -> cpp_oop/5_spreadsheets/src/xstring.hpp | 0
Acpp_oop/game/Engine.cc | 366+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Rcpp-oop/game/Engine.hpp -> cpp_oop/game/Engine.hpp | 0
Rcpp-oop/game/Gnome.cc -> cpp_oop/game/Gnome.cc | 0
Rcpp-oop/game/Gnome.hpp -> cpp_oop/game/Gnome.hpp | 0
Rcpp-oop/game/Makefile -> cpp_oop/game/Makefile | 0
Rcpp-oop/game/Movable.cc -> cpp_oop/game/Movable.cc | 0
Rcpp-oop/game/Movable.hpp -> cpp_oop/game/Movable.hpp | 0
Rcpp-oop/game/Potter.cc -> cpp_oop/game/Potter.cc | 0
Rcpp-oop/game/Potter.hpp -> cpp_oop/game/Potter.hpp | 0
Rcpp-oop/game/Score.cc -> cpp_oop/game/Score.cc | 0
Rcpp-oop/game/Score.hpp -> cpp_oop/game/Score.hpp | 0
Rcpp-oop/game/Traal.cc -> cpp_oop/game/Traal.cc | 0
Rcpp-oop/game/Traal.hpp -> cpp_oop/game/Traal.hpp | 0
Rcpp-oop/game/main.cc -> cpp_oop/game/main.cc | 0
Rcpp-oop/game/map -> cpp_oop/game/map | 0
Rcpp-oop/game/score -> cpp_oop/game/score | 0
Rjava-development/CopyPaste.java -> java_development/CopyPaste.java | 0
Rjava-development/Occurences.java -> java_development/Occurences.java | 0
Rjava-development/Prime.java -> java_development/Prime.java | 0
Rjava-development/ReadLines.java -> java_development/ReadLines.java | 0
Rjava-development/RecursiveRev.java -> java_development/RecursiveRev.java | 0
Rjava-development/csv/Album.java -> java_development/csv/Album.java | 0
Rjava-development/csv/Main.java -> java_development/csv/Main.java | 0
Rjava-development/csv/data -> java_development/csv/data | 0
Rjava-development/rect/Main.java -> java_development/rect/Main.java | 0
Rjava-development/rect/Pixel.java -> java_development/rect/Pixel.java | 0
Rjava-development/rect/Point.java -> java_development/rect/Point.java | 0
Rjava-development/rect/Rectangle.java -> java_development/rect/Rectangle.java | 0
Dmips-architecture/lab1.asm | 19-------------------
Dmips-architecture/lab2.asm | 40----------------------------------------
Dmips-architecture/lab2_exmpl.asm | 37-------------------------------------
Dmips-architecture/lab3_ex1.asm | 76----------------------------------------------------------------------------
Dmips-architecture/lab3_ex2.asm | 73-------------------------------------------------------------------------
Dmips-architecture/lab4_ex1.asm | 31-------------------------------
Dmips-architecture/lab4_ex2.asm | 33---------------------------------
Dmips-architecture/lab4_ex3.asm | 28----------------------------
Dmips-architecture/lab4_ex4.asm | 51---------------------------------------------------
Dmips-architecture/lab4_ex5.asm | 42------------------------------------------
Dmips-architecture/lab4_ex6.asm | 77-----------------------------------------------------------------------------
Dmips-architecture/lab5_ex1.asm | 40----------------------------------------
Dmips-architecture/lab5_ex2.asm | 46----------------------------------------------
Dmips-architecture/lab5_ex3.asm | 23-----------------------
Dmips-architecture/lab5_ex4.asm | 36------------------------------------
Dmips-architecture/lab5_ex5.asm | 64----------------------------------------------------------------
Dmips-architecture/lab6_ex1.asm | 37-------------------------------------
Dmips-architecture/lab6_ex2.asm | 37-------------------------------------
Dmips-architecture/lab6_ex3.asm | 43-------------------------------------------
Dmips-architecture/lab6_ex4.asm | 62--------------------------------------------------------------
Dmips-architecture/lab6_ex5.asm | 62--------------------------------------------------------------
Amips_architecture/lab1.asm | 19+++++++++++++++++++
Amips_architecture/lab2.asm | 40++++++++++++++++++++++++++++++++++++++++
Amips_architecture/lab2_exmpl.asm | 37+++++++++++++++++++++++++++++++++++++
Amips_architecture/lab3_ex1.asm | 76++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Amips_architecture/lab3_ex2.asm | 73+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Amips_architecture/lab4_ex1.asm | 31+++++++++++++++++++++++++++++++
Amips_architecture/lab4_ex2.asm | 33+++++++++++++++++++++++++++++++++
Amips_architecture/lab4_ex3.asm | 28++++++++++++++++++++++++++++
Amips_architecture/lab4_ex4.asm | 51+++++++++++++++++++++++++++++++++++++++++++++++++++
Amips_architecture/lab4_ex5.asm | 42++++++++++++++++++++++++++++++++++++++++++
Amips_architecture/lab4_ex6.asm | 77+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Amips_architecture/lab5_ex1.asm | 40++++++++++++++++++++++++++++++++++++++++
Amips_architecture/lab5_ex2.asm | 46++++++++++++++++++++++++++++++++++++++++++++++
Amips_architecture/lab5_ex3.asm | 23+++++++++++++++++++++++
Amips_architecture/lab5_ex4.asm | 36++++++++++++++++++++++++++++++++++++
Amips_architecture/lab5_ex5.asm | 64++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Amips_architecture/lab6_ex1.asm | 37+++++++++++++++++++++++++++++++++++++
Amips_architecture/lab6_ex2.asm | 37+++++++++++++++++++++++++++++++++++++
Amips_architecture/lab6_ex3.asm | 43+++++++++++++++++++++++++++++++++++++++++++
Amips_architecture/lab6_ex4.asm | 62++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Amips_architecture/lab6_ex5.asm | 62++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Dsh-os1/ex1/ex1.txt | 750-------------------------------------------------------------------------------
Dsh-os1/ex2/bck | 48------------------------------------------------
Dsh-os1/ex2/createpvs | 81-------------------------------------------------------------------------------
Dsh-os1/ex2/mfproc | 110-------------------------------------------------------------------------------
Dsh-os1/ex2/searching | 82-------------------------------------------------------------------------------
Dsh-os1/ex2/teldb | 114-------------------------------------------------------------------------------
Dsh-os1/ex3/ex1_cmds | 39---------------------------------------
Dsh-os1/ex3/ex2_studavgs.awk | 20--------------------
Dsh-os1/ex3/ex3_courseavgs.awk | 25-------------------------
Dsh-os1/ex3/ex4_rev.awk | 20--------------------
Dsh-os1/ex3/ex5_filesize | 3---
Dsh-os1/ex3/ex6_votes.awk | 29-----------------------------
Dsh-os1/ex3/ex7_countmatch | 20--------------------
Ash_os1/ex1/ex1.txt | 750+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Ash_os1/ex2/bck | 48++++++++++++++++++++++++++++++++++++++++++++++++
Ash_os1/ex2/createpvs | 81+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Ash_os1/ex2/mfproc | 110+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Ash_os1/ex2/searching | 82+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Ash_os1/ex2/teldb | 114+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Ash_os1/ex3/ex1_cmds | 39+++++++++++++++++++++++++++++++++++++++
Ash_os1/ex3/ex2_studavgs.awk | 20++++++++++++++++++++
Ash_os1/ex3/ex3_courseavgs.awk | 25+++++++++++++++++++++++++
Ash_os1/ex3/ex4_rev.awk | 20++++++++++++++++++++
Ash_os1/ex3/ex5_filesize | 3+++
Ash_os1/ex3/ex6_votes.awk | 29+++++++++++++++++++++++++++++
Ash_os1/ex3/ex7_countmatch | 20++++++++++++++++++++
Dsql-databases/ex1_new_personnel.sql | 133-------------------------------------------------------------------------------
Dsql-databases/ex2_new_personnel.sql | 135-------------------------------------------------------------------------------
Asql_databases1/ex1_new_personnel.sql | 133+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Asql_databases1/ex2_new_personnel.sql | 135+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Dvhdl-digital-design/Makefile | 10----------
Dvhdl-digital-design/ex1/Makefile | 1-
Dvhdl-digital-design/ex1/adder4.vhd | 23-----------------------
Dvhdl-digital-design/ex1/adder4_tb.vhd | 67-------------------------------------------------------------------
Dvhdl-digital-design/ex1/dec2to4.vhd | 16----------------
Dvhdl-digital-design/ex1/dec2to4_tb.vhd | 37-------------------------------------
Dvhdl-digital-design/ex1/dec2to4en.vhd | 17-----------------
Dvhdl-digital-design/ex1/dec2to4en_tb.vhd | 60------------------------------------------------------------
Dvhdl-digital-design/ex1/dec4to16.vhd | 28----------------------------
Dvhdl-digital-design/ex1/dec4to16_tb.vhd | 73-------------------------------------------------------------------------
Dvhdl-digital-design/ex1/fa.vhd | 14--------------
Dvhdl-digital-design/ex1/fa_tb.vhd | 68--------------------------------------------------------------------
Dvhdl-digital-design/ex1/ha.vhd | 14--------------
Dvhdl-digital-design/ex1/ha_tb.vhd | 43-------------------------------------------
Dvhdl-digital-design/ex1/mux2to1.vhd | 15---------------
Dvhdl-digital-design/ex1/mux2to1_tb.vhd | 33---------------------------------
Dvhdl-digital-design/ex1/mux4to1.vhd | 22----------------------
Dvhdl-digital-design/ex1/mux4to1_tb.vhd | 44--------------------------------------------
Dvhdl-digital-design/ex1/mux_triple_2to1.vhd | 14--------------
Dvhdl-digital-design/ex1/mux_triple_2to1_tb.vhd | 69---------------------------------------------------------------------
Dvhdl-digital-design/ex2/Makefile | 1-
Dvhdl-digital-design/ex2/ff.vhd | 15---------------
Dvhdl-digital-design/ex2/ff_tb.vhd | 53-----------------------------------------------------
Dvhdl-digital-design/ex2/ffrst.vhd | 18------------------
Dvhdl-digital-design/ex2/ffrst_tb.vhd | 59-----------------------------------------------------------
Dvhdl-digital-design/ex2/latch.vhd | 15---------------
Dvhdl-digital-design/ex2/latch_tb.vhd | 53-----------------------------------------------------
Dvhdl-digital-design/ex2/reg.vhd | 22----------------------
Dvhdl-digital-design/ex2/reg_tb.vhd | 49-------------------------------------------------
Dvhdl-digital-design/ex2/shift4.vhd | 32--------------------------------
Dvhdl-digital-design/ex2/shiftn.vhd | 35-----------------------------------
Dvhdl-digital-design/ex2/upcount.vhd | 22----------------------
Dvhdl-digital-design/ex2/upcount_tb.vhd | 35-----------------------------------
Dvhdl-digital-design/ex3/Makefile | 1-
Dvhdl-digital-design/ex3/regfile.vhd | 35-----------------------------------
Dvhdl-digital-design/ex3/regfile_ext.vhd | 45---------------------------------------------
Dvhdl-digital-design/ex3/regfile_ext_tb.vhd | 111-------------------------------------------------------------------------------
Dvhdl-digital-design/ex3/regfile_tb.vhd | 83-------------------------------------------------------------------------------
Avhdl_digital_design/Makefile | 10++++++++++
Avhdl_digital_design/ex1/Makefile | 1+
Avhdl_digital_design/ex1/adder4.vhd | 23+++++++++++++++++++++++
Avhdl_digital_design/ex1/adder4_tb.vhd | 67+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex1/dec2to4.vhd | 16++++++++++++++++
Avhdl_digital_design/ex1/dec2to4_tb.vhd | 37+++++++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex1/dec2to4en.vhd | 17+++++++++++++++++
Avhdl_digital_design/ex1/dec2to4en_tb.vhd | 60++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex1/dec4to16.vhd | 28++++++++++++++++++++++++++++
Avhdl_digital_design/ex1/dec4to16_tb.vhd | 73+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex1/fa.vhd | 14++++++++++++++
Avhdl_digital_design/ex1/fa_tb.vhd | 68++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex1/ha.vhd | 14++++++++++++++
Avhdl_digital_design/ex1/ha_tb.vhd | 43+++++++++++++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex1/mux2to1.vhd | 15+++++++++++++++
Avhdl_digital_design/ex1/mux2to1_tb.vhd | 33+++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex1/mux4to1.vhd | 22++++++++++++++++++++++
Avhdl_digital_design/ex1/mux4to1_tb.vhd | 44++++++++++++++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex1/mux_triple_2to1.vhd | 14++++++++++++++
Avhdl_digital_design/ex1/mux_triple_2to1_tb.vhd | 69+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex2/Makefile | 1+
Avhdl_digital_design/ex2/ff.vhd | 15+++++++++++++++
Avhdl_digital_design/ex2/ff_tb.vhd | 53+++++++++++++++++++++++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex2/ffrst.vhd | 18++++++++++++++++++
Avhdl_digital_design/ex2/ffrst_tb.vhd | 59+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex2/latch.vhd | 15+++++++++++++++
Avhdl_digital_design/ex2/latch_tb.vhd | 53+++++++++++++++++++++++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex2/reg.vhd | 22++++++++++++++++++++++
Avhdl_digital_design/ex2/reg_tb.vhd | 49+++++++++++++++++++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex2/shift4.vhd | 32++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex2/shiftn.vhd | 35+++++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex2/upcount.vhd | 22++++++++++++++++++++++
Avhdl_digital_design/ex2/upcount_tb.vhd | 35+++++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex3/Makefile | 1+
Avhdl_digital_design/ex3/regfile.vhd | 35+++++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex3/regfile_ext.vhd | 45+++++++++++++++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex3/regfile_ext_tb.vhd | 111+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex3/regfile_tb.vhd | 83+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex4/Makefile | 1+
Avhdl_digital_design/ex4/alu4.vhd | 37+++++++++++++++++++++++++++++++++++++
Avhdl_digital_design/ex4/alu4_tb.vhd | 64++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
359 files changed, 5106 insertions(+), 4638 deletions(-)

diff --git a/c-os2/ex2/Makefile b/c-os2/ex2/Makefile @@ -1,12 +0,0 @@ -all: - cc ex3_server.c -lpthread -o ex3_server - cc ex3_client.c -o ex3_client - -run_srv: all - ./ex3_server - -run_cli: all - ./ex3_client - -clean: - rm -f ex3_server ex3_client *.core *.o diff --git a/c-os2/ex2/ex1_1.c b/c-os2/ex2/ex1_1.c @@ -1,97 +0,0 @@ -#include <pthread.h> -#include <semaphore.h> -#include <stdio.h> -#include <stdlib.h> -#include <string.h> - -#define LEN(x) (sizeof(x) / sizeof(x[0])) - -/* - * Εργαστήριο ΛΣ2 (Δ6) / Εργασία 2: Άσκηση 1.1 / 2020-2021 - * Ονοματεπώνυμο: Χρήστος Μαργιώλης - * ΑΜ: 19390133 - * Τρόπος μεταγλώττισης: `cc ex1_1.c -lpthread -o ex1_1` - */ - -struct foo { - char *str; - sem_t mutex; -}; - -/* Function declarations */ -static void *tdprint(void *); -static void *emalloc(size_t); - -/* Global variables */ -static const char *nums[] = { /* Each thread will print one of these */ - "<one>", - "<two>", - "<three>", -}; - -static void * -tdprint(void *foo) -{ - struct foo *f; - - f = (struct foo *)foo; - if (sem_wait(&f->mutex) < 0) - err(1, "sem_wait"); - printf("%s", f->str); - /* Prevent memory leak from strdup(2). */ - free(f->str); - if (sem_post(&f->mutex) < 0) - err(1, "sem_post"); - - return NULL; -} - -static void * -emalloc(size_t nb) -{ - void *p; - - if ((p = malloc(nb)) == NULL) - err(1, "malloc"); - - return p; -} - -int -main(int argc, char *argv[]) -{ - struct foo *f; - pthread_t *tds; - int i, len, n = 5; - - len = LEN(nums); - f = emalloc(sizeof(struct foo)); - /* - * Instead of hardcoding how many threads we want to have, the - * number of threads is always equal to how many elements the - * `nums` array has. That means in case we want to add/remove - * entries from `nums`, everything will adapt automatically. - */ - tds = emalloc(len * sizeof(pthread_t)); - - if (sem_init(&f->mutex, 0, 1) < 0) - err(1, "sem_init"); - while (n--) { - for (i = 0; i < len; i++) { - if ((f->str = strdup(nums[i])) == NULL) - err(1, "strdup"); - if (pthread_create(&tds[i], NULL, tdprint, (void *)f) != 0) - err(1, "pthread_create"); - if (pthread_join(tds[i], NULL) != 0) - err(1, "pthread_join"); - } - } - printf("\n"); - - (void)sem_destroy(&f->mutex); - pthread_exit(NULL); - free(tds); - free(f); - - return 0; -} diff --git a/c-os2/ex2/ex3_server.c b/c-os2/ex2/ex3_server.c @@ -1,234 +0,0 @@ -#include <sys/socket.h> -#include <sys/types.h> -#include <sys/un.h> - -#include <err.h> -#include <signal.h> -#include <stdio.h> -#include <stdlib.h> -#include <string.h> -#include <unistd.h> - -/* - * Εργαστήριο ΛΣ2 (Δ6) / Εργασία 2: Άσκηση 3 (server) / 2020-2021 - * Ονοματεπώνυμο: Χρήστος Μαργιώλης - * ΑΜ: 19390133 - * Τρόπος μεταγλώττισης: `cc ex3_server.c -o ex3_server` - */ - -/* Results to be sent back to the client. */ -struct pack_res { - char str[32]; - float avg; -}; - -struct foo { - int cfd; - int nsucc; - int ntotal; -}; - -static int srv(struct foo *); -static void sighandler(int); -static void *emalloc(size_t); - -static char *argv0; -/* Only gets set if a termination signal is caught. */ -static volatile sig_atomic_t f_quit = 0; - -static int -srv(struct foo *foo) -{ - struct foo *f; - struct pack_res *res; - int *arr; - int i, n, sum; - int rc; - char cont; - - /* - * The return code is -1 (error) by default so that we don't - * need to set it everytime an error occurs in the main loop. - * If there are no errors, `rc` will be set to 0 (success) right - * after the loop. - */ - rc = -1; - f = (struct foo *)foo; - for (;;) { - if (recv(f->cfd, &n, sizeof(int), 0) < 0) - goto fail; - arr = emalloc(n * sizeof(int)); - if (recv(f->cfd, arr, n * sizeof(int), 0) < 0) - goto fail; - res = emalloc(sizeof(struct pack_res)); - printf("cfd: %d\tn: %d\n", f->cfd, n); - for (i = 0, sum = 0; i < n; i++) { - printf("cfd: %d\tarr[%d]: %d\n", f->cfd, i, arr[i]); - sum += arr[i]; - } - free(arr); - /* - * If we go to `fail:`, `gcc` for some reason double frees if - * we don't manually set it to NULL, even though we explicitly - * check for NULL first... - */ - arr = NULL; - - if ((res->avg = sum / (float)n) > 10.0f) { - (void)strncpy(res->str, "sequence: ok", - sizeof(res->str) - 1); - f->nsucc++; - } else - (void)strncpy(res->str, "sequence: failed", - sizeof(res->str) - 1); - if (send(f->cfd, res, sizeof(struct pack_res), 0) < 0) - goto fail; - f->ntotal++; - printf("[%s] success: %d: total: %d\n", - argv0, f->nsucc, f->ntotal); - - if (recv(f->cfd, &cont, 1, 0) < 0) - goto fail; - if (cont == 'n') - break; - } - rc = 0; - -fail: - printf("[%s] connection with client %d closed\n", argv0, f->cfd); - (void)close(f->cfd); - if (arr != NULL) - free(arr); - if (res != NULL) - free(res); - - return rc; -} - -static void -sighandler(int sig) -{ - f_quit = 1; -} - -static void * -emalloc(size_t nb) -{ - void *p; - - if ((p = malloc(nb)) == NULL) - err(1, "malloc"); - return p; -} - -static void -usage(void) -{ - fprintf(stderr, "usage: %s [-b backlog] [-s sockfile]\n", argv0); - exit(1); -} - -int -main(int argc, char *argv[]) -{ - struct foo *f; - struct sockaddr_un sun; - struct sigaction sa; - char *sockfile = "/tmp/cool.sock"; - int sfd; - int backlog = 10; - char ch; - - argv0 = *argv; - if ((ch = getopt(argc, argv, "b:s:")) != -1) { - switch (ch) { - case 'b': - /* - * Negative `backlog` value normally requests the - * maximum allowable value (HISTORY section of - * listen(2)'s FreeBSD man page), but it's better to - * not allow it in case the user passes a negative - * value accidentally. Also a value of 0 doesn't make - * sense, so we don't allow it either. - */ - if ((backlog = atoi(optarg)) < 1) - usage(); - break; - case 's': - sockfile = optarg; - break; - case '?': - default: - usage(); - } - } - argc -= optind; - argv += optind; - - /* - * Handle termination signals so we don't exit abnormally - * (i.e without cleaning up resources). - */ - (void)memset(&sa, 0, sizeof(sa)); - (void)sigemptyset(&sa.sa_mask); - sa.sa_handler = sighandler; - sa.sa_flags = SA_RESTART; - /*if (sigaction(SIGHUP, &sa, NULL) < 0)*/ - /*err(1, "sigaction: SIGHUP");*/ - /*if (sigaction(SIGINT, &sa, NULL) < 0)*/ - /*err(1, "sigaction: SIGINT");*/ - /*if (sigaction(SIGTERM, &sa, NULL) < 0)*/ - /*err(1, "sigaction: SIGTERM");*/ - - if ((sfd = socket(AF_UNIX, SOCK_STREAM, 0)) < 0) - err(1, "socket"); - (void)memset(&sun, 0, sizeof(sun)); - sun.sun_family = AF_UNIX; - (void)strncpy(sun.sun_path, sockfile, sizeof(sun.sun_path) - 1); - - if (bind(sfd, (struct sockaddr *)&sun, sizeof(sun)) < 0) - err(1, "bind"); - if (listen(sfd, backlog) < 0) - err(1, "listen"); - - f = emalloc(sizeof(struct foo)); - f->nsucc = 0; - f->ntotal = 0; - - for (;;) { - /* FIXME: blocked by accept(2) */ - if (f_quit) - break; - /* - * accept(2)'s `addr` and `addrlen` arguments can be NULL if - * we don't care about the address information of the client. - */ - if ((f->cfd = accept(sfd, NULL, NULL)) < 0) - continue; - printf("[%s] accepted client: %d\n", argv0, f->cfd); - switch (fork()) { - case -1: - err(1, "fork"); - case 0: - if (srv(f) < 0) - warnx("srv failed"); - _exit(0); - default: - (void)close(f->cfd); - } - - } - - /* Will get here only if a termination signal is caught. */ - (void)close(f->cfd); - (void)close(sfd); - free(f); - /* - * bind(2)'s man page states that the socket should be deleted when - * it's no longer needed, otherwise it'll stay there even after - * we exit. - */ - (void)unlink(sockfile); - - return 0; -} diff --git a/c-programming/5-arrays-pointers-files/minecurses/src/audio.h b/c-programming/5-arrays-pointers-files/minecurses/src/audio.h @@ -1,13 +0,0 @@ -#ifndef AUDIO_H -#define AUDIO_H - -#include <SDL2/SDL.h> -#include <SDL2/SDL_mixer.h> - -#define AUDIO_PATH "res/detective-8bit.wav" - -void *play_audio(void *tid); -void volume (char); -void pause_audio(void); - -#endif /* AUDIO_H */ diff --git a/c-data-structures/arrays_ex1.c b/c_data_structures/arrays_ex1.c diff --git a/c-data-structures/arrays_ex2.c b/c_data_structures/arrays_ex2.c diff --git a/c-data-structures/arrays_ex3.c b/c_data_structures/arrays_ex3.c diff --git a/c-data-structures/bintree.c b/c_data_structures/bintree.c diff --git a/c-data-structures/files_ex1.c b/c_data_structures/files_ex1.c diff --git a/c-data-structures/files_ex2.c b/c_data_structures/files_ex2.c diff --git a/c-data-structures/funcs_ex1.c b/c_data_structures/funcs_ex1.c diff --git a/c-data-structures/funcs_ex2.c b/c_data_structures/funcs_ex2.c diff --git a/c-data-structures/funcs_ex3.c b/c_data_structures/funcs_ex3.c diff --git a/c-data-structures/memalloc_ex1.c b/c_data_structures/memalloc_ex1.c diff --git a/c-data-structures/memalloc_ex2.c b/c_data_structures/memalloc_ex2.c diff --git a/c-data-structures/ptrs_ex1.c b/c_data_structures/ptrs_ex1.c diff --git a/c-data-structures/ptrs_ex2.c b/c_data_structures/ptrs_ex2.c diff --git a/c-data-structures/ptrs_ex3.c b/c_data_structures/ptrs_ex3.c diff --git a/c-data-structures/queue.c b/c_data_structures/queue.c diff --git a/c-data-structures/stack_list.c b/c_data_structures/stack_list.c diff --git a/c-os2/ex1/ex1.c b/c_os2/ex1/ex1.c diff --git a/c-os2/ex1/ex2.c b/c_os2/ex1/ex2.c diff --git a/c-os2/ex1/ex3.c b/c_os2/ex1/ex3.c diff --git a/c_os2/ex2/Makefile b/c_os2/ex2/Makefile @@ -0,0 +1,9 @@ +all: + cc ex1_1.c -lpthread -o ex1_1 + cc ex1_2.c -lpthread -o ex1_2 + cc ex2.c -lpthread -DLLIM=10 -DULIM=100 -o ex2 + cc ex3_server.c -lpthread -o ex3_server + cc ex3_client.c -o ex3_client + +clean: + rm -f ex1_1 ex1_2 ex2 ex3_server ex3_client *.core *.o diff --git a/c_os2/ex2/ex1_1.c b/c_os2/ex2/ex1_1.c @@ -0,0 +1,128 @@ +#include <err.h> +#include <pthread.h> +#include <semaphore.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> + +#define LEN(x) (sizeof(x) / sizeof(x[0])) + +/* + * Εργαστήριο ΛΣ2 (Δ6) / Εργασία 2: Άσκηση 1.1 / 2020-2021 + * Ονοματεπώνυμο: Χρήστος Μαργιώλης + * ΑΜ: 19390133 + * Τρόπος μεταγλώττισης: `cc ex1_1.c -lpthread -o ex1_1` + */ + +struct foo { + char *str; + sem_t sem; +}; + +/* Function declarations */ +static void *tdprint(void *); +static void *emalloc(size_t); +static void usage(void); + +/* Global variables */ +static char *argv0; +/* + * Each thread will print one of these. Everything will adapt in case more + * strings are added to the array. + */ +static const char *nums[] = { + "<one>", + "<two>", + "<three>", +}; + +static void * +tdprint(void *foo) +{ + struct foo *f; + + f = (struct foo *)foo; + if (sem_wait(&f->sem) < 0) + err(1, "sem_wait"); + printf("%s", f->str); + /* Prevent memory leak from strdup(2). */ + free(f->str); + if (sem_post(&f->sem) < 0) + err(1, "sem_post"); + + return NULL; +} + +static void * +emalloc(size_t nb) +{ + void *p; + + if ((p = malloc(nb)) == NULL) + err(1, "malloc"); + + return p; +} + +static void +usage(void) +{ + fprintf(stderr, "usage: %s [-n times]\n", argv0); + exit(1); +} + +int +main(int argc, char *argv[]) +{ + struct foo *f; + pthread_t *tds; + int i, len, n = 5; + char ch; + + argv0 = *argv; + while ((ch = getopt(argc, argv, "n:")) != -1) { + switch (ch) { + case 'n': + if ((n = atoi(optarg)) < 1) + usage(); + break; + case '?': + default: + usage(); + } + } + argc -= optind; + argv += optind; + + len = LEN(nums); + /* + * Instead of hardcoding how many threads we want to have, the + * number of threads is always equal to how many elements the + * `nums` array has. That means in case we want to add/remove + * entries from `nums`, everything will adapt automatically. + */ + tds = emalloc(len * sizeof(pthread_t)); + f = emalloc(sizeof(struct foo)); + + if (sem_init(&f->sem, 0, 1) < 0) + err(1, "sem_init"); + while (n--) { + for (i = 0; i < len; i++) { + if ((f->str = strdup(nums[i])) == NULL) + err(1, "strdup"); + if (pthread_create(&tds[i], NULL, tdprint, (void *)f) != 0) + err(1, "pthread_create"); + if (pthread_join(tds[i], NULL) != 0) + err(1, "pthread_join"); + } + } + printf("\n"); + + (void)sem_destroy(&f->sem); + pthread_exit(NULL); + free(tds); + free(f); + + return 0; +} diff --git a/c_os2/ex2/ex1_2.c b/c_os2/ex2/ex1_2.c @@ -0,0 +1,137 @@ +#include <err.h> +#include <pthread.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> + +#define LEN(x) (sizeof(x) / sizeof(x[0])) + +/* + * Εργαστήριο ΛΣ2 (Δ6) / Εργασία 2: Άσκηση 1.2 / 2020-2021 + * Ονοματεπώνυμο: Χρήστος Μαργιώλης + * ΑΜ: 19390133 + * Τρόπος μεταγλώττισης: `cc ex1_2.c -lpthread -o ex1_2` + */ + +struct foo { + char *str; + pthread_mutex_t mtx; + pthread_cond_t cv; + int done; +}; + +/* Function declarations */ +static void *tdprint(void *); +static void *emalloc(size_t); +static void usage(void); + +/* Global variables */ +static char *argv0; +static const char *nums[] = { + "<one>", + "<two>", + "<three>", +}; + +static void * +tdprint(void *foo) +{ + struct foo *f; + + f = (struct foo *)foo; + if (pthread_mutex_lock(&f->mtx) != 0) + err(1, "pthread_mutex_lock"); + /* + * Set the flag to zero so that the other threads will be blocked + * with `pthread_cond_wait`. + */ + f->done = 0; + printf("%s", f->str); + free(f->str); + f->done = 1; + /* If a thread is not done executing the statements above, wait. */ + if (!f->done) { + if (pthread_cond_wait(&f->cv, &f->mtx) != 0) + err(1, "pthread_cond_wait"); + /* We're done, the next thread can do its job now. */ + } else { + if (pthread_cond_signal(&f->cv) != 0) + err(1, "pthread_cond_signal"); + } + if (pthread_mutex_unlock(&f->mtx) != 0) + err(1, "pthread_mutex_unlock"); + + return NULL; +} + +static void * +emalloc(size_t nb) +{ + void *p; + + if ((p = malloc(nb)) == NULL) + err(1, "malloc"); + + return p; +} + +static void +usage(void) +{ + fprintf(stderr, "usage: %s [-n times]\n", argv0); + exit(1); +} + +int +main(int argc, char *argv[]) +{ + struct foo *f; + pthread_t *tds; + int i, len, n = 5; + char ch; + + argv0 = *argv; + while ((ch = getopt(argc, argv, "n:")) != -1) { + switch (ch) { + case 'n': + if ((n = atoi(optarg)) < 1) + usage(); + break; + case '?': + default: + usage(); + } + } + argc -= optind; + argv += optind; + + len = LEN(nums); + tds = emalloc(len * sizeof(pthread_t)); + f = emalloc(sizeof(struct foo)); + + f->done = 0; + if (pthread_mutex_init(&f->mtx, NULL) != 0) + err(1, "pthread_mutex_init"); + if (pthread_cond_init(&f->cv, NULL) != 0) + err(1, "pthread_cond_init"); + while (n--) { + for (i = 0; i < len; i++) { + if ((f->str = strdup(nums[i])) == NULL) + err(1, "strdup"); + if (pthread_create(&tds[i], NULL, tdprint, (void *)f) != 0) + err(1, "pthread_create"); + if (pthread_join(tds[i], NULL) != 0) + err(1, "pthread_join"); + } + } + printf("\n"); + + (void)pthread_mutex_destroy(&f->mtx); + (void)pthread_cond_destroy(&f->cv); + pthread_exit(NULL); + free(tds); + free(f); + + return 0; +} diff --git a/c_os2/ex2/ex2.c b/c_os2/ex2/ex2.c @@ -0,0 +1,198 @@ +#include <err.h> +#include <errno.h> +#include <pthread.h> +#include <stdio.h> +#include <stdlib.h> +#include <time.h> + +/* + * Εργαστήριο ΛΣ2 (Δ6) / Εργασία 2: Άσκηση 2 / 2020-2021 + * Ονοματεπώνυμο: Χρήστος Μαργιώλης + * ΑΜ: 19390133 + * Τρόπος μεταγλώττισης: `cc ex2.c -lpthread -DLLIM=x -DULIM=y -o ex2` + * Όπου `x` και `y` το κάτω και πάνω όριο αντίστοιχα. + */ + +struct foo { + int **g_arr; /* Global array. */ + int **d; /* `d[i][j] = g_max - g_arr[i][j]` */ + int *l_max; /* Local maximums. */ + int g_max; /* Global maximum. */ + int l_n; /* Number of elements for each thread. */ + int n; /* Dimensions. */ + int ntd; /* Number of threads. */ + int tid; /* Thread ID. */ + pthread_mutex_t mtx; + pthread_barrier_t bar; +}; + +/* Function declarations */ +static void *threaded_stuff(void *); +static void *emalloc(size_t); +static void usage(void); + +/* Global variables */ +static char *argv0; + +static void * +threaded_stuff(void *foo) +{ + struct foo *f; + int i, j, start, end, max; + + f = (struct foo *)foo; + /* + * Each thread reads X rows from `g_arr`. Suppose that we have + * 2 threads and a 4x4 array: + * + * row: 0 | 1, 2, 3, 4 | + * row: 1 | 5, 6, 7, 8 | + * row: 2 | 9, 10, 11, 12 | + * row: 3 | 13, 14, 15, 16 | + * + * Each thread now has to work with 2 rows from the array since + * `l_n = n / p = 4 / 2 = 2`. But in order to get the + * correct row, we have to offset it by the thread number. + * + * So, thread 0 will read the following part of `g_arr`: + * start: tid * l_n -> 0 * 2 -> 0 + * end: start + l_n -> 0 + 2 -> 2 + * + * which is the first half of `g_arr`: + * row: 0 | 1, 2, 3, 4 | + * row: 1 | 5, 6, 7, 8 | + * + * Following the same logic, thread 1 will read at: + * start = 1 * 2 -> 2 + * end = 2 + 2 -> 4 + * + * which is the second half of `g_arr`: + * row: 2 | 9, 10, 11, 12 | + * row: 3 | 13, 14, 15, 16 | + * + */ + start = f->tid * f->l_n; + end = start + f->l_n; + + /* Calculate the local max. */ + max = *f->g_arr[start]; + for (i = start; i < end; i++) + for (j = 0; j < f->n; j++) + if (f->g_arr[i][j] > max) + max = f->g_arr[i][j]; + f->l_max[f->tid] = max; + + /* Calculate the global max, no need for more functions. */ + if (pthread_mutex_lock(&f->mtx) != 0) + err(1, "pthread_mutex_lock"); + if (f->tid == 0) + f->g_max = *f->l_max; + else if (f->l_max[f->tid] > f->g_max) + f->g_max = f->l_max[f->tid]; + if (pthread_mutex_unlock(&f->mtx) != 0) + err(1, "pthread_mutex_unlock"); + /* + * Wait for all threads to finish executing the statements above, + * then continue. + * FIXME + */ + (void)pthread_barrier_wait(&f->bar); + if (errno == EINVAL) + err(1, "pthread_barrier_wait"); + + /* Calculate the D array. */ + for (i = start; i < end; i++) + for (j = 0; j < f->n; j++) + f->d[i][j] = f->g_max - f->g_arr[i][j]; + + return NULL; +} + +static void * +emalloc(size_t nb) +{ + void *p; + + if ((p = malloc(nb)) == NULL) + err(1, "malloc"); + + return p; +} + +static void +usage(void) +{ + fprintf(stderr, "usage: %s [-t threads]\n", argv0); + exit(1); +} + +int +main(int argc, char *argv[]) +{ + struct foo *f; + pthread_t *tds; + int i, j; + + argv0 = *argv; + f = emalloc(sizeof(struct foo)); + + do { + printf("p: "); + scanf("%d", &f->ntd); + } while (f->ntd < 0); + + do { + printf("n: "); + scanf("%d", &f->n); + } while (f->n < 0 || f->n % f->ntd != 0); + + tds = emalloc(f->ntd * sizeof(pthread_t)); + f->l_n = f->n / f->ntd; + f->g_arr = emalloc(f->n * sizeof(int *)); + f->l_max = emalloc(f->ntd * sizeof(int)); + f->d = emalloc(f->n * sizeof(int *)); + + srand(time(NULL)); + for (i = 0; i < f->n; i++) { + f->g_arr[i] = emalloc(f->n * sizeof(int)); + f->d[i] = emalloc(f->n * sizeof(int)); + for (j = 0; j < f->n; j++) + f->g_arr[i][j] = rand() % (ULIM - LLIM) + LLIM; + } + + if (pthread_mutex_init(&f->mtx, NULL) != 0) + err(1, "pthread_mutex_init"); + if (pthread_barrier_init(&f->bar, NULL, f->ntd) != 0) + err(1, "pthread_barrier_init"); + + for (i = 0; i < f->ntd; i++) { + f->tid = i; + if (pthread_create(&tds[i], NULL, threaded_stuff, (void *)f) != 0) + err(1, "pthread_create"); + if (pthread_join(tds[i], NULL) != 0) + err(1, "pthread_join"); + } + + /* Print results. */ + for (i = 0; i < f->n; i++) + for (j = 0; j < f->n; j++) + printf("arr[%d][%d]: %d\td[%d][%d]: %d\n", + i, j, f->g_arr[i][j], + i, j, f->d[i][j]); + printf("max: %d\n", f->g_max); + + (void)pthread_barrier_destroy(&f->bar); + (void)pthread_mutex_destroy(&f->mtx); + pthread_exit(NULL); + free(tds); + while (f->n--) { + free(*f->g_arr++); + free(*f->d++); + } + free(f->g_arr); + free(f->l_max); + free(f->d); + free(f); + + return 0; +} diff --git a/c-os2/ex2/ex3_client.c b/c_os2/ex2/ex3_client.c diff --git a/c_os2/ex2/ex3_server.c b/c_os2/ex2/ex3_server.c @@ -0,0 +1,235 @@ +#include <sys/socket.h> +#include <sys/types.h> +#include <sys/un.h> + +#include <err.h> +#include <signal.h> +#include <stdio.h> +#include <stdlib.h> +#include <string.h> +#include <unistd.h> + +/* + * Εργαστήριο ΛΣ2 (Δ6) / Εργασία 2: Άσκηση 3 (server) / 2020-2021 + * Ονοματεπώνυμο: Χρήστος Μαργιώλης + * ΑΜ: 19390133 + * Τρόπος μεταγλώττισης: `cc ex3_server.c -o ex3_server` + */ + +/* Results to be sent back to the client. */ +struct pack_res { + char str[32]; + float avg; +}; + +struct foo { + int cfd; + int nsucc; + int ntotal; +}; + +static int srv(struct foo *); +static void sighandler(int); +static void *emalloc(size_t); + +static char *argv0; +/* Only gets set if a termination signal is caught. */ +static volatile sig_atomic_t f_quit = 0; + +static int +srv(struct foo *foo) +{ + struct foo *f; + struct pack_res *res; + int *arr; + int i, n, sum; + int rc; + char cont; + + /* + * The return code is -1 (error) by default so that we don't + * need to set it everytime an error occurs in the main loop. + * If there are no errors, `rc` will be set to 0 (success) right + * after the loop. + */ + rc = -1; + f = (struct foo *)foo; + for (;;) { + if (recv(f->cfd, &n, sizeof(int), 0) < 0) + goto fail; + arr = emalloc(n * sizeof(int)); + if (recv(f->cfd, arr, n * sizeof(int), 0) < 0) + goto fail; + res = emalloc(sizeof(struct pack_res)); + printf("cfd: %d\tn: %d\n", f->cfd, n); + for (i = 0, sum = 0; i < n; i++) { + printf("cfd: %d\tarr[%d]: %d\n", f->cfd, i, arr[i]); + sum += arr[i]; + } + free(arr); + /* + * If we go to `fail:`, `gcc` for some reason double frees if + * we don't manually set it to NULL, even though we explicitly + * check for NULL first... + */ + arr = NULL; + + if ((res->avg = sum / (float)n) > 10.0f) { + (void)strncpy(res->str, "sequence: ok", + sizeof(res->str) - 1); + f->nsucc++; + } else + (void)strncpy(res->str, "sequence: failed", + sizeof(res->str) - 1); + if (send(f->cfd, res, sizeof(struct pack_res), 0) < 0) + goto fail; + f->ntotal++; + printf("[%s] success: %d: total: %d\n", + argv0, f->nsucc, f->ntotal); + + if (recv(f->cfd, &cont, 1, 0) < 0) + goto fail; + if (cont == 'n') + break; + } + rc = 0; + +fail: + printf("[%s] connection with client %d closed\n", argv0, f->cfd); + (void)close(f->cfd); + if (arr != NULL) + free(arr); + if (res != NULL) + free(res); + + return rc; +} + +static void +sighandler(int sig) +{ + f_quit = 1; +} + +static void * +emalloc(size_t nb) +{ + void *p; + + if ((p = malloc(nb)) == NULL) + err(1, "malloc"); + return p; +} + +static void +usage(void) +{ + fprintf(stderr, "usage: %s [-b backlog] [-s sockfile]\n", argv0); + exit(1); +} + +int +main(int argc, char *argv[]) +{ + struct foo *f; + struct sockaddr_un sun; + struct sigaction sa; + char *sockfile = "/tmp/cool.sock"; + int sfd; + int backlog = 10; + char ch; + + argv0 = *argv; + if ((ch = getopt(argc, argv, "b:s:")) != -1) { + switch (ch) { + case 'b': + /* + * Negative `backlog` value normally requests the + * maximum allowable value (HISTORY section of + * listen(2)'s FreeBSD man page), but it's better to + * not allow it in case the user passes a negative + * value accidentally. Also a value of 0 doesn't make + * sense, so we don't allow it either. + */ + if ((backlog = atoi(optarg)) < 1) + usage(); + break; + case 's': + sockfile = optarg; + break; + case '?': + default: + usage(); + } + } + argc -= optind; + argv += optind; + + /* + * Handle termination signals so we don't exit abnormally + * (i.e without cleaning up resources). + */ + (void)memset(&sa, 0, sizeof(sa)); + (void)sigemptyset(&sa.sa_mask); + sa.sa_handler = sighandler; + sa.sa_flags = SA_RESTART; + /* FIXME*/ + /*if (sigaction(SIGHUP, &sa, NULL) < 0)*/ + /*err(1, "sigaction: SIGHUP");*/ + /*if (sigaction(SIGINT, &sa, NULL) < 0)*/ + /*err(1, "sigaction: SIGINT");*/ + /*if (sigaction(SIGTERM, &sa, NULL) < 0)*/ + /*err(1, "sigaction: SIGTERM");*/ + + if ((sfd = socket(AF_UNIX, SOCK_STREAM, 0)) < 0) + err(1, "socket"); + (void)memset(&sun, 0, sizeof(sun)); + sun.sun_family = AF_UNIX; + (void)strncpy(sun.sun_path, sockfile, sizeof(sun.sun_path) - 1); + + if (bind(sfd, (struct sockaddr *)&sun, sizeof(sun)) < 0) + err(1, "bind"); + if (listen(sfd, backlog) < 0) + err(1, "listen"); + + f = emalloc(sizeof(struct foo)); + f->nsucc = 0; + f->ntotal = 0; + + for (;;) { + /* FIXME: blocked by accept(2) */ + if (f_quit) + break; + /* + * accept(2)'s `addr` and `addrlen` arguments can be NULL if + * we don't care about the address information of the client. + */ + if ((f->cfd = accept(sfd, NULL, NULL)) < 0) + continue; + printf("[%s] accepted client: %d\n", argv0, f->cfd); + switch (fork()) { + case -1: + err(1, "fork"); + case 0: + if (srv(f) < 0) + warnx("srv failed"); + _exit(0); + default: + (void)close(f->cfd); + } + + } + + /* Will get here only if a termination signal is caught. */ + (void)close(f->cfd); + (void)close(sfd); + free(f); + /* + * bind(2)'s man page states that the socket should be deleted when + * it's no longer needed, otherwise it'll stay there even after + * we exit. + */ + (void)unlink(sockfile); + + return 0; +} diff --git a/c-os2/lab2_fifo.c b/c_os2/lab2_fifo.c diff --git a/c-os2/lab2_pipe.c b/c_os2/lab2_pipe.c diff --git a/c-parallel-computing/ex1/doc.pdf b/c_parallel_computing/ex1/doc.pdf Binary files differ. diff --git a/c-parallel-computing/ex1/doc.tex b/c_parallel_computing/ex1/doc.tex diff --git a/c-parallel-computing/ex1/ex1.c b/c_parallel_computing/ex1/ex1.c diff --git a/c-parallel-computing/ex1/res/exmpl1.png b/c_parallel_computing/ex1/res/exmpl1.png Binary files differ. diff --git a/c-parallel-computing/ex1/res/exmpl2.png b/c_parallel_computing/ex1/res/exmpl2.png Binary files differ. diff --git a/c-parallel-computing/ex1/res/exmpl3.png b/c_parallel_computing/ex1/res/exmpl3.png Binary files differ. diff --git a/c-parallel-computing/ex1/res/exmpl4.png b/c_parallel_computing/ex1/res/exmpl4.png Binary files differ. diff --git a/c-parallel-computing/ex2/data b/c_parallel_computing/ex2/data diff --git a/c-parallel-computing/ex2/doc.pdf b/c_parallel_computing/ex2/doc.pdf Binary files differ. diff --git a/c-parallel-computing/ex2/doc.tex b/c_parallel_computing/ex2/doc.tex diff --git a/c-parallel-computing/ex2/ex2.c b/c_parallel_computing/ex2/ex2.c diff --git a/c-parallel-computing/ex2/res/run1.png b/c_parallel_computing/ex2/res/run1.png Binary files differ. diff --git a/c-parallel-computing/ex2/res/run2.png b/c_parallel_computing/ex2/res/run2.png Binary files differ. diff --git a/c-parallel-computing/ex2/res/run3.png b/c_parallel_computing/ex2/res/run3.png Binary files differ. diff --git a/c-programming/1-basic-elements/C1a-CORRECTED.c b/c_programming/1_basic_elements/C1a_correct.c diff --git a/c-programming/1-basic-elements/Cube-Sphere.c b/c_programming/1_basic_elements/Cube_Sphere.c diff --git a/c-programming/1-basic-elements/IO-Exercise.c b/c_programming/1_basic_elements/IO_Exercise.c diff --git a/c-programming/1-basic-elements/docs/assignment-1.odt b/c_programming/1_basic_elements/docs/assignment_1.odt Binary files differ. diff --git a/c-programming/1-basic-elements/docs/assignment-1.pdf b/c_programming/1_basic_elements/docs/assignment_1.pdf Binary files differ. diff --git a/c-programming/2-conditional-statements/docs/assignment-2.odt b/c_programming/2_conditional_statements/docs/assignment_2.odt Binary files differ. diff --git a/c-programming/2-conditional-statements/docs/assignment-2.pdf b/c_programming/2_conditional_statements/docs/assignment_2.pdf Binary files differ. diff --git a/c-programming/2-conditional-statements/int-comparison.c b/c_programming/2_conditional_statements/int_comparison.c diff --git a/c-programming/2-conditional-statements/quadratic-equation.c b/c_programming/2_conditional_statements/quadratic_equation.c diff --git a/c-programming/3-loops/docs/assignment-3.odt b/c_programming/3_loops/docs/assignment_3.odt Binary files differ. diff --git a/c-programming/3-loops/docs/assignment-3.pdf b/c_programming/3_loops/docs/assignment_3.pdf Binary files differ. diff --git a/c-programming/3-loops/int-calcs.c b/c_programming/3_loops/int_calcs.c diff --git a/c-programming/3-loops/shapes.c b/c_programming/3_loops/shapes.c diff --git a/c-programming/3-loops/sine-taylor.c b/c_programming/3_loops/sine_taylor.c diff --git a/c-programming/4-functions/docs/assignment-4.odt b/c_programming/4_functions/docs/assignment_4.odt Binary files differ. diff --git a/c-programming/4-functions/docs/assignment-4.pdf b/c_programming/4_functions/docs/assignment_4.pdf Binary files differ. diff --git a/c-programming/4-functions/docs/photos-diagrams/hanoi-end.png b/c_programming/4_functions/docs/photos_diagrams/hanoi_end.png Binary files differ. diff --git a/c-programming/4-functions/docs/photos-diagrams/hanoi-start.png b/c_programming/4_functions/docs/photos_diagrams/hanoi_start.png Binary files differ. diff --git a/c-programming/4-functions/docs/photos-diagrams/menu-diagram.drawio b/c_programming/4_functions/docs/photos_diagrams/menu_diagram.drawio diff --git a/c-programming/4-functions/docs/photos-diagrams/menu-diagram.png b/c_programming/4_functions/docs/photos_diagrams/menu_diagram.png Binary files differ. diff --git a/c-programming/4-functions/docs/photos-diagrams/sct-diagram.drawio b/c_programming/4_functions/docs/photos_diagrams/sct_diagram.drawio diff --git a/c-programming/4-functions/docs/photos-diagrams/sct-diagram.jpg b/c_programming/4_functions/docs/photos_diagrams/sct_diagram.jpg Binary files differ. diff --git a/c-programming/4-functions/hanoi-tower/Makefile b/c_programming/4_functions/hanoi_tower/Makefile diff --git a/c-programming/4-functions/hanoi-tower/src/hanoi-tower.c b/c_programming/4_functions/hanoi_tower/src/hanoi_tower.c diff --git a/c-programming/4-functions/menu/Makefile b/c_programming/4_functions/menu/Makefile diff --git a/c-programming/4-functions/menu/include/menu.h b/c_programming/4_functions/menu/include/menu.h diff --git a/c-programming/4-functions/menu/src/main.c b/c_programming/4_functions/menu/src/main.c diff --git a/c-programming/4-functions/menu/src/menu.c b/c_programming/4_functions/menu/src/menu.c diff --git a/c-programming/4-functions/sine-cos-taylor/Makefile b/c_programming/4_functions/sine_cos_taylor/Makefile diff --git a/c-programming/4-functions/sine-cos-taylor/include/sine-cos-taylor.h b/c_programming/4_functions/sine_cos_taylor/include/sine_cos_taylor.h diff --git a/c-programming/4-functions/sine-cos-taylor/src/main.c b/c_programming/4_functions/sine_cos_taylor/src/main.c diff --git a/c-programming/4-functions/sine-cos-taylor/src/sine-cos-taylor.c b/c_programming/4_functions/sine_cos_taylor/src/sine_cos_taylor.c diff --git a/c-programming/5-arrays-pointers-files/combinations/Makefile b/c_programming/5_arrays_ptrs_files/combinations/Makefile diff --git a/c-programming/5-arrays-pointers-files/combinations/include/arrhandler.h b/c_programming/5_arrays_ptrs_files/combinations/include/arrhandler.h diff --git a/c-programming/5-arrays-pointers-files/combinations/include/ccolors.h b/c_programming/5_arrays_ptrs_files/combinations/include/ccolors.h diff --git a/c-programming/5-arrays-pointers-files/combinations/include/combinations.h b/c_programming/5_arrays_ptrs_files/combinations/include/combinations.h diff --git a/c-programming/5-arrays-pointers-files/combinations/src/arrhandler.c b/c_programming/5_arrays_ptrs_files/combinations/src/arrhandler.c diff --git a/c-programming/5-arrays-pointers-files/combinations/src/combinations.c b/c_programming/5_arrays_ptrs_files/combinations/src/combinations.c diff --git a/c-programming/5-arrays-pointers-files/combinations/src/main.c b/c_programming/5_arrays_ptrs_files/combinations/src/main.c diff --git a/c-programming/5-arrays-pointers-files/combinations/txt/data.txt b/c_programming/5_arrays_ptrs_files/combinations/txt/data.txt diff --git a/c-programming/5-arrays-pointers-files/combinations/txt/data40.txt b/c_programming/5_arrays_ptrs_files/combinations/txt/data40.txt diff --git a/c-programming/5-arrays-pointers-files/combinations/txt/data49.txt b/c_programming/5_arrays_ptrs_files/combinations/txt/data49.txt diff --git a/c-programming/5-arrays-pointers-files/combinations/txt/data7.txt b/c_programming/5_arrays_ptrs_files/combinations/txt/data7.txt diff --git a/c-programming/5-arrays-pointers-files/docs/assignment-5.pdf b/c_programming/5_arrays_ptrs_files/docs/assignment_5.pdf Binary files differ. diff --git a/c-programming/5-arrays-pointers-files/docs/assignment-5.tex b/c_programming/5_arrays_ptrs_files/docs/assignment_5.tex diff --git a/c-programming/5-arrays-pointers-files/fcombinations/Makefile b/c_programming/5_arrays_ptrs_files/fcombinations/Makefile diff --git a/c-programming/5-arrays-pointers-files/fcombinations/include/arrhandler.h b/c_programming/5_arrays_ptrs_files/fcombinations/include/arrhandler.h diff --git a/c-programming/5-arrays-pointers-files/fcombinations/include/ccolors.h b/c_programming/5_arrays_ptrs_files/fcombinations/include/ccolors.h diff --git a/c-programming/5-arrays-pointers-files/fcombinations/include/fcombinations.h b/c_programming/5_arrays_ptrs_files/fcombinations/include/fcombinations.h diff --git a/c-programming/5-arrays-pointers-files/fcombinations/src/arrhandler.c b/c_programming/5_arrays_ptrs_files/fcombinations/src/arrhandler.c diff --git a/c-programming/5-arrays-pointers-files/fcombinations/src/fcombinations.c b/c_programming/5_arrays_ptrs_files/fcombinations/src/fcombinations.c diff --git a/c-programming/5-arrays-pointers-files/fcombinations/src/main.c b/c_programming/5_arrays_ptrs_files/fcombinations/src/main.c diff --git a/c-programming/5-arrays-pointers-files/fcombinations/txt/data.txt b/c_programming/5_arrays_ptrs_files/fcombinations/txt/data.txt diff --git a/c-programming/5-arrays-pointers-files/fcombinations/txt/data40.txt b/c_programming/5_arrays_ptrs_files/fcombinations/txt/data40.txt diff --git a/c-programming/5-arrays-pointers-files/fcombinations/txt/data49.txt b/c_programming/5_arrays_ptrs_files/fcombinations/txt/data49.txt diff --git a/c-programming/5-arrays-pointers-files/fcombinations/txt/data7.txt b/c_programming/5_arrays_ptrs_files/fcombinations/txt/data7.txt diff --git a/c-programming/5-arrays-pointers-files/kcombinations/Makefile b/c_programming/5_arrays_ptrs_files/kcombinations/Makefile diff --git a/c-programming/5-arrays-pointers-files/kcombinations/include/arrhandler.h b/c_programming/5_arrays_ptrs_files/kcombinations/include/arrhandler.h diff --git a/c-programming/5-arrays-pointers-files/kcombinations/include/ccolors.h b/c_programming/5_arrays_ptrs_files/kcombinations/include/ccolors.h diff --git a/c-programming/5-arrays-pointers-files/kcombinations/include/kcombinations.h b/c_programming/5_arrays_ptrs_files/kcombinations/include/kcombinations.h diff --git a/c-programming/5-arrays-pointers-files/kcombinations/src/arrhandler.c b/c_programming/5_arrays_ptrs_files/kcombinations/src/arrhandler.c diff --git a/c-programming/5-arrays-pointers-files/kcombinations/src/kcombinations.c b/c_programming/5_arrays_ptrs_files/kcombinations/src/kcombinations.c diff --git a/c-programming/5-arrays-pointers-files/kcombinations/src/main.c b/c_programming/5_arrays_ptrs_files/kcombinations/src/main.c diff --git a/c-programming/5-arrays-pointers-files/kcombinations/txt/kdata.txt b/c_programming/5_arrays_ptrs_files/kcombinations/txt/kdata.txt diff --git a/c-programming/5-arrays-pointers-files/kcombinations/txt/kdata40.txt b/c_programming/5_arrays_ptrs_files/kcombinations/txt/kdata40.txt diff --git a/c-programming/5-arrays-pointers-files/kcombinations/txt/kdata49.txt b/c_programming/5_arrays_ptrs_files/kcombinations/txt/kdata49.txt diff --git a/c-programming/5-arrays-pointers-files/minecurses/Makefile b/c_programming/5_arrays_ptrs_files/minecurses/Makefile diff --git a/c-programming/5-arrays-pointers-files/minecurses/README.md b/c_programming/5_arrays_ptrs_files/minecurses/README.md diff --git a/c-programming/5-arrays-pointers-files/minecurses/log/scorelog.csv b/c_programming/5_arrays_ptrs_files/minecurses/log/scorelog.csv diff --git a/c-programming/5-arrays-pointers-files/minecurses/log/session.txt b/c_programming/5_arrays_ptrs_files/minecurses/log/session.txt diff --git a/c-programming/5-arrays-pointers-files/minecurses/res/detective-8bit.wav b/c_programming/5_arrays_ptrs_files/minecurses/res/detective_8bit.wav Binary files differ. diff --git a/c-programming/5-arrays-pointers-files/minecurses/src/audio.c b/c_programming/5_arrays_ptrs_files/minecurses/src/audio.c diff --git a/c_programming/5_arrays_ptrs_files/minecurses/src/audio.h b/c_programming/5_arrays_ptrs_files/minecurses/src/audio.h @@ -0,0 +1,13 @@ +#ifndef AUDIO_H +#define AUDIO_H + +#include <SDL2/SDL.h> +#include <SDL2/SDL_mixer.h> + +#define AUDIO_PATH "res/detective_8bit.wav" + +void *play_audio(void *tid); +void volume (char); +void pause_audio(void); + +#endif /* AUDIO_H */ diff --git a/c-programming/5-arrays-pointers-files/minecurses/src/gameplay.c b/c_programming/5_arrays_ptrs_files/minecurses/src/gameplay.c diff --git a/c-programming/5-arrays-pointers-files/minecurses/src/gameplay.h b/c_programming/5_arrays_ptrs_files/minecurses/src/gameplay.h diff --git a/c-programming/5-arrays-pointers-files/minecurses/src/main.c b/c_programming/5_arrays_ptrs_files/minecurses/src/main.c diff --git a/c-programming/5-arrays-pointers-files/minecurses/src/main.h b/c_programming/5_arrays_ptrs_files/minecurses/src/main.h diff --git a/c-programming/5-arrays-pointers-files/minecurses/src/minesweeper.c b/c_programming/5_arrays_ptrs_files/minecurses/src/minesweeper.c diff --git a/c-programming/5-arrays-pointers-files/minecurses/src/minesweeper.h b/c_programming/5_arrays_ptrs_files/minecurses/src/minesweeper.h diff --git a/c-programming/5-arrays-pointers-files/minecurses/src/navigation.c b/c_programming/5_arrays_ptrs_files/minecurses/src/navigation.c diff --git a/c-programming/5-arrays-pointers-files/minecurses/src/navigation.h b/c_programming/5_arrays_ptrs_files/minecurses/src/navigation.h diff --git a/c-programming/5-arrays-pointers-files/minecurses/src/outputs.c b/c_programming/5_arrays_ptrs_files/minecurses/src/outputs.c diff --git a/c-programming/5-arrays-pointers-files/minecurses/src/outputs.h b/c_programming/5_arrays_ptrs_files/minecurses/src/outputs.h diff --git a/c-programming/5-arrays-pointers-files/minecurses/src/settings.c b/c_programming/5_arrays_ptrs_files/minecurses/src/settings.c diff --git a/c-programming/5-arrays-pointers-files/minecurses/src/settings.h b/c_programming/5_arrays_ptrs_files/minecurses/src/settings.h diff --git a/c-programming/5-arrays-pointers-files/minecurses/src/wins.c b/c_programming/5_arrays_ptrs_files/minecurses/src/wins.c diff --git a/c-programming/5-arrays-pointers-files/minecurses/src/wins.h b/c_programming/5_arrays_ptrs_files/minecurses/src/wins.h diff --git a/cpp-oop/game/Engine.cc b/cpp-oop/game/Engine.cc @@ -1,364 +0,0 @@ -#include "Engine.hpp" - -enum Color { - WALL = 1, - PATH, - POTTER, - GNOME, - TRAAL, - LAST -}; - -Engine::Engine(const char *mapfile, const char *scorefile) -{ - if (!load_map(mapfile)) - throw "load_map failed: " + std::string(mapfile); - if (!init_curses()) - throw "init_curses failed"; - if (!init_entities()) - throw "init_entities failed"; - if (!init_score(scorefile)) - throw "init_score failed: " + std::string(scorefile); - f_running = 1; -} - - -Engine::~Engine() -{ - player = nullptr; - for (auto&& e : entities) - delete e; - delete score; - map.clear(); - colors.clear(); - (void)delwin(gw); - (void)endwin(); -} - -/* Private methods */ - -bool -Engine::load_map(const char *mapfile) -{ - std::ifstream f; - std::vector<char> row; - char c; - - f.exceptions(std::ifstream::badbit); - f.open(mapfile); - if (!f.is_open()) - return false; - while (f.get(c)) { - if (f.eof()) - break; - row.push_back(c); - if (c == '\n') { - /* XXX: h != hprev */ - w = row.size(); - map.push_back(row); - row.clear(); - } - } - f.close(); - h = map.size(); - - return true; -} - -/* Initialize curses(3) environment */ -bool -Engine::init_curses() -{ - int wr, wc, wy, wx; - - if (!initscr()) - return false; - noecho(); - cbreak(); - curs_set(false); - /* Allow arrow key presses. */ - keypad(stdscr, true); - /* ESC has a small delay after it's pressed, so remove it. */ - set_escdelay(0); - /* Don't wait for a keypress, just continue if there's nothing. */ - timeout(1000); - - xmax = getmaxx(stdscr); - ymax = getmaxy(stdscr); - - wr = h; - wc = w; - wy = CENTER(ymax, wr); - wx = CENTER(xmax, wc); - if ((gw = newwin(wr, wc, wy, wx)) == NULL) - return false; - box(gw, 0, 0); - wxmax = getmaxx(gw); - wymax = getmaxy(gw); - - colors.push_back(COLOR_BLUE); /* Wall */ - colors.push_back(COLOR_RED); /* Path */ - colors.push_back(COLOR_CYAN); /* Potter */ - colors.push_back(COLOR_GREEN); /* Gnome */ - colors.push_back(COLOR_YELLOW); /* Traal */ - - start_color(); - use_default_colors(); - for (int i = 1; i < Color::LAST; i++) - (void)init_pair(i, colors[i-1], -1); - - return true; -} - -bool -Engine::collides_with_wall(int x, int y) -{ - if (x < w && y < h) - return map[y][x] == '*'; - return true; -} - -void -Engine::calc_pos(int *x, int *y) -{ - do { - *x = rand() % w; - *y = rand() % h; - /* - * Don't spawn an enemy at the same coordinates with - * another entity. - */ - for (const auto& e : entities) - if (*x == e->get_x() && *y == e->get_y()) - continue; - } while (collides_with_wall(*x, *y)); -} - -bool -Engine::init_entities() -{ - int i, x, y, type; - - srand(time(nullptr)); - - calc_pos(&x, &y); - entities.push_back(new Potter(x, y, Movable::Direction::DOWN, 'P')); - for (i = 0; i < nenemies; i++) { - calc_pos(&x, &y); - /* - * Randomly choose whether we'll create a `Gnome` or - * `Traal` enemy. - */ - switch (type = rand() % 2) { - case 0: - entities.push_back(new Gnome(x, y, - Movable::Direction::DOWN, 'G')); - break; - case 1: - entities.push_back(new Traal(x, y, - Movable::Direction::DOWN, 'T')); - break; - } - } - player = (Potter *)entities[0]; - - return true; -} - -bool -Engine::init_score(const char *scorefile) -{ - score = new Score(scorefile); - - return true; -} - -void -Engine::ctrl_menu() -{ - WINDOW *opts; - int wr, wc, wy, wx; - - wc = 32; - wr = 9; - wx = CENTER(xmax, wc); - wy = CENTER(ymax, wr); - if ((opts = newwin(wr, wc, wy, wx)) == NULL) - return; - werase(opts); - box(opts, 0, 0); - - mvwprintw(opts, 1, 1, "Up Move up"); - mvwprintw(opts, 2, 1, "Down Move down"); - mvwprintw(opts, 3, 1, "Left Move left"); - mvwprintw(opts, 4, 1, "Right Move right"); - mvwprintw(opts, 5, 1, "ESC Quit"); - mvwprintw(opts, 7, 1, "Press any key to quit the menu"); - - wrefresh(opts); - (void)wgetch(opts); - werase(opts); - wrefresh(opts); - (void)delwin(opts); -} - -void -Engine::calc_dist(std::map<int, int>& dists, int ex, int ey, int dir) -{ - int px, py, dx, dy, d; - - px = player->get_x(); - py = player->get_y(); - dx = ex - px; - dy = ey - py; - d = floor(sqrt(dx * dx + dy * dy)); - dists.insert(std::pair<int, int>(d, dir)); -} - -/* Public methods */ - -void -Engine::kbd_input() -{ - int key, dir, newx, newy; - - newx = player->get_x(); - newy = player->get_y(); - - switch (key = getch()) { - case KEY_LEFT: - newx--; - dir = Movable::Direction::LEFT; - break; - case KEY_RIGHT: - newx++; - dir = Movable::Direction::RIGHT; - break; - case KEY_UP: - newy--; - dir = Movable::Direction::UP; - break; - case KEY_DOWN: - newy++; - dir = Movable::Direction::DOWN; - break; - case 'c': - ctrl_menu(); - return; - case ESC: /* FALLTHROUGH */ - /* FIXME: what? */ - f_running = 0; - default: - return; - } - - if (!collides_with_wall(newx, newy)) - player->set_newpos(dir, wxmax, wymax); -} - -/* FIXME: move asynchronously */ -void -Engine::enemies_move() -{ - std::map<int, int> dists; - int ex, ey; - auto distcmp = [](const std::pair<int, int>& a, const std::pair<int, int>& b) { - return a.first < b.second; - }; - - for (const auto& e : entities) { - if (e == player) - continue; - ex = e->get_x(); - ey = e->get_y(); - dists.clear(); - /* West */ - if (!collides_with_wall(ex - 1, ey)) - calc_dist(dists, ex - 1, ey, Movable::Direction::LEFT); - /* East */ - if (!collides_with_wall(ex + 1, ey)) - calc_dist(dists, ex + 1, ey, Movable::Direction::RIGHT); - /* North */ - if (!collides_with_wall(ex, ey - 1)) - calc_dist(dists, ex, ey - 1, Movable::Direction::UP); - /* South */ - if (!collides_with_wall(ex, ey + 1)) - calc_dist(dists, ex, ey + 1, Movable::Direction::DOWN); - - if (!dists.empty()) { - auto min = std::min_element(dists.begin(), - dists.end(), distcmp); - e->set_newpos(min->second, wxmax, wymax); - } - } -} - -void -Engine::collisions() -{ - int px, py, ex, ey; - - px = player->get_x(); - py = player->get_y(); - - for (const auto& e : entities) { - ex = e->get_x(); - ey = e->get_y(); - if (e != player && px == ex && py == ey) { - /* TODO: increase score */ - } - } -} - -void -Engine::upd_score() -{ -} - -void -Engine::redraw() -{ - char msg_score[] = "Score: %d"; - char msg_opts[] = "c Controls"; - int color; - - /* TODO: print more info */ - werase(gw); - erase(); - mvprintw(0, 0, "Potter: (%d, %d)", player->get_x(), player->get_y()); - mvprintw(0, CENTER(xmax, strlen(msg_score)), msg_score, 10); - mvprintw(0, xmax - strlen(msg_opts), msg_opts); - mvhline(1, 0, ACS_HLINE, xmax); - wattron(gw, A_REVERSE); - for (const auto& row : map) { - for (const auto& c : row) { - if (c == '*') - color = COLOR_PAIR(Color::WALL); - else if (c == ' ') - color = COLOR_PAIR(Color::PATH); - wattron(gw, color); - waddch(gw, c); - wattroff(gw, color); - } - } - for (const auto& e : entities) { - if (dynamic_cast<Potter *>(e) != nullptr) - color = COLOR_PAIR(Color::POTTER); - else if (dynamic_cast<Gnome *>(e) != nullptr) - color = COLOR_PAIR(Color::GNOME); - else if (dynamic_cast<Traal *>(e) != nullptr) - color = COLOR_PAIR(Color::TRAAL); - wattron(gw, color); - mvwaddch(gw, e->get_y(), e->get_x(), e->get_sym()); - wattroff(gw, color); - } - wattroff(gw, A_REVERSE); - refresh(); - wrefresh(gw); -} - -bool -Engine::is_running() -{ - return f_running; -} diff --git a/cpp-oop/1-fromctocpp/fromctocpp.cpp b/cpp_oop/1_fromctocpp/fromctocpp.cpp diff --git a/cpp-oop/2-classes/classes.cpp b/cpp_oop/2_classes/classes.cpp diff --git a/cpp-oop/3-operoverloading/Makefile b/cpp_oop/3_operoverloading/Makefile diff --git a/cpp-oop/3-operoverloading/src/course.cpp b/cpp_oop/3_operoverloading/src/course.cpp diff --git a/cpp-oop/3-operoverloading/src/course.hpp b/cpp_oop/3_operoverloading/src/course.hpp diff --git a/cpp-oop/3-operoverloading/src/main.cpp b/cpp_oop/3_operoverloading/src/main.cpp diff --git a/cpp-oop/3-operoverloading/src/student.cpp b/cpp_oop/3_operoverloading/src/student.cpp diff --git a/cpp-oop/3-operoverloading/src/student.hpp b/cpp_oop/3_operoverloading/src/student.hpp diff --git a/cpp-oop/4-inheritance/Makefile b/cpp_oop/4_inheritance/Makefile diff --git a/cpp-oop/4-inheritance/res/appdata.csv b/cpp_oop/4_inheritance/res/appdata.csv diff --git a/cpp-oop/4-inheritance/res/appdata_out.csv b/cpp_oop/4_inheritance/res/appdata_out.csv diff --git a/cpp-oop/4-inheritance/res/errlog.txt b/cpp_oop/4_inheritance/res/errlog.txt diff --git a/cpp-oop/4-inheritance/res/manfdata.csv b/cpp_oop/4_inheritance/res/manfdata.csv diff --git a/cpp-oop/4-inheritance/res/manfdata_out.csv b/cpp_oop/4_inheritance/res/manfdata_out.csv diff --git a/cpp-oop/4-inheritance/res/revs.csv b/cpp_oop/4_inheritance/res/revs.csv diff --git a/cpp-oop/4-inheritance/res/revs_out.csv b/cpp_oop/4_inheritance/res/revs_out.csv diff --git a/cpp-oop/4-inheritance/src/app.cpp b/cpp_oop/4_inheritance/src/app.cpp diff --git a/cpp-oop/4-inheritance/src/app.hpp b/cpp_oop/4_inheritance/src/app.hpp diff --git a/cpp-oop/4-inheritance/src/appsystem.cpp b/cpp_oop/4_inheritance/src/appsystem.cpp diff --git a/cpp-oop/4-inheritance/src/appsystem.hpp b/cpp_oop/4_inheritance/src/appsystem.hpp diff --git a/cpp-oop/4-inheritance/src/errlog.cpp b/cpp_oop/4_inheritance/src/errlog.cpp diff --git a/cpp-oop/4-inheritance/src/errlog.hpp b/cpp_oop/4_inheritance/src/errlog.hpp diff --git a/cpp-oop/4-inheritance/src/game.cpp b/cpp_oop/4_inheritance/src/game.cpp diff --git a/cpp-oop/4-inheritance/src/game.hpp b/cpp_oop/4_inheritance/src/game.hpp diff --git a/cpp-oop/4-inheritance/src/main.cpp b/cpp_oop/4_inheritance/src/main.cpp diff --git a/cpp-oop/4-inheritance/src/manufacturer.cpp b/cpp_oop/4_inheritance/src/manufacturer.cpp diff --git a/cpp-oop/4-inheritance/src/manufacturer.hpp b/cpp_oop/4_inheritance/src/manufacturer.hpp diff --git a/cpp-oop/4-inheritance/src/office.cpp b/cpp_oop/4_inheritance/src/office.cpp diff --git a/cpp-oop/4-inheritance/src/office.hpp b/cpp_oop/4_inheritance/src/office.hpp diff --git a/cpp-oop/4-inheritance/src/review.cpp b/cpp_oop/4_inheritance/src/review.cpp diff --git a/cpp-oop/4-inheritance/src/review.hpp b/cpp_oop/4_inheritance/src/review.hpp diff --git a/cpp-oop/5-spreadsheets/Makefile b/cpp_oop/5_spreadsheets/Makefile diff --git a/cpp-oop/5-spreadsheets/res/courses.csv b/cpp_oop/5_spreadsheets/res/courses.csv diff --git a/cpp-oop/5-spreadsheets/res/equivalencies.csv b/cpp_oop/5_spreadsheets/res/equivalencies.csv diff --git a/cpp-oop/5-spreadsheets/res/errlog.csv b/cpp_oop/5_spreadsheets/res/errlog.csv diff --git a/cpp-oop/5-spreadsheets/res/grades.csv b/cpp_oop/5_spreadsheets/res/grades.csv diff --git a/cpp-oop/5-spreadsheets/res/report.csv b/cpp_oop/5_spreadsheets/res/report.csv diff --git a/cpp-oop/5-spreadsheets/res/students.csv b/cpp_oop/5_spreadsheets/res/students.csv diff --git a/cpp-oop/5-spreadsheets/src/course.hpp b/cpp_oop/5_spreadsheets/src/course.hpp diff --git a/cpp-oop/5-spreadsheets/src/datahandler.cpp b/cpp_oop/5_spreadsheets/src/datahandler.cpp diff --git a/cpp-oop/5-spreadsheets/src/datahandler.hpp b/cpp_oop/5_spreadsheets/src/datahandler.hpp diff --git a/cpp-oop/5-spreadsheets/src/errlog.cpp b/cpp_oop/5_spreadsheets/src/errlog.cpp diff --git a/cpp-oop/5-spreadsheets/src/errlog.hpp b/cpp_oop/5_spreadsheets/src/errlog.hpp diff --git a/cpp-oop/5-spreadsheets/src/main.cpp b/cpp_oop/5_spreadsheets/src/main.cpp diff --git a/cpp-oop/5-spreadsheets/src/student.hpp b/cpp_oop/5_spreadsheets/src/student.hpp diff --git a/cpp-oop/5-spreadsheets/src/xstring.cpp b/cpp_oop/5_spreadsheets/src/xstring.cpp diff --git a/cpp-oop/5-spreadsheets/src/xstring.hpp b/cpp_oop/5_spreadsheets/src/xstring.hpp diff --git a/cpp_oop/game/Engine.cc b/cpp_oop/game/Engine.cc @@ -0,0 +1,366 @@ +#include "Engine.hpp" + +enum Color { + WALL = 1, + PATH, + POTTER, + GNOME, + TRAAL, + LAST +}; + +/* TODO: intro message and stuff? */ +Engine::Engine(const char *mapfile, const char *scorefile) +{ + if (!load_map(mapfile)) + throw "load_map failed: " + std::string(mapfile); + if (!init_curses()) + throw "init_curses failed"; + if (!init_entities()) + throw "init_entities failed"; + if (!init_score(scorefile)) + throw "init_score failed: " + std::string(scorefile); + f_running = 1; +} + + +Engine::~Engine() +{ + player = nullptr; + for (auto&& e : entities) + delete e; + delete score; + map.clear(); + colors.clear(); + (void)delwin(gw); + (void)endwin(); +} + +/* Private methods */ + +/* XXX: getline? */ +bool +Engine::load_map(const char *mapfile) +{ + std::ifstream f; + std::vector<char> row; + char c; + + f.exceptions(std::ifstream::badbit); + f.open(mapfile); + if (!f.is_open()) + return false; + while (f.get(c)) { + if (f.eof()) + break; + row.push_back(c); + if (c == '\n') { + /* XXX: h != hprev */ + w = row.size(); + map.push_back(row); + row.clear(); + } + } + f.close(); + h = map.size(); + + return true; +} + +/* Initialize curses(3) environment */ +bool +Engine::init_curses() +{ + int wr, wc, wy, wx; + + if (!initscr()) + return false; + noecho(); + cbreak(); + curs_set(false); + /* Allow arrow key presses. */ + keypad(stdscr, true); + /* ESC has a small delay after it's pressed, so remove it. */ + set_escdelay(0); + /* Don't wait for a keypress, just continue if there's nothing. */ + timeout(1000); + + xmax = getmaxx(stdscr); + ymax = getmaxy(stdscr); + + wr = h; + wc = w; + wy = CENTER(ymax, wr); + wx = CENTER(xmax, wc); + if ((gw = newwin(wr, wc, wy, wx)) == NULL) + return false; + box(gw, 0, 0); + wxmax = getmaxx(gw); + wymax = getmaxy(gw); + + colors.push_back(COLOR_BLUE); /* Wall */ + colors.push_back(COLOR_RED); /* Path */ + colors.push_back(COLOR_CYAN); /* Potter */ + colors.push_back(COLOR_GREEN); /* Gnome */ + colors.push_back(COLOR_YELLOW); /* Traal */ + + start_color(); + use_default_colors(); + for (int i = 1; i < Color::LAST; i++) + (void)init_pair(i, colors[i-1], -1); + + return true; +} + +bool +Engine::collides_with_wall(int x, int y) +{ + if (x < w && y < h) + return map[y][x] == '*'; + return true; +} + +void +Engine::calc_pos(int *x, int *y) +{ + do { + *x = rand() % w; + *y = rand() % h; + /* + * Don't spawn an enemy at the same coordinates with + * another entity. + */ + for (const auto& e : entities) + if (*x == e->get_x() && *y == e->get_y()) + continue; + } while (collides_with_wall(*x, *y)); +} + +bool +Engine::init_entities() +{ + int i, x, y, type; + + srand(time(nullptr)); + + calc_pos(&x, &y); + entities.push_back(new Potter(x, y, Movable::Direction::DOWN, 'P')); + for (i = 0; i < nenemies; i++) { + calc_pos(&x, &y); + /* + * Randomly choose whether we'll create a `Gnome` or + * `Traal` enemy. + */ + switch (type = rand() % 2) { + case 0: + entities.push_back(new Gnome(x, y, + Movable::Direction::DOWN, 'G')); + break; + case 1: + entities.push_back(new Traal(x, y, + Movable::Direction::DOWN, 'T')); + break; + } + } + player = (Potter *)entities[0]; + + return true; +} + +bool +Engine::init_score(const char *scorefile) +{ + score = new Score(scorefile); + + return true; +} + +void +Engine::ctrl_menu() +{ + WINDOW *opts; + int wr, wc, wy, wx; + + wc = 32; + wr = 9; + wx = CENTER(xmax, wc); + wy = CENTER(ymax, wr); + if ((opts = newwin(wr, wc, wy, wx)) == NULL) + return; + werase(opts); + box(opts, 0, 0); + + mvwprintw(opts, 1, 1, "Up Move up"); + mvwprintw(opts, 2, 1, "Down Move down"); + mvwprintw(opts, 3, 1, "Left Move left"); + mvwprintw(opts, 4, 1, "Right Move right"); + mvwprintw(opts, 5, 1, "ESC Quit"); + mvwprintw(opts, 7, 1, "Press any key to quit the menu"); + + wrefresh(opts); + (void)wgetch(opts); + werase(opts); + wrefresh(opts); + (void)delwin(opts); +} + +void +Engine::calc_dist(std::map<int, int>& dists, int ex, int ey, int dir) +{ + int px, py, dx, dy, d; + + px = player->get_x(); + py = player->get_y(); + dx = ex - px; + dy = ey - py; + d = floor(sqrt(dx * dx + dy * dy)); + dists.insert(std::pair<int, int>(d, dir)); +} + +/* Public methods */ + +void +Engine::kbd_input() +{ + int key, dir, newx, newy; + + newx = player->get_x(); + newy = player->get_y(); + + switch (key = getch()) { + case KEY_LEFT: + newx--; + dir = Movable::Direction::LEFT; + break; + case KEY_RIGHT: + newx++; + dir = Movable::Direction::RIGHT; + break; + case KEY_UP: + newy--; + dir = Movable::Direction::UP; + break; + case KEY_DOWN: + newy++; + dir = Movable::Direction::DOWN; + break; + case 'c': + ctrl_menu(); + return; + case ESC: /* FALLTHROUGH */ + /* FIXME: what? */ + f_running = 0; + default: + return; + } + + if (!collides_with_wall(newx, newy)) + player->set_newpos(dir, wxmax, wymax); +} + +/* FIXME: move asynchronously */ +void +Engine::enemies_move() +{ + std::map<int, int> dists; + int ex, ey; + auto distcmp = [](const std::pair<int, int>& a, const std::pair<int, int>& b) { + return a.first < b.second; + }; + + for (const auto& e : entities) { + if (e == player) + continue; + ex = e->get_x(); + ey = e->get_y(); + dists.clear(); + /* West */ + if (!collides_with_wall(ex - 1, ey)) + calc_dist(dists, ex - 1, ey, Movable::Direction::LEFT); + /* East */ + if (!collides_with_wall(ex + 1, ey)) + calc_dist(dists, ex + 1, ey, Movable::Direction::RIGHT); + /* North */ + if (!collides_with_wall(ex, ey - 1)) + calc_dist(dists, ex, ey - 1, Movable::Direction::UP); + /* South */ + if (!collides_with_wall(ex, ey + 1)) + calc_dist(dists, ex, ey + 1, Movable::Direction::DOWN); + + if (!dists.empty()) { + auto min = std::min_element(dists.begin(), + dists.end(), distcmp); + e->set_newpos(min->second, wxmax, wymax); + } + } +} + +void +Engine::collisions() +{ + int px, py, ex, ey; + + px = player->get_x(); + py = player->get_y(); + + for (const auto& e : entities) { + ex = e->get_x(); + ey = e->get_y(); + if (e != player && px == ex && py == ey) { + /* TODO: increase score */ + } + } +} + +void +Engine::upd_score() +{ +} + +void +Engine::redraw() +{ + char msg_score[] = "Score: %d"; + char msg_opts[] = "c Controls"; + int color; + + /* TODO: print more info */ + werase(gw); + erase(); + mvprintw(0, 0, "Potter: (%d, %d)", player->get_x(), player->get_y()); + mvprintw(0, CENTER(xmax, strlen(msg_score)), msg_score, 10); + mvprintw(0, xmax - strlen(msg_opts), msg_opts); + mvhline(1, 0, ACS_HLINE, xmax); + wattron(gw, A_REVERSE); + for (const auto& row : map) { + for (const auto& c : row) { + if (c == '*') + color = COLOR_PAIR(Color::WALL); + else if (c == ' ') + color = COLOR_PAIR(Color::PATH); + wattron(gw, color); + waddch(gw, c); + wattroff(gw, color); + } + } + for (const auto& e : entities) { + if (dynamic_cast<Potter *>(e) != nullptr) + color = COLOR_PAIR(Color::POTTER); + else if (dynamic_cast<Gnome *>(e) != nullptr) + color = COLOR_PAIR(Color::GNOME); + else if (dynamic_cast<Traal *>(e) != nullptr) + color = COLOR_PAIR(Color::TRAAL); + wattron(gw, color); + mvwaddch(gw, e->get_y(), e->get_x(), e->get_sym()); + wattroff(gw, color); + } + wattroff(gw, A_REVERSE); + refresh(); + wrefresh(gw); +} + +bool +Engine::is_running() +{ + return f_running; +} diff --git a/cpp-oop/game/Engine.hpp b/cpp_oop/game/Engine.hpp diff --git a/cpp-oop/game/Gnome.cc b/cpp_oop/game/Gnome.cc diff --git a/cpp-oop/game/Gnome.hpp b/cpp_oop/game/Gnome.hpp diff --git a/cpp-oop/game/Makefile b/cpp_oop/game/Makefile diff --git a/cpp-oop/game/Movable.cc b/cpp_oop/game/Movable.cc diff --git a/cpp-oop/game/Movable.hpp b/cpp_oop/game/Movable.hpp diff --git a/cpp-oop/game/Potter.cc b/cpp_oop/game/Potter.cc diff --git a/cpp-oop/game/Potter.hpp b/cpp_oop/game/Potter.hpp diff --git a/cpp-oop/game/Score.cc b/cpp_oop/game/Score.cc diff --git a/cpp-oop/game/Score.hpp b/cpp_oop/game/Score.hpp diff --git a/cpp-oop/game/Traal.cc b/cpp_oop/game/Traal.cc diff --git a/cpp-oop/game/Traal.hpp b/cpp_oop/game/Traal.hpp diff --git a/cpp-oop/game/main.cc b/cpp_oop/game/main.cc diff --git a/cpp-oop/game/map b/cpp_oop/game/map diff --git a/cpp-oop/game/score b/cpp_oop/game/score diff --git a/java-development/CopyPaste.java b/java_development/CopyPaste.java diff --git a/java-development/Occurences.java b/java_development/Occurences.java diff --git a/java-development/Prime.java b/java_development/Prime.java diff --git a/java-development/ReadLines.java b/java_development/ReadLines.java diff --git a/java-development/RecursiveRev.java b/java_development/RecursiveRev.java diff --git a/java-development/csv/Album.java b/java_development/csv/Album.java diff --git a/java-development/csv/Main.java b/java_development/csv/Main.java diff --git a/java-development/csv/data b/java_development/csv/data diff --git a/java-development/rect/Main.java b/java_development/rect/Main.java diff --git a/java-development/rect/Pixel.java b/java_development/rect/Pixel.java diff --git a/java-development/rect/Point.java b/java_development/rect/Point.java diff --git a/java-development/rect/Rectangle.java b/java_development/rect/Rectangle.java diff --git a/mips-architecture/lab1.asm b/mips-architecture/lab1.asm @@ -1,19 +0,0 @@ -.data - str: .asciiz "Hello world\n" - num: .word 256 - -.text -.globl main - -main: - li $v0, 4 # 4 - print string - la $a0, str # load address of str - syscall - - la $t0, num # load address of num - lw $s1, 0($t0) # load (t0 + 0) to s1 - addi $t2, $s1, 8 # add s1 + 8 to t2 - sw $t2, 0($t0) # store t2 to address of (t0 + 0) - - li $v0, 10 # exit - syscall diff --git a/mips-architecture/lab2.asm b/mips-architecture/lab2.asm @@ -1,40 +0,0 @@ -.data - numstr1: .asciiz "Number 1: " - numstr2: .asciiz "Number 2: " - resstr: .asciiz "Result\n" - addstr: .asciiz "Addition: " - -.text -.globl main - -main: - li $v0, 4 - la $a0, numstr1 # print first input message - syscall - - li $v0, 5 # read first word - syscall - move $t0, $v0 # store input in t0 - - li $v0, 4 - la $a0, numstr2 # print second input message - syscall - - li $v0, 5 # read second word - syscall - move $t1, $v0 # store input in t1 - - li $v0, 4 - la $a0, resstr - syscall - - la $a0, addstr # don't load 4 to v0, it's already there - syscall - - li $v0, 1 - add $t2, $t0, $t1 # add two inputs - la $a0, 0($t2) # load sum and prin it - syscall - - li $v0, 10 # exit - syscall diff --git a/mips-architecture/lab2_exmpl.asm b/mips-architecture/lab2_exmpl.asm @@ -1,37 +0,0 @@ -.data - value: .word 0, 0, 0 - message1: .asciiz "RESULT\n" - message2: .asciiz "addition = " - -.text -.globl main - -main: - la $t0, value - li $v0, 5 # Δώστε τον πρώτο αριθμό - syscall - - sw $v0, 0($t0) - li $v0, 5 # Δώστε τον δεύτερο αριθμό - syscall - - sw $v0, 4($t0) - lw $t1, 0($t0) - lw $t2, 4($t0) - add $t3, $t1, $t2 - sw $t3, 8($t0) - - li $v0, 4 # Τύπωσε το message1 - la $a0, message1 - syscall - - li $v0, 4 # Τύπωσε το message2 - la $a0, message2 - syscall - - li $v0, 1 # Τύπωσε το αποτέλεσμα - move $a0, $t3 - syscall - - li $v0, 10 - syscall # Έξοδος diff --git a/mips-architecture/lab3_ex1.asm b/mips-architecture/lab3_ex1.asm @@ -1,76 +0,0 @@ -.eqv SYS_PRINT_WORD 1 -.eqv SYS_PRINT_STRING 4 -.eqv SYS_READ_WORD 5 -.eqv SYS_READ_STRING 8 -.eqv SYS_EXIT 10 -.eqv SYS_PRINT_CHAR 11 -.eqv SYS_READ_CHAR 12 - -.macro endl() -li $v0, SYS_PRINT_CHAR -li $a0, 0xa -syscall -.end_macro - -.data - str1: .asciiz "Hello\n" - str2: .asciiz "TEI\n" - name: .space 64 - -.text -.globl _main - -_main: - # 1. print a character - li $v0, SYS_PRINT_CHAR - li $a0, 'C' - syscall - - endl() - - # 2. print characters 'a' and 'd' - li $a0, 'a' - syscall - li $a0, 'd' - syscall - - endl() - - # 3. print 'Hello' - li $v0, SYS_PRINT_STRING - la $a0, str1 - syscall - - # 4. print 'Hello' and 'TEI' - la $a0, str1 - syscall - la $a0, str2 - syscall - - # 5. print 5 - li $v0, SYS_PRINT_WORD - li $a0, 5 - syscall - - endl() - - # 6. read a word and print it - li $v0, SYS_READ_WORD - syscall - move $t0, $v0 - li $v0, SYS_PRINT_WORD - la $a0, 0($t0) - syscall - - endl() - - # 7. read name, store in mem and print it - li $v0, SYS_READ_STRING - la $a0, name - li $a1, 64 - syscall - li $v0, SYS_PRINT_STRING - syscall - - li $v0, SYS_EXIT - syscall diff --git a/mips-architecture/lab3_ex2.asm b/mips-architecture/lab3_ex2.asm @@ -1,73 +0,0 @@ -.eqv SYS_PRINT_WORD 1 -.eqv SYS_PRINT_STRING 4 -.eqv SYS_READ_WORD 5 -.eqv SYS_READ_STRING 8 -.eqv SYS_EXIT 10 -.eqv SYS_PRINT_CHAR 11 -.eqv SYS_READ_CHAR 12 - -.macro endl() - li $v0, SYS_PRINT_CHAR - li $a0, 0xa - syscall -.end_macro - -.data - str: .asciiz "hello\n" - name: .space 64 - x: .word 0 - a: .word 20 - b: .word 30 - c: .word 15 - -.text -.globl main - -main: - # 1. print 1st and 2nd character in string - li $v0, SYS_PRINT_CHAR - lb $a0, str - syscall - lb $a0, str + 1 - syscall - - endl() - - # 2. read x and print str[x] - li $v0, SYS_READ_WORD - syscall - lb $a0, str($v0) - li $v0, SYS_PRINT_CHAR - syscall - - endl() - - # 3. read a string and print its 2nd char - li $v0, SYS_READ_STRING - la $a0, name - li $a1, 64 - syscall - lb $a0, name + 1 - li $v0, SYS_PRINT_CHAR - syscall - - endl() - - # 4. int x, a = 20, b = 30, c = 15; - # x = (a + b) - (c + 10); - lw $t0, x - lw $t1, a - lw $t2, b - lw $t3, c - add $t4, $t1, $t2 - addi $t5, $t3, 10 - sub $t0, $t4, $t5 - - li $v0, SYS_PRINT_WORD - la $a0, 0($t0) - syscall - - endl() - - li $v0, SYS_EXIT - syscall diff --git a/mips-architecture/lab4_ex1.asm b/mips-architecture/lab4_ex1.asm @@ -1,30 +0,0 @@ -.eqv SYS_PRINT_STRING 4 -.eqv SYS_READ_WORD 5 -.eqv SYS_EXIT 10 - -.data - zstr: .asciiz "Zero\n" - nzstr: .asciiz "Non Zero\n" - -.text -.globl main - -main: - li $v0, SYS_READ_WORD - syscall - - bne $v0, $zero, nonzero - li $v0, SYS_PRINT_STRING - la $a0, zstr - syscall - - j exit - -nonzero: - li $v0, SYS_PRINT_STRING - la $a0, nzstr - syscall - -exit: - li $v0, SYS_EXIT - syscall- \ No newline at end of file diff --git a/mips-architecture/lab4_ex2.asm b/mips-architecture/lab4_ex2.asm @@ -1,33 +0,0 @@ -.eqv SYS_PRINT_STRING 4 -.eqv SYS_READ_WORD 5 -.eqv SYS_EXIT 10 - -.data - posstr: .asciiz "Positive\n" - nonposstr: .asciiz "Non Positive\n" - -.text -.globl main - -main: - li $v0, SYS_READ_WORD - syscall - - # t0 = 1 if v0 == 0 - slt $t0, $v0, $zero - beq $t0, $zero, pos - - li $v0, SYS_PRINT_STRING - la $a0, nonposstr - syscall - - j exit - -pos: - li $v0, SYS_PRINT_STRING - la $a0, posstr - syscall - -exit: - li $v0, SYS_EXIT - syscall diff --git a/mips-architecture/lab4_ex3.asm b/mips-architecture/lab4_ex3.asm @@ -1,28 +0,0 @@ -.eqv SYS_EXIT 10 -.eqv SYS_PRINT_CHAR 11 -.eqv LOOP_ITER 5 - -.text -.globl main - -main: - # init loop counter - li $t0, 0 - -loop: - # exit if t0 == 5 - beq $t0, LOOP_ITER, exit - addi $t0, $t0, 1 - - li $v0, SYS_PRINT_CHAR - li $a0, '*' - syscall - - j loop - - li $a0, 0xa - syscall - -exit: - li $v0, SYS_EXIT - syscall diff --git a/mips-architecture/lab4_ex4.asm b/mips-architecture/lab4_ex4.asm @@ -1,51 +0,0 @@ -.eqv SYS_PRINT_STRING 4 -.eqv SYS_READ_WORD 5 -.eqv SYS_EXIT 10 -.eqv SYS_PRINT_CHAR 11 - -.data - msg: .asciiz "Number: " - errstr: .asciiz "Give a positive number.\n" - -.text -.globl main - -main: - li $v0, SYS_PRINT_STRING - la $a0, msg - syscall - - li $v0, SYS_READ_WORD - syscall - move $t0, $v0 - - # exit if t0 <= 0 - beq $t0, $zero, err - slt $t1, $t0, $zero - bne $t1, $zero, err - - # init loop counter - li $t2, 0 - -loop: - beq $t2, $t0, exit - addi $t2, $t2, 1 - - li $v0, SYS_PRINT_CHAR - li $a0, '*' - syscall - - j loop - - li $v0, SYS_PRINT_CHAR - li $a0, 0xa - syscall - -err: - li $v0, SYS_PRINT_STRING - la $a0, errstr - syscall - -exit: - li $v0, SYS_EXIT - syscall diff --git a/mips-architecture/lab4_ex5.asm b/mips-architecture/lab4_ex5.asm @@ -1,42 +0,0 @@ -.eqv SYS_EXIT 10 -.eqv SYS_PRINT_CHAR 11 -.eqv OUTLOOP_ITER 5 -.eqv INLOOP_ITER 4 - -.text -.globl main - -main: - # init outer loop counter - li $t0, 0 - -outloop: - # exit if t0 == 5 - beq $t0, OUTLOOP_ITER, exit - addi $t0, $t0, 1 - - # init inner loop counter - li $t1, 0 - - # print newline - li $v0, SYS_PRINT_CHAR - li $a0, 0xa - syscall - j inloop - - j outloop - -inloop: - # break inner loop if t1 == 4 - beq $t1, INLOOP_ITER, outloop - addi $t1, $t1, 1 - - li $v0, SYS_PRINT_CHAR - li $a0, '*' - syscall - - j inloop - -exit: - li $v0, SYS_EXIT - syscall diff --git a/mips-architecture/lab4_ex6.asm b/mips-architecture/lab4_ex6.asm @@ -1,77 +0,0 @@ -.eqv SYS_PRINT_STRING 4 -.eqv SYS_READ_WORD 5 -.eqv SYS_EXIT 10 -.eqv SYS_PRINT_CHAR 11 - -.macro input(%msg) - li $v0, SYS_PRINT_STRING - la $a0, %msg - syscall - - li $v0, SYS_READ_WORD - syscall -.end_macro - -.macro ispositive(%val) - # exit if t0 or $t1 <= 0 - beq %val, $zero, err - slt $t2, %val, $zero - bne $t2, $zero, err -.end_macro - -.data - msg1: .asciiz "Lines: " - msg2: .asciiz "Chars: " - errstr: .asciiz "Give positive numbers only.\n" - -.text -.globl main - -main: - input(msg1) - move $t0, $v0 - - input(msg2) - move $t1, $v0 - - ispositive($t0) - ispositive($t1) - - # init outer loop counter - li $t3, 0 - -outloop: - # exit if t3 == x - beq $t3, $t0, exit - addi $t3, $t3, 1 - - # init inner loop counter - li $t4, 0 - - # print newline - li $v0, SYS_PRINT_CHAR - li $a0, 0xa - syscall - j inloop - - j outloop - -inloop: - # break inner loop if t4 == y - beq $t4, $t1, outloop - addi $t4, $t4, 1 - - li $v0, SYS_PRINT_CHAR - li $a0, '*' - syscall - - j inloop - -err: - li $v0, SYS_PRINT_STRING - la $a0, errstr - syscall - -exit: - li $v0, SYS_EXIT - syscall diff --git a/mips-architecture/lab5_ex1.asm b/mips-architecture/lab5_ex1.asm @@ -1,40 +0,0 @@ -.eqv SYS_PRINT_WORD 1 -.eqv SYS_PRINT_STRING 4 -.eqv SYS_READ_STRING 8 -.eqv SYS_EXIT 10 - -.data - str: .space 17 # + 2 bytes to include '\n' and '\0' - len: .asciiz "strlen: " - revstr: .asciiz "reverse: " - -.text -.globl main - -main: - # read input string - li $v0, SYS_READ_STRING - la $a0, str - li $a1, 17 - syscall - - # init strlen counter - li $t0, 0 - -strlen: - lb $t1, str($t0) - beqz $t1, exit - addi $t0, $t0, 1 - j strlen - -exit: - li $v0, SYS_PRINT_STRING - la $a0, len - syscall - - li $v0, SYS_PRINT_WORD - la $a0, 0($t0) - syscall - - li $v0, SYS_EXIT - syscall diff --git a/mips-architecture/lab5_ex2.asm b/mips-architecture/lab5_ex2.asm @@ -1,46 +0,0 @@ -.eqv SYS_PRINT_STRING 4 -.eqv SYS_READ_STRING 8 -.eqv SYS_EXIT 10 -.eqv SYS_PRINT_CHAR 11 - -.data - str: .space 17 # + 2 bytes to include '\n' and '\0' - revstr: .asciiz "reverse: " - -.text -.globl main - -main: - # read input string - li $v0, SYS_READ_STRING - la $a0, str - li $a1, 17 - syscall - - # init strlen counter - li $t0, 0 - -strlen: - lb $t1, str($t0) - beqz $t1, strrev - addi $t0, $t0, 1 - j strlen - - # subtract 2 so that we skip '\n' and '\0' and get to the - # last character in the string - addi $t0, $t0, -2 - -strrev: - # if $t0 is 0 is means we reached str[0] - beqz $t0, exit - # in the first loop, $t1 is at the last actual character, - # so we'll go backwards to get to the beginning - li $v0, SYS_PRINT_CHAR - lb $a0, str($t0) - syscall - addi $t0, $t0, -1 - j strrev - -exit: - li $v0, SYS_EXIT - syscall diff --git a/mips-architecture/lab5_ex3.asm b/mips-architecture/lab5_ex3.asm @@ -1,23 +0,0 @@ -.eqv SYS_EXIT 10 - -.data - arr: .byte 1, 15, 0, -3, 99, 48, -17, -9, 20, 15 - -.text -.globl main - -main: - # init loop $t0, sum $t1 counters - li $t0, 0 - li $t1, 0 - -calcsum: - beq $t0, 10, exit - lb $t3, arr($t0) - add $t1, $t1, $t3 - addi $t0, $t0, 1 - j calcsum - -exit: - li $v0, SYS_EXIT - syscall diff --git a/mips-architecture/lab5_ex4.asm b/mips-architecture/lab5_ex4.asm @@ -1,36 +0,0 @@ -.eqv SYS_EXIT 10 - -.data - val: .word 0xabcd - # 'val' is 2 bytes - first: .space 2 - second: .space 2 - third: .space 2 - fourth: .space 2 - -.text -.globl main - -main: - # init loop counter - li $t0, 0 - # 4 iterations because we'll store 'val' 4 times - li $t1, 4 - # this is our offset, we'll increment it by 2 - # in each iteration so that we store 0xabcd in - # the appropriate label - li $t2, 0 - lh $t3, val - -loop: - beq $t0, $t1, exit - # store it as half word so that it and doesn't - # there aren't any zeros between that and the next 'val' - sh $t3, first($t2) - addi $t0, $t0, 1 - addi $t2, $t2, 2 - j loop - -exit: - li $v0, SYS_EXIT - syscall diff --git a/mips-architecture/lab5_ex5.asm b/mips-architecture/lab5_ex5.asm @@ -1,64 +0,0 @@ -.eqv SYS_PRINT_WORD 1 -.eqv SYS_EXIT 10 -.eqv SYS_READ_CHAR 12 - -.macro isnotdigit(%ch, %lbl) - # the character must be 0x30 <= c <= 0x39 - # for it to be a digit, otherwise, stop - blt %ch, 0x30, %lbl - bgt %ch, 0x39, %lbl -.end_macro - -.data - # max word can be 10 digits long but à - # we add + 1 byte in case there is '\n' - str: .space 11 - -.text -.globl main - -main: - # init strlen/iterations counter - li $t1, 0 - -getdigit: - li $v0, SYS_READ_CHAR - syscall - # copy $v0 to $t0 - addu $t0, $v0, $zero - isnotdigit($t0, atoi) - # we don't read more than 10 digits - beq $t1, 10, atoi - # save the digit in memory so that we can - # retrieve it later - sb $t0, str($t1) - addi $t1, $t1, 1 - j getdigit - -atoi: - li $t0, 0 - # init sum - li $t3, 0 - -atoiloop: - lb $t2, str($t0) - # $t1 is the strlen of str so loop as - # long as $t0 < $t1 - beq $t0, $t1, exit - # in case we hit '\n' or '\0' - isnotdigit($t2, exit) - - # get decimal value - addi $t2, $t2, -0x30 - mul $t3, $t3, 10 - add $t3, $t3, $t2 - addi $t0, $t0, 1 - j atoiloop - -exit: - li $v0, SYS_PRINT_WORD - la $a0, 0($t3) - syscall - - li $v0, SYS_EXIT - syscall diff --git a/mips-architecture/lab6_ex1.asm b/mips-architecture/lab6_ex1.asm @@ -1,37 +0,0 @@ -.eqv SYS_PRINT_STRING 4 -.eqv SYS_READ_WORD 5 -.eqv SYS_EXIT 10 - -.data - inputmsg: .asciiz "Number: " - evenstr: .asciiz "Even number\n" - oddstr: .asciiz "Odd number\n" - -.text -.globl main - -main: - li $v0, SYS_PRINT_STRING - la $a0, inputmsg - syscall - - li $v0, SYS_READ_WORD - syscall - - # Get the LSB - andi $t0, $v0, 1 - beq $t0, 1, odd - - li $v0, SYS_PRINT_STRING - la $a0, evenstr - syscall - j exit - -odd: - li $v0, SYS_PRINT_STRING - la $a0, oddstr - syscall - -exit: - li $v0, SYS_EXIT - syscall diff --git a/mips-architecture/lab6_ex2.asm b/mips-architecture/lab6_ex2.asm @@ -1,37 +0,0 @@ -.eqv SYS_PRINT_STRING 4 -.eqv SYS_READ_WORD 5 -.eqv SYS_EXIT 10 - -.data - inputmsg: .asciiz "Number: " - ismultstr: .asciiz "Multiple of 4\n" - isnmultstr: .asciiz "Not a multiple of 4\n" - -.text -.globl main - -main: - li $v0, SYS_PRINT_STRING - la $a0, inputmsg - syscall - - li $v0, SYS_READ_WORD - syscall - - # get 2 lowest bits - andi $t0, $v0, 3 - beq $t0, 0, ismult - - li $v0, SYS_PRINT_STRING - la $a0, isnmultstr - syscall - j exit - -ismult: - li $v0, SYS_PRINT_STRING - la $a0, ismultstr - syscall - -exit: - li $v0, SYS_EXIT - syscall diff --git a/mips-architecture/lab6_ex3.asm b/mips-architecture/lab6_ex3.asm @@ -1,43 +0,0 @@ -.eqv SYS_PRINT_STRING 4 -.eqv SYS_READ_WORD 5 -.eqv SYS_EXIT 10 - -.data - inputmsg: .asciiz "Number: " - posstr: .asciiz "Positive\n" - negstr: .asciiz "Negative\n" - -.text -.globl main - -main: - li $v0, SYS_PRINT_STRING - la $a0, inputmsg - syscall - - li $v0, SYS_READ_WORD - syscall - - # Right shift number 31 bits so that the MSB falls - # on the LSB's position. Since we're using 2's - # complement, if the MSB is 1 the number is negative - # and if it's 0 it's positive. After the right shift - # `t0` will either be 0 or 1 - - srl $t0, $v0, 31 - beq $t0, 0, positive - - li $v0, SYS_PRINT_STRING - la $a0, negstr - syscall - - j exit - -positive: - li $v0, SYS_PRINT_STRING - la $a0, posstr - syscall - -exit: - li $v0, SYS_EXIT - syscall diff --git a/mips-architecture/lab6_ex4.asm b/mips-architecture/lab6_ex4.asm @@ -1,62 +0,0 @@ -.eqv SYS_PRINT_WORD 1 -.eqv SYS_PRINT_STRING 4 -.eqv SYS_READ_WORD 5 -.eqv SYS_EXIT 10 - -.data - inputmsg: .asciiz "Number (0-15): " - bounderrstr: .asciiz "Number must be 0-15\n" - binstr: .asciiz "Binary: " - -.text -.globl main - -main: - li $v0, SYS_PRINT_STRING - la $a0, inputmsg - syscall - - li $v0, SYS_READ_WORD - syscall - move $t0, $v0 - - # Bounds check - blt $t0, 0, bounderr - bgt $t0, 15, bounderr - - # Init loop counter, We're right shifting in reverse - # because otherwise the binary number is going to - # show reversed. We assign 3 to `s0` because the range - # 0-15 is 4 bits and we'll go from 3 to 0 (4 iterations). - # We DON'T start with `s0 = 4` because the last bit - # will be eaten. - # For example if the number is 3 then - # - # (0011 >> 3) & 1 = 0000 & 1 = 0 - # (0011 >> 2) & 1 = 0000 & 1 = 0 - # (0011 >> 1) & 1 = 0001 & 1 = 1 - # (0011 >> 0) & 1 = 0011 & 1 = 1 - # - # So the result is 0011 which is the binary form of 3 - li $s0, 3 - -binloop: - srlv $t1, $t0, $s0 # t1 = t0 >> s0 - andi $t2, $t1, 1 # t2 = t1 & 1 - - li $v0, SYS_PRINT_WORD - la $a0, 0($t2) - syscall - - beq $s0, 0, exit - addi $s0, $s0, -1 - j binloop - -bounderr: - li $v0, SYS_PRINT_STRING - la $a0, bounderrstr - syscall - -exit: - li $v0, SYS_EXIT - syscall diff --git a/mips-architecture/lab6_ex5.asm b/mips-architecture/lab6_ex5.asm @@ -1,62 +0,0 @@ -.eqv SYS_PRINT_STRING 4 -.eqv SYS_READ_WORD 5 -.eqv SYS_EXIT 10 -.eqv SYS_PRINT_CHAR 11 - -.data - inputmsg: .asciiz "Number (1-255): " - bounderrstr: .asciiz "Number must be 1-255\n" - resstr: .asciiz "Hex: 0x" - hex: .ascii "0123456789abcdef" - -.text -.globl main - -main: - li $v0, SYS_PRINT_STRING - la $a0, inputmsg - syscall - - li $v0, SYS_READ_WORD - syscall - move $t0, $v0 - - # Bounds check - blt $t0, 1, bounderr - bgt $t0, 255, bounderr - - li $v0, SYS_PRINT_STRING - la $a0, resstr - syscall - - # Get first 4 bits and shift them 4 bits right - # so that `t2` can have their value. For example - # if the number is 50 (00110010): - # - # (00110010 & 0xf0) >> 4 = 00110000 >> 4 = 00000011 = 3 - andi $t1, $t0, 0xf0 - srl $t2, $t1, 4 - - # Print first portion (4 bits) - li $v0, SYS_PRINT_CHAR - lb $a0, hex($t2) - syscall - - # Get last 4 bits. Using 50 as an example again - # 00110010 & 0x0f = 00000010 = 2 - andi $t1, $t0, 0x0f - - # Print second portion (4 bits) - lb $a0, hex($t1) - syscall - - j exit - -bounderr: - li $v0, SYS_PRINT_STRING - la $a0, bounderrstr - syscall - -exit: - li $v0, SYS_EXIT - syscall diff --git a/mips_architecture/lab1.asm b/mips_architecture/lab1.asm @@ -0,0 +1,19 @@ +.data + str: .asciiz "Hello world\n" + num: .word 256 + +.text +.globl main + +main: + li $v0, 4 # 4 - print string + la $a0, str # load address of str + syscall + + la $t0, num # load address of num + lw $s1, 0($t0) # load (t0 + 0) to s1 + addi $t2, $s1, 8 # add s1 + 8 to t2 + sw $t2, 0($t0) # store t2 to address of (t0 + 0) + + li $v0, 10 # exit + syscall diff --git a/mips_architecture/lab2.asm b/mips_architecture/lab2.asm @@ -0,0 +1,40 @@ +.data + numstr1: .asciiz "Number 1: " + numstr2: .asciiz "Number 2: " + resstr: .asciiz "Result\n" + addstr: .asciiz "Addition: " + +.text +.globl main + +main: + li $v0, 4 + la $a0, numstr1 # print first input message + syscall + + li $v0, 5 # read first word + syscall + move $t0, $v0 # store input in t0 + + li $v0, 4 + la $a0, numstr2 # print second input message + syscall + + li $v0, 5 # read second word + syscall + move $t1, $v0 # store input in t1 + + li $v0, 4 + la $a0, resstr + syscall + + la $a0, addstr # don't load 4 to v0, it's already there + syscall + + li $v0, 1 + add $t2, $t0, $t1 # add two inputs + la $a0, 0($t2) # load sum and prin it + syscall + + li $v0, 10 # exit + syscall diff --git a/mips_architecture/lab2_exmpl.asm b/mips_architecture/lab2_exmpl.asm @@ -0,0 +1,37 @@ +.data + value: .word 0, 0, 0 + message1: .asciiz "RESULT\n" + message2: .asciiz "addition = " + +.text +.globl main + +main: + la $t0, value + li $v0, 5 # Δώστε τον πρώτο αριθμό + syscall + + sw $v0, 0($t0) + li $v0, 5 # Δώστε τον δεύτερο αριθμό + syscall + + sw $v0, 4($t0) + lw $t1, 0($t0) + lw $t2, 4($t0) + add $t3, $t1, $t2 + sw $t3, 8($t0) + + li $v0, 4 # Τύπωσε το message1 + la $a0, message1 + syscall + + li $v0, 4 # Τύπωσε το message2 + la $a0, message2 + syscall + + li $v0, 1 # Τύπωσε το αποτέλεσμα + move $a0, $t3 + syscall + + li $v0, 10 + syscall # Έξοδος diff --git a/mips_architecture/lab3_ex1.asm b/mips_architecture/lab3_ex1.asm @@ -0,0 +1,76 @@ +.eqv SYS_PRINT_WORD 1 +.eqv SYS_PRINT_STRING 4 +.eqv SYS_READ_WORD 5 +.eqv SYS_READ_STRING 8 +.eqv SYS_EXIT 10 +.eqv SYS_PRINT_CHAR 11 +.eqv SYS_READ_CHAR 12 + +.macro endl() +li $v0, SYS_PRINT_CHAR +li $a0, 0xa +syscall +.end_macro + +.data + str1: .asciiz "Hello\n" + str2: .asciiz "TEI\n" + name: .space 64 + +.text +.globl _main + +_main: + # 1. print a character + li $v0, SYS_PRINT_CHAR + li $a0, 'C' + syscall + + endl() + + # 2. print characters 'a' and 'd' + li $a0, 'a' + syscall + li $a0, 'd' + syscall + + endl() + + # 3. print 'Hello' + li $v0, SYS_PRINT_STRING + la $a0, str1 + syscall + + # 4. print 'Hello' and 'TEI' + la $a0, str1 + syscall + la $a0, str2 + syscall + + # 5. print 5 + li $v0, SYS_PRINT_WORD + li $a0, 5 + syscall + + endl() + + # 6. read a word and print it + li $v0, SYS_READ_WORD + syscall + move $t0, $v0 + li $v0, SYS_PRINT_WORD + la $a0, 0($t0) + syscall + + endl() + + # 7. read name, store in mem and print it + li $v0, SYS_READ_STRING + la $a0, name + li $a1, 64 + syscall + li $v0, SYS_PRINT_STRING + syscall + + li $v0, SYS_EXIT + syscall diff --git a/mips_architecture/lab3_ex2.asm b/mips_architecture/lab3_ex2.asm @@ -0,0 +1,73 @@ +.eqv SYS_PRINT_WORD 1 +.eqv SYS_PRINT_STRING 4 +.eqv SYS_READ_WORD 5 +.eqv SYS_READ_STRING 8 +.eqv SYS_EXIT 10 +.eqv SYS_PRINT_CHAR 11 +.eqv SYS_READ_CHAR 12 + +.macro endl() + li $v0, SYS_PRINT_CHAR + li $a0, 0xa + syscall +.end_macro + +.data + str: .asciiz "hello\n" + name: .space 64 + x: .word 0 + a: .word 20 + b: .word 30 + c: .word 15 + +.text +.globl main + +main: + # 1. print 1st and 2nd character in string + li $v0, SYS_PRINT_CHAR + lb $a0, str + syscall + lb $a0, str + 1 + syscall + + endl() + + # 2. read x and print str[x] + li $v0, SYS_READ_WORD + syscall + lb $a0, str($v0) + li $v0, SYS_PRINT_CHAR + syscall + + endl() + + # 3. read a string and print its 2nd char + li $v0, SYS_READ_STRING + la $a0, name + li $a1, 64 + syscall + lb $a0, name + 1 + li $v0, SYS_PRINT_CHAR + syscall + + endl() + + # 4. int x, a = 20, b = 30, c = 15; + # x = (a + b) - (c + 10); + lw $t0, x + lw $t1, a + lw $t2, b + lw $t3, c + add $t4, $t1, $t2 + addi $t5, $t3, 10 + sub $t0, $t4, $t5 + + li $v0, SYS_PRINT_WORD + la $a0, 0($t0) + syscall + + endl() + + li $v0, SYS_EXIT + syscall diff --git a/mips_architecture/lab4_ex1.asm b/mips_architecture/lab4_ex1.asm @@ -0,0 +1,30 @@ +.eqv SYS_PRINT_STRING 4 +.eqv SYS_READ_WORD 5 +.eqv SYS_EXIT 10 + +.data + zstr: .asciiz "Zero\n" + nzstr: .asciiz "Non Zero\n" + +.text +.globl main + +main: + li $v0, SYS_READ_WORD + syscall + + bne $v0, $zero, nonzero + li $v0, SYS_PRINT_STRING + la $a0, zstr + syscall + + j exit + +nonzero: + li $v0, SYS_PRINT_STRING + la $a0, nzstr + syscall + +exit: + li $v0, SYS_EXIT + syscall+ \ No newline at end of file diff --git a/mips_architecture/lab4_ex2.asm b/mips_architecture/lab4_ex2.asm @@ -0,0 +1,33 @@ +.eqv SYS_PRINT_STRING 4 +.eqv SYS_READ_WORD 5 +.eqv SYS_EXIT 10 + +.data + posstr: .asciiz "Positive\n" + nonposstr: .asciiz "Non Positive\n" + +.text +.globl main + +main: + li $v0, SYS_READ_WORD + syscall + + # t0 = 1 if v0 == 0 + slt $t0, $v0, $zero + beq $t0, $zero, pos + + li $v0, SYS_PRINT_STRING + la $a0, nonposstr + syscall + + j exit + +pos: + li $v0, SYS_PRINT_STRING + la $a0, posstr + syscall + +exit: + li $v0, SYS_EXIT + syscall diff --git a/mips_architecture/lab4_ex3.asm b/mips_architecture/lab4_ex3.asm @@ -0,0 +1,28 @@ +.eqv SYS_EXIT 10 +.eqv SYS_PRINT_CHAR 11 +.eqv LOOP_ITER 5 + +.text +.globl main + +main: + # init loop counter + li $t0, 0 + +loop: + # exit if t0 == 5 + beq $t0, LOOP_ITER, exit + addi $t0, $t0, 1 + + li $v0, SYS_PRINT_CHAR + li $a0, '*' + syscall + + j loop + + li $a0, 0xa + syscall + +exit: + li $v0, SYS_EXIT + syscall diff --git a/mips_architecture/lab4_ex4.asm b/mips_architecture/lab4_ex4.asm @@ -0,0 +1,51 @@ +.eqv SYS_PRINT_STRING 4 +.eqv SYS_READ_WORD 5 +.eqv SYS_EXIT 10 +.eqv SYS_PRINT_CHAR 11 + +.data + msg: .asciiz "Number: " + errstr: .asciiz "Give a positive number.\n" + +.text +.globl main + +main: + li $v0, SYS_PRINT_STRING + la $a0, msg + syscall + + li $v0, SYS_READ_WORD + syscall + move $t0, $v0 + + # exit if t0 <= 0 + beq $t0, $zero, err + slt $t1, $t0, $zero + bne $t1, $zero, err + + # init loop counter + li $t2, 0 + +loop: + beq $t2, $t0, exit + addi $t2, $t2, 1 + + li $v0, SYS_PRINT_CHAR + li $a0, '*' + syscall + + j loop + + li $v0, SYS_PRINT_CHAR + li $a0, 0xa + syscall + +err: + li $v0, SYS_PRINT_STRING + la $a0, errstr + syscall + +exit: + li $v0, SYS_EXIT + syscall diff --git a/mips_architecture/lab4_ex5.asm b/mips_architecture/lab4_ex5.asm @@ -0,0 +1,42 @@ +.eqv SYS_EXIT 10 +.eqv SYS_PRINT_CHAR 11 +.eqv OUTLOOP_ITER 5 +.eqv INLOOP_ITER 4 + +.text +.globl main + +main: + # init outer loop counter + li $t0, 0 + +outloop: + # exit if t0 == 5 + beq $t0, OUTLOOP_ITER, exit + addi $t0, $t0, 1 + + # init inner loop counter + li $t1, 0 + + # print newline + li $v0, SYS_PRINT_CHAR + li $a0, 0xa + syscall + j inloop + + j outloop + +inloop: + # break inner loop if t1 == 4 + beq $t1, INLOOP_ITER, outloop + addi $t1, $t1, 1 + + li $v0, SYS_PRINT_CHAR + li $a0, '*' + syscall + + j inloop + +exit: + li $v0, SYS_EXIT + syscall diff --git a/mips_architecture/lab4_ex6.asm b/mips_architecture/lab4_ex6.asm @@ -0,0 +1,77 @@ +.eqv SYS_PRINT_STRING 4 +.eqv SYS_READ_WORD 5 +.eqv SYS_EXIT 10 +.eqv SYS_PRINT_CHAR 11 + +.macro input(%msg) + li $v0, SYS_PRINT_STRING + la $a0, %msg + syscall + + li $v0, SYS_READ_WORD + syscall +.end_macro + +.macro ispositive(%val) + # exit if t0 or $t1 <= 0 + beq %val, $zero, err + slt $t2, %val, $zero + bne $t2, $zero, err +.end_macro + +.data + msg1: .asciiz "Lines: " + msg2: .asciiz "Chars: " + errstr: .asciiz "Give positive numbers only.\n" + +.text +.globl main + +main: + input(msg1) + move $t0, $v0 + + input(msg2) + move $t1, $v0 + + ispositive($t0) + ispositive($t1) + + # init outer loop counter + li $t3, 0 + +outloop: + # exit if t3 == x + beq $t3, $t0, exit + addi $t3, $t3, 1 + + # init inner loop counter + li $t4, 0 + + # print newline + li $v0, SYS_PRINT_CHAR + li $a0, 0xa + syscall + j inloop + + j outloop + +inloop: + # break inner loop if t4 == y + beq $t4, $t1, outloop + addi $t4, $t4, 1 + + li $v0, SYS_PRINT_CHAR + li $a0, '*' + syscall + + j inloop + +err: + li $v0, SYS_PRINT_STRING + la $a0, errstr + syscall + +exit: + li $v0, SYS_EXIT + syscall diff --git a/mips_architecture/lab5_ex1.asm b/mips_architecture/lab5_ex1.asm @@ -0,0 +1,40 @@ +.eqv SYS_PRINT_WORD 1 +.eqv SYS_PRINT_STRING 4 +.eqv SYS_READ_STRING 8 +.eqv SYS_EXIT 10 + +.data + str: .space 17 # + 2 bytes to include '\n' and '\0' + len: .asciiz "strlen: " + revstr: .asciiz "reverse: " + +.text +.globl main + +main: + # read input string + li $v0, SYS_READ_STRING + la $a0, str + li $a1, 17 + syscall + + # init strlen counter + li $t0, 0 + +strlen: + lb $t1, str($t0) + beqz $t1, exit + addi $t0, $t0, 1 + j strlen + +exit: + li $v0, SYS_PRINT_STRING + la $a0, len + syscall + + li $v0, SYS_PRINT_WORD + la $a0, 0($t0) + syscall + + li $v0, SYS_EXIT + syscall diff --git a/mips_architecture/lab5_ex2.asm b/mips_architecture/lab5_ex2.asm @@ -0,0 +1,46 @@ +.eqv SYS_PRINT_STRING 4 +.eqv SYS_READ_STRING 8 +.eqv SYS_EXIT 10 +.eqv SYS_PRINT_CHAR 11 + +.data + str: .space 17 # + 2 bytes to include '\n' and '\0' + revstr: .asciiz "reverse: " + +.text +.globl main + +main: + # read input string + li $v0, SYS_READ_STRING + la $a0, str + li $a1, 17 + syscall + + # init strlen counter + li $t0, 0 + +strlen: + lb $t1, str($t0) + beqz $t1, strrev + addi $t0, $t0, 1 + j strlen + + # subtract 2 so that we skip '\n' and '\0' and get to the + # last character in the string + addi $t0, $t0, -2 + +strrev: + # if $t0 is 0 is means we reached str[0] + beqz $t0, exit + # in the first loop, $t1 is at the last actual character, + # so we'll go backwards to get to the beginning + li $v0, SYS_PRINT_CHAR + lb $a0, str($t0) + syscall + addi $t0, $t0, -1 + j strrev + +exit: + li $v0, SYS_EXIT + syscall diff --git a/mips_architecture/lab5_ex3.asm b/mips_architecture/lab5_ex3.asm @@ -0,0 +1,23 @@ +.eqv SYS_EXIT 10 + +.data + arr: .byte 1, 15, 0, -3, 99, 48, -17, -9, 20, 15 + +.text +.globl main + +main: + # init loop $t0, sum $t1 counters + li $t0, 0 + li $t1, 0 + +calcsum: + beq $t0, 10, exit + lb $t3, arr($t0) + add $t1, $t1, $t3 + addi $t0, $t0, 1 + j calcsum + +exit: + li $v0, SYS_EXIT + syscall diff --git a/mips_architecture/lab5_ex4.asm b/mips_architecture/lab5_ex4.asm @@ -0,0 +1,36 @@ +.eqv SYS_EXIT 10 + +.data + val: .word 0xabcd + # 'val' is 2 bytes + first: .space 2 + second: .space 2 + third: .space 2 + fourth: .space 2 + +.text +.globl main + +main: + # init loop counter + li $t0, 0 + # 4 iterations because we'll store 'val' 4 times + li $t1, 4 + # this is our offset, we'll increment it by 2 + # in each iteration so that we store 0xabcd in + # the appropriate label + li $t2, 0 + lh $t3, val + +loop: + beq $t0, $t1, exit + # store it as half word so that it and doesn't + # there aren't any zeros between that and the next 'val' + sh $t3, first($t2) + addi $t0, $t0, 1 + addi $t2, $t2, 2 + j loop + +exit: + li $v0, SYS_EXIT + syscall diff --git a/mips_architecture/lab5_ex5.asm b/mips_architecture/lab5_ex5.asm @@ -0,0 +1,64 @@ +.eqv SYS_PRINT_WORD 1 +.eqv SYS_EXIT 10 +.eqv SYS_READ_CHAR 12 + +.macro isnotdigit(%ch, %lbl) + # the character must be 0x30 <= c <= 0x39 + # for it to be a digit, otherwise, stop + blt %ch, 0x30, %lbl + bgt %ch, 0x39, %lbl +.end_macro + +.data + # max word can be 10 digits long but à + # we add + 1 byte in case there is '\n' + str: .space 11 + +.text +.globl main + +main: + # init strlen/iterations counter + li $t1, 0 + +getdigit: + li $v0, SYS_READ_CHAR + syscall + # copy $v0 to $t0 + addu $t0, $v0, $zero + isnotdigit($t0, atoi) + # we don't read more than 10 digits + beq $t1, 10, atoi + # save the digit in memory so that we can + # retrieve it later + sb $t0, str($t1) + addi $t1, $t1, 1 + j getdigit + +atoi: + li $t0, 0 + # init sum + li $t3, 0 + +atoiloop: + lb $t2, str($t0) + # $t1 is the strlen of str so loop as + # long as $t0 < $t1 + beq $t0, $t1, exit + # in case we hit '\n' or '\0' + isnotdigit($t2, exit) + + # get decimal value + addi $t2, $t2, -0x30 + mul $t3, $t3, 10 + add $t3, $t3, $t2 + addi $t0, $t0, 1 + j atoiloop + +exit: + li $v0, SYS_PRINT_WORD + la $a0, 0($t3) + syscall + + li $v0, SYS_EXIT + syscall diff --git a/mips_architecture/lab6_ex1.asm b/mips_architecture/lab6_ex1.asm @@ -0,0 +1,37 @@ +.eqv SYS_PRINT_STRING 4 +.eqv SYS_READ_WORD 5 +.eqv SYS_EXIT 10 + +.data + inputmsg: .asciiz "Number: " + evenstr: .asciiz "Even number\n" + oddstr: .asciiz "Odd number\n" + +.text +.globl main + +main: + li $v0, SYS_PRINT_STRING + la $a0, inputmsg + syscall + + li $v0, SYS_READ_WORD + syscall + + # Get the LSB + andi $t0, $v0, 1 + beq $t0, 1, odd + + li $v0, SYS_PRINT_STRING + la $a0, evenstr + syscall + j exit + +odd: + li $v0, SYS_PRINT_STRING + la $a0, oddstr + syscall + +exit: + li $v0, SYS_EXIT + syscall diff --git a/mips_architecture/lab6_ex2.asm b/mips_architecture/lab6_ex2.asm @@ -0,0 +1,37 @@ +.eqv SYS_PRINT_STRING 4 +.eqv SYS_READ_WORD 5 +.eqv SYS_EXIT 10 + +.data + inputmsg: .asciiz "Number: " + ismultstr: .asciiz "Multiple of 4\n" + isnmultstr: .asciiz "Not a multiple of 4\n" + +.text +.globl main + +main: + li $v0, SYS_PRINT_STRING + la $a0, inputmsg + syscall + + li $v0, SYS_READ_WORD + syscall + + # get 2 lowest bits + andi $t0, $v0, 3 + beq $t0, 0, ismult + + li $v0, SYS_PRINT_STRING + la $a0, isnmultstr + syscall + j exit + +ismult: + li $v0, SYS_PRINT_STRING + la $a0, ismultstr + syscall + +exit: + li $v0, SYS_EXIT + syscall diff --git a/mips_architecture/lab6_ex3.asm b/mips_architecture/lab6_ex3.asm @@ -0,0 +1,43 @@ +.eqv SYS_PRINT_STRING 4 +.eqv SYS_READ_WORD 5 +.eqv SYS_EXIT 10 + +.data + inputmsg: .asciiz "Number: " + posstr: .asciiz "Positive\n" + negstr: .asciiz "Negative\n" + +.text +.globl main + +main: + li $v0, SYS_PRINT_STRING + la $a0, inputmsg + syscall + + li $v0, SYS_READ_WORD + syscall + + # Right shift number 31 bits so that the MSB falls + # on the LSB's position. Since we're using 2's + # complement, if the MSB is 1 the number is negative + # and if it's 0 it's positive. After the right shift + # `t0` will either be 0 or 1 + + srl $t0, $v0, 31 + beq $t0, 0, positive + + li $v0, SYS_PRINT_STRING + la $a0, negstr + syscall + + j exit + +positive: + li $v0, SYS_PRINT_STRING + la $a0, posstr + syscall + +exit: + li $v0, SYS_EXIT + syscall diff --git a/mips_architecture/lab6_ex4.asm b/mips_architecture/lab6_ex4.asm @@ -0,0 +1,62 @@ +.eqv SYS_PRINT_WORD 1 +.eqv SYS_PRINT_STRING 4 +.eqv SYS_READ_WORD 5 +.eqv SYS_EXIT 10 + +.data + inputmsg: .asciiz "Number (0-15): " + bounderrstr: .asciiz "Number must be 0-15\n" + binstr: .asciiz "Binary: " + +.text +.globl main + +main: + li $v0, SYS_PRINT_STRING + la $a0, inputmsg + syscall + + li $v0, SYS_READ_WORD + syscall + move $t0, $v0 + + # Bounds check + blt $t0, 0, bounderr + bgt $t0, 15, bounderr + + # Init loop counter, We're right shifting in reverse + # because otherwise the binary number is going to + # show reversed. We assign 3 to `s0` because the range + # 0-15 is 4 bits and we'll go from 3 to 0 (4 iterations). + # We DON'T start with `s0 = 4` because the last bit + # will be eaten. + # For example if the number is 3 then + # + # (0011 >> 3) & 1 = 0000 & 1 = 0 + # (0011 >> 2) & 1 = 0000 & 1 = 0 + # (0011 >> 1) & 1 = 0001 & 1 = 1 + # (0011 >> 0) & 1 = 0011 & 1 = 1 + # + # So the result is 0011 which is the binary form of 3 + li $s0, 3 + +binloop: + srlv $t1, $t0, $s0 # t1 = t0 >> s0 + andi $t2, $t1, 1 # t2 = t1 & 1 + + li $v0, SYS_PRINT_WORD + la $a0, 0($t2) + syscall + + beq $s0, 0, exit + addi $s0, $s0, -1 + j binloop + +bounderr: + li $v0, SYS_PRINT_STRING + la $a0, bounderrstr + syscall + +exit: + li $v0, SYS_EXIT + syscall diff --git a/mips_architecture/lab6_ex5.asm b/mips_architecture/lab6_ex5.asm @@ -0,0 +1,62 @@ +.eqv SYS_PRINT_STRING 4 +.eqv SYS_READ_WORD 5 +.eqv SYS_EXIT 10 +.eqv SYS_PRINT_CHAR 11 + +.data + inputmsg: .asciiz "Number (1-255): " + bounderrstr: .asciiz "Number must be 1-255\n" + resstr: .asciiz "Hex: 0x" + hex: .ascii "0123456789abcdef" + +.text +.globl main + +main: + li $v0, SYS_PRINT_STRING + la $a0, inputmsg + syscall + + li $v0, SYS_READ_WORD + syscall + move $t0, $v0 + + # Bounds check + blt $t0, 1, bounderr + bgt $t0, 255, bounderr + + li $v0, SYS_PRINT_STRING + la $a0, resstr + syscall + + # Get first 4 bits and shift them 4 bits right + # so that `t2` can have their value. For example + # if the number is 50 (00110010): + # + # (00110010 & 0xf0) >> 4 = 00110000 >> 4 = 00000011 = 3 + andi $t1, $t0, 0xf0 + srl $t2, $t1, 4 + + # Print first portion (4 bits) + li $v0, SYS_PRINT_CHAR + lb $a0, hex($t2) + syscall + + # Get last 4 bits. Using 50 as an example again + # 00110010 & 0x0f = 00000010 = 2 + andi $t1, $t0, 0x0f + + # Print second portion (4 bits) + lb $a0, hex($t1) + syscall + + j exit + +bounderr: + li $v0, SYS_PRINT_STRING + la $a0, bounderrstr + syscall + +exit: + li $v0, SYS_EXIT + syscall diff --git a/sh-os1/ex1/ex1.txt b/sh-os1/ex1/ex1.txt @@ -1,750 +0,0 @@ -# Eργαστήριο ΛΣ 1 / Άσκηση 1 / 2020-21 -# Ονοματεπώνυμο: Χρήστος Μαργιώλης -# ΑΜ: [REDACTED] -# ==================================== -# -# Ερώτηση 1: -# ---------- -# Δημιουργήστε στον τρέχοντα κατάλογο το αρχείο 'ask1.txt' με τα ακόλουθα -# περιεχόμενα(όνομα, επώνυμο, username, ΤΚ, περιοχή, τηλ.), και εμφανίστε -# το στησυνέχεια στην οθόνη, με αριθμημένες τις γραμμές του. -# -# Απάντηση: -# Προκειμένου να δημιουργήσουμε ένα αρχείο χρησιμοποιούμε την εντολή 'touch [FILE...]', -# όπου FILE είναι το όνομα του αρχείου και ... ότι μπορούμε να δώσουμε όσα ορίσματα -# θελουμε. Στην προκειμένη περίπτωση - -touch ask1.txt - -# Αν και θα μπορούσαμε να γράψουμε τα δεδομένα του αρχείο σε έναν -# κειμενογράφο, χρησιμοποιώντας την 'echo' (και οποιαδηποτε παρόμοια εντολή, -# όπως την 'printf'), μπορούμε να ανακατευθύνουμε την έξοδο της στο αρχείο που θέλουμε, -# οπότε μπορούμε με τις παρακάτω εντολές να έχουμε το ίδιο αποτέλεσμα. -# Για χάρην απλότητας στο διάβασμα επέλεξα να καλέσω αρκετές φορές την 'echo' αντί να -# ενώσω τα πάντα με newlines. Από την δεύτερη κλήση της και μετά το >> σημαίνει -# ότι θέλουμε να γράψουμε στο τέλος του αρχείο, όχι να γράψουμε το αρχείο από την αρχή. - -echo "George Pappas george2 12136 Peristeri-------" > ask1.txt -echo "Nick Nikolaoy nick23 12232 Aigaleo 5314555" >> ask1.txt -echo "George Georgioy george583 11132 Athens-------" >> ask1.txt -echo "Helen Georgioy helen3 12136 Peristeri 5748456" >> ask1.txt -echo "Nick Pappas nick4 11223 Aigaleo 5324123" >> ask1.txt -echo "Helen Ioannoy helen367 13222 Athens" ------- >> ask1.txt -echo "Helen Thanoy helen36 11132 Peristeri9718345" >> ask1.txt -echo "Vasilis Mamalis vas32 12345 Dafni 9738383" >> ask1.txt - -# Για να εμφανίσουμε τα περιεχόμενα του αρχείου με αριθμημένες σειρές, -# θα χρησιμοποιηθεί η εντολή 'nl', η οποία αριθμεί σειρές, δέχοντας ως -# input το αρχείο με τα περιεχόμενα. - -nl ask1.txt - -# Αποτέλεσμα εκτέλεσης εντολής: -# -# 1 George Pappas george2 12136 Peristeri------- -# 2 Nick Nikolaoy nick23 12232 Aigaleo 5314555 -# 3 George Georgioy george583 11132 Athens------- -# 4 Helen Georgioy helen3 12136 Peristeri 5748456 -# 5 Nick Pappas nick4 11223 Aigaleo 5324123 -# 6 Helen Ioannoy helen367 13222 Athens ------- -# 7 Helen Thanoy helen36 11132 Peristeri9718345 -# 8 Vasilis Mamalis vas32 12345 Dafni 9738383 -# -# Ερώτηση 2: -# ---------- -# Τρέξτε την εντολή cal -3 > calfile.txt και εξηγείστε τι ακριβώς κάνει. -# -# Απάντηση: -# Η εντολή 'cal' αρχικά εμφανίζει ημερολόγιο του τρέχοντος μήνα. Με την -# εντολή - -cal -3 > calfile.txt - -# Θα εμφανιστεί ο προηγούμενος, τρέχων και επόμενος μήνας, και στην συνέχεια -# το output της εντολής θα γραφτεί στο αρχείο calfile.txt -# -# Ερώτηση 3: -# ---------- -# Συνενώστε τα αρχεία calfile.txt και ask1.txt σε ένα αρχείο με όνομα full.txt -# -# Απάντηση: -# Για την συνένωση των δύο παραπάνω αρχείων - και γενικότερα δύο ή παραπάνω -# αρχειών - χρησιμοποιούμε την εντολή 'cat', οπότε - -cat calfile.txt ask1.txt > full.txt - -# Ερώτηση 4: -# ---------- -# Εμφανίστε στην οθόνη τα πέντε πιο πρόσφατα τροποποιημένα αρχεία του καταλόγου σας. -# -# Απάντηση: -# Για να εμφανίσουμε τα αρχεία του καταλόγου χρησιμοποιούμε την εντολή 'ls'. -# Προκειμένου να εμφανιστούν κατά ημερομηνία τροποποίησης ενεργοποιούμε την -# επιλογή -t. Έπειτα θα κάνουμε pipe το output του 'ls' στην εντολή 'head' για να -# εμφανίσουμε μόνο τα 5 πρώτα αρχεία. - -ls -t | head -6 - -# Ερώτηση 5: -# ---------- -# Δημιουργήστε έναν κατάλογο με όνομα 'mydir1'. Μεταβείτε σε αυτόν και στη -# συνέχεια αντιγράψτε εκεί (χωρίς να αλλάξετε κατάλογο) το αρχείο 'full.txt' -# (από το γονικό κατάλογο). Μετονομάστε το εν συνεχεία σε 'new.txt'. -# Επιστρέψτε στο γονικό κατάλογο. Διαγράψτε τον κατάλογο 'mydir1' και τα -# περιεχόμενά του. -# -# Απάντηση: -# Οι εντολές που θα χρειαστούμε είναι οι εξής: -# mkdir Δημιουργεί κατάλογο -# cd Αλλάζει κατάλογο -# cp Αντιγράφει αρχεία και καταλόγους -# rm -rf Διαγράφει αναδρομικά έναν κατάλογο (εφόσον υπάρχει το -rf) -# -# Στην πρώτη σειρά, το && σημαίνει ότι η επόμενη εντολή θα εκτελεστεί -# μόνο αν η προηγούμενη εντολή εκτελεστεί επιτυχώς. Στην δεύτερη σειρά -# το '.' δηλώνει τον κατάλογο που βρισκόμαστε - το '..' δηλώνει -# τον γονικό κατάλογο. - -mkdir mydir1 && cd mydir1 -cp ../full.txt . -cd .. -rm -rf mydir1 - -# Ερώτηση 6: -# ---------- -# Δώστε τις εντολές που θα εμφανίσουν: -# (α) όλα τα αρχεία του καταλόγου /usr με πληροφορίες για το inode τους και -# το μέγεθος τους σε blocks. -# (β) όλα τα περιεχόμενα του δέντρου καταλόγων και υποκαταλόγων (αναδρομικά) -# που βρίσκονται κάτω από τον κατάλογο /usr, με πλήρεις πληροφορίες για -# κάθε ένα από αυτά και εμφανιζόμενα σταδιακά, σελίδα προς σελίδα. -# -# Απάντηση: -# Και στα δύο υποερωτήματα θα χρησιμοποιηθεί η εντολή 'ls' -# (α) Η επιλογή -i εμφανίζει το inode και η επιλογή -# -s το μέγεθος σε blocks, οπότε - -ls -lsi /usr - -# (β) Η επιλογή -R εμφανίζει αναδρομικά όλα τα περιεχόμενα ενός -# καταλόγου, οπότε - -ls -lR /usr - -# Ερώτηση 7: -# ---------- -# Δημιουργήστε έναν κατάλογο με όνομα 'testdir1'. Μεταβείτε σε αυτόν -# και φτιάξτε εκεί ένα hard link (με το όνομα 'ask1link') προς το αρχείο -# 'ask1.txt' του γονικού καταλόγου. Βεβαιωθείτε (δίνοντας την κατάλληλη -# εντολή και εξηγώντας τι βλέπετε) ότι έχει δημιουργηθεί και ότι δεν είναι -# symbolic (soft) link. -# -# Απάντηση: -# Για να φτιάξουμε hard link θα χρησιμοποιήσουμε την εντολή 'ln'. - -mkdir testdir1 && cd testdir1 -ln ../ask1.txt ask1link - -# Αν εκτελέσουμε την εντολή 'ls -li' στον κατάλογο testdir1 θα δούμε -# ότι σε αντίθεση με το soft link, στο hard link δεν εμφανίζεται -# το -> το οποίο δηλώνει ότι είναι symbolic link. -# -# 11403520 -rw-r--r-- 2 christos wheel 350 Nov 11 12:28 ask1link -# -# Επίσης παρατηρούμε ότι και το ask1link αλλά και το ask1.txt έχουν το ίδιο inode. -# -# 11403520 -rw-r--r-- 2 christos wheel 350 Nov 11 12:28 ask1.txt -# 11403520 -rw-r--r-- 2 christos wheel 350 Nov 11 12:28 ask1link -# -# Ερώτηση 8: -# ---------- -# Μπείτε στο αρχείο 'ask1link' και διαγράψτε την τελευταία του γραμμή. -# Βεβαιωθείτε στη συνέχεια ότι η αλλαγή αυτή έχει γίνει και στο αρχείο 'ask1.txt'. -# -# Απάντηση: -# Εφόσον το ask1link ειναι hardlink στο 'ask1.txt', δηλαδή είναι reference -# στο 'ask1.txt', ό,τι αλλαγή γίνει στο ένα αρχείο, θα γίνει και στο άλλο, -# οπότε αν διαγράψουμε την τελευταία γραμμή από το 'ask1link', η αλλαγή -# πράγματι θα έχει γίνει και στο 'ask1.txt'. Ανοίγουμε το 'ask1link' στο -# Vim και εκτελούμε τις εξής εντολές ώστε να σβήσουμε την τελευταία γραμμή - -# vim ask1link - -# G πάει στην τελευταία γραμμή -# dd την σβήνει -# ZZ βγαίνουμε από το Vim -# -# Τώρα κάνοντας - -cd .. -diff ask1.txt testdir1/ask1link - -# βλέπουμε ότι εντολή δεν βγάζει output, το οποίο σημαίνει ότι τα αρχεία -# είναι ίδια, οπότε η αλλαγή που κάναμε στο ένα αρχείο ίσχυσε και στο άλλο. -# -# Ερώτηση 9: -# ---------- -# Δημιουργήστε ένα κατάλογο kat1 και μέσα σε αυτόν δύο αρχεία, file1 και file2, -# με περιεχόμενο τη λέξη 'one' το ένα και τη λέξη 'two' το άλλο. -# Τρέξτε (μέσα στον κατάλογο kat1) την εντολή 'cp *' και εξηγήστε το αποτέλεσμα. -# Στη συνέχεια τρέξτε την εντολή 'mv *' και εξηγήστε το αποτέλεσμα. -# -# Απάντηση: -# Αρχικά πρέπει να γράψουμε τα περιέχομενα στα κατάλληλα αρχεία. - -mkdir kat1 && cd kat1 -echo "one" > file1 -echo "two" > file2 - -# Αφού τρέξουμε την εντολή 'cp *' στον kat1 θα παρατηρήσουμε ότι και τα -# δύο αρχεία τώρα έχουν την λέξη "one". - -cp * -cat file1 file2 - -# one -# one -# -# Αυτό γίνεται επειδή γράφοντας 'cp *', επιλέγουμε όλα τα αρχεία του -# καταλόγου. Επειδή όμως έχουμε δύο αρχεία η εντολή θα αναπτυχθεί σε -# -# cp file1 file2 -# -# και αυτό που θα γίνει τελικά είναι να αντιγραφεί το file1 στο file2. -# Όταν τρέξουμε την εντολή 'mv *' θα δούμε ότι διαγράφεται το file1, -# επειδή, όπως και με την 'cp *', η εντολή θα αναπτυχθεί σε - -mv file1 file2 -ls -cd .. - -# οπότε το file1 θα μετονομαστεί σε file2, και έτσι θα χαθεί. -# -# Ερώτηση 10: -# ----------- -# Εμφανίστε τις γραμμές του αρχείου 'ask1.txt' οι οποίες τελειώνουν -# με ένα ή περισσότερα συνεχόμενα ψηφία. -# -# Απάντηση: -# Η εντολή 'grep' δέχεται ένα regular expression (regex) και επιστρέφει -# τις γραμμές στο αρχείο στις οποίες βρίσκεται το regex. -# Το regex που θα ψάξουμε θα αποτελείται από τα εξής μέρη: -# -# 1. [0-9] οποιδήποτε ψηφίο από το 0 εώς το 9 -# 2. \+ μία ή παραπάνω επαναλήψεις του προηγούμενου -# 3. $ τέλος γραμμής -# -# Οπότε η τελική εντολή θα είναι - -grep "[0-9]\+$" ask1.txt - -# Ερώτηση 11: -# ----------- -# Εμφανίστε τις γραμμές του αρχείου 'ask1.txt' οι οποίες περιέχουν μεν -# το πρότυπο 'Pap' αλλά δεν περιέχουν το πρότυπο 'Aig'. -# -# Απάντηση: -# Στην εντολή 'grep' η επιλογή -v αποκλείει το δοθέν regex. Προκειμένου -# πρώτα να πάρουμε τις γραμμές που περιέχουν το πρότυπο 'Pap' αλλα όχι -# το πρότυπο 'Aig', θα εκτελέσουμε το 'grep' 2 φορές, ώστε πρώτα να πάρουμε -# όλες τις γραμμές που περιέχουν το 'Pap' και μετά να αποκλείσουμε το 'Aig'. - -grep "Pap" ask1.txt | grep -v "Aig" - -# Ερώτηση 12: -# ----------- -# Εμφανίστε τις γραμμές του αρχείου 'ask1.txt' οι οποίες δεν αρχίζουν -# με 'G' ή 'N' και περιέχουν εν συνεχεία (κάπου στα περιεχόμενά τους) -# τα πρότυπα 'Geo' και 'Per' με αυτή τη σειρά.' -# -# Aπάντηση: -# Όπως και στην ερώτηση 11, θα μπορούσαμε να χρησιμοποιήσουμε την επιλογή -# -v για την εντολή 'grep', αλλα θα χρησιμοποιήσουμε μία διαφορετική σύνταξη. -# Αυτή τη φορά τα regex που θα ψάξουμε είναι τα εξής -# -# Για την πρώτη κλήση: -# 1. ^ ξεκινάει με -# 2. ^[GN] πρεπει να ξεκινάει με G ή N -# 3. ^[^GN] ΔΕΝ πρέπει να ξεκινάει με G ή N -# -# Για την δεύτερη κλήση: -# 1. Geo περιέχει την λέξη 'Geo' -# 2. .* οποιοσδήποτε αριθμός οποιουδήποτε χαρακτήρα -# 3. Per περιέχει την λέξη 'Per' -# -# Οπότε η τελική εντολή είναι (το | ειναι separator) - -grep "^[^GN]" ask1.txt | grep "Geo.*Per" - -# Αποτέλεσμα εκτέλεσης εντολής: -# -# Helen Georgioy helen3 12136 Peristeri 5748456 -# -# Ερώτηση 13: -# ----------- -# Πόσοι χρήστες που το username τους δεν αρχίζει από 'ls1' είναι -# συνδεδεμένοι στο σύστημα; -# -# Απάντηση: -# Η εντολή 'who' μπορεί να μας επιστρέψει μια λίστα με τους χρήστες -# που είναι συνδεδεμένοι. Ο λόγος που χρησιμοποίησα την 'who' αντί -# για την 'w' που κάνει περίπου το ίδιο πράγμα είναι επειδή η 'w' -# έχει και μια γραμμή header στην αρχή, οπότε 'wc -l' θα την μέτραγε. -# Με την χρήση της εντολής 'wc' μπορούμε να μετρήσουμε λέξεις, γραμμές -# και χαρακτήρες. Αν στην εντολή 'wc' δώσουμε την επιλογή -l τότε θα -# μετρήσει μόνο πόσες γραμμές έχει το input που της δώθηκε. - -who | grep -v "^ls1" | wc -l - -# Ερώτηση 14: -# ----------- -# Εμφανίστε όλες τις διεργασίες χρηστών (αλλ/σης) που τρέχουν αυτή -# τη στιγμή στο σύστημα. -# -# Απάντηση: -# Η εντολή 'ps' (process status) εμφανίζει τις τρέχουσες διεργασίες που -# εκτελεί το σύστημα. Επιπλέον θα χρειαστούμε τις επιλογές a και u, οι οποίες -# εμφανίζουν τις διεργασίες που εκτελούνται από όλους τους συνδεδεμένους χρήστες -# αυτή τη στιγμη. Στην εντολή 'ps' χρησιμοποιήσα την BSD σύνταξη. - -ps -au - -# Αποτέλεσμα εκτέλεσης της εντολής: -# -# USER PID %CPU %MEM VSZ RSS TT STAT STARTED TIME COMMAND -# christos 5200 0.1 0.1 18048 7084 2 Ss 21:44 0:09.04 /usr/local/bin/zsh -# christos 1160 0.0 0.1 15072 6016 v0 I 12:19 0:00.07 -zsh (zsh) -# christos 1175 0.0 0.0 11828 3044 v0 I+ 12:19 0:00.00 /bin/sh /usr/local/bin/startx -# christos 1188 0.0 0.0 13164 3240 v0 I+ 12:19 0:00.00 xinit /home/christos/.xinitrc -# christos 1192 0.0 0.1 22152 11360 v0 S 12:19 0:19.69 dwm -# christos 1218 0.0 0.1 17136 8000 0- S 12:20 0:16.20 slstatus -# christos 5005 0.0 0.1 18004 7000 1 Is 21:15 0:00.31 /usr/local/bin/zsh -# christos 5193 0.0 0.2 28028 16288 1 S+ 21:44 0:07.88 nvim ex1.txt -# christos 6849 0.0 0.0 11860 3080 2 R+ 00:22 0:00.00 ps -u -# root 1158 0.0 0.0 10880 2304 v1 Is+ 13:14 0:00.00 /usr/libexec/getty Pc ttyv1 -# root 1159 0.0 0.0 10880 2304 v2 Is+ 13:14 0:00.00 /usr/libexec/getty Pc ttyv2 -# root 1160 0.0 0.0 10880 2304 v3 Is+ 13:14 0:00.00 /usr/libexec/getty Pc ttyv3 -# -# Ερώτηση 15: -# ----------- -# Πόσες διεργασίες χρηστών (αλλ/σης) τρέχουν στο σύστημα και τελειώνει -# το όνομά τους με 'sh' ? -# -# Απάντηση: -# Τρέχοντας την εντολή της ερώτησης 14 (ps -ux) και φιλτράροντας -# το ouput ώστε να πάρουμε μόνο τις γραμμές που τελειώνουν σε -# 'sh', έχω 3 διεργασίες που το όνομα τους τελειώνει σε 'sh' - -ps -au | grep "sh$" | wc -l - -# Συνολικά έχουμε 3 διεργασίες που τελειώνουν σε sh. -# -# Ερώτηση 16: -# ----------- -# Εμφανίστε όλες τις διεργασίες χρηστών (αλλ/σης) που τρέχουν αυτή τη στιγμή στο σύστημα. -# -# Απάντηση: -# Αυτή τη φορά στην εντολή 'ps', πέρα από την επιλογή u, θα δώσουμε και την επιλογή -# x, η οποία εμφναίζει πληροφορίες ακόμα και για διεργασίες που δεν ελέγχουν κάποιο terminal - -ps -aux - -# Το output της εντολής είναι πολύ μεγάλο για να το συμπεριλάβω εδώ. -# -# Ερώτηση 17: -# ----------- -# Πόσα αρχεία του τρέχοντος καταλόγου σας (μόνο του τρέχοντος -όχι και -# των υποκαταλόγων του) έχουν permissions 'rw' από τους πάντες και 'x' -# από κανέναν; -# -# Απάντηση: -# Η 'ls -l' στην αρχή κάθε σειράς εμφανίζει το permission string και με την -# 'grep' μπορούμε να εμφανίσουμε μόνο τις γραμμές που περιέχουν το permission -# που ζητάει η εκφώνηση. Τέλος διοχετεύουμε την έξοδο στην 'wc -l'. - -ls -l | grep "^-rw-rw-rw-" | wc -l - -# Ερώτηση 18: -# ----------- -# Βρείτε τους καταλόγους του συστήματος που το όνομά τους αρχίζει από 'b'. -# -# Απάντηση: -# Η εντολή 'find' είναι μια πιο ανεπτυγμένη μορφή της 'ls' στην οποία μπορούμε -# να δώσουμε πολλές παραπάνω επιλογές. Οι επιλογές που έχουν δωθεί στην παρακάτω εντολή -# σημαίνουν τα εξής: -# /* - η αναζήτηση ξεκινάει από την ρίζα του συστήματος (root directory) -# -type d - αναζήτηση μόνο για directories -# -name "b*" - το όνομα τους πρέπει να ξεκινάει από 'b' - -find /* -type d -name "b*" - -# Ερώτηση 19: -# ----------- -# Να βρείτε και να παρουσιάσετε στην οθόνη με πλήρεις πληροφορίες -# όλα τα αρχεία με όνομα που αρχίζει από tty και βρίσκονται στον κατάλογο /dev. -# -# Απάντηση: -# Η εντολή stat επιστρέφει πλήρεις πληροφορίες για ένα αρχείο. -# Με την εντολή 'grep', όπως έχει ειπωθεί και σε παραπάνω ερωτήσεις, μπορούμε -# να πάρουμε τις γραμμές στις οποίες γίνεται match ένα regular -# expression - έτσι κατά την εμφάνιση των αρχείων του /dev μπορούμε -# να εξάγουμε μόνο όσες γραμμές περιέχουν την λέξη 'tty'. - -stat /dev/* | grep "tty" - -# Ερώτηση 20: -# ----------- -# Ταξινομήστε τα περιεχόμενα του αρχείου 'ask1.txt' ως προς το -# username σε φθίνουσα σειρά. -# -# Απάντηση: -# Θα ταξινομίσουμε το αρχείο με την χρήση της εντολής 'sort'. -# Στην εντολή αυτή μπορούμε να της δώσουμε κατα ποιά στήλη θέλουμε -# να ταξινομηθεί το αρχείο με την επιλογή -k. Εφόσον username -# βρίσκεται στην 3η στήλη, θα δώσουμε την 3η στήλη ως μέσο -# σύγκρισης για ταξινόμηση. Επίσης, προκειμένου να είναι κατα -# φθήνουσα σειρά η ταξινόμηση, θα χρησιμοποιήσουμε την επιλογή -r - -sort -rk 3 ask1.txt - -# Σε περίπτωση που θέλουμε οι αλλαγές να γραφτούν στο αρχείο, μπορούμε -# να γράψουμε την εντολή ως -# -# sort -rk 3 ask1.txt -o ask1.txt -# -# Ερώτηση 21: -# ----------- -# Ταξινομήστε τα '.c' αρχεία του καταλόγου στον οποίον δουλεύετε ως -# προς το μέγεθός τους. -# -# Απάντηση: -# Στην εντολή 'ls' η επιλογή -S ταξινομεί τα αρχεία ανάλογα με το -# μέγεθός του κατα φθήνουσα σειρά (μεγαλύτερο πρώτα), οπότε - -ls -S *.c - -# Ερώτηση 22: -# ----------- -# Ταξινομήστε τα αρχεία του λογαριασμού σας με permissions 644 -# ως προς το μέγεθός τους. -# -# Απάντηση: -# Μπορούμε να εμφανίσουμε αρχεία που έχουν συγκεκριμένα permissions -# με την εντολή 'find' και την επιλογή -perm [PERMISSION] όπου -# το PERMISSION πρέπει να δωθεί σε οκταδικό. Επίσης μέσα στην 'find' -# μπορούμε να εκτελέσουμε και επιπλέον shell commands στο output της με -# την επιλογή -exec [COMMAND] - θα χρησιμοποιήσουμε την 'ls -alS' ώστε -# να ταξινομήσει το output κατα μέγεθος. Η τελική εντολή θα εκτελεστεί -# στον κατάλογο '/usr/home/christos', ο οποίος είναι ο κατάλογος του λογαριασμού -# μου. Το {} \; στο τέλος της εντολής δηλώνει ότι η 'ls -alS' θα εκτελεστεί -# σε κάθε αρχείο που βρίσκεται από την 'find'. - -find /home/christos -perm 644 -exec ls -alS {} \; - -# Ερώτηση 23: -# ----------- -# Ταξινομήστε όλα τα περιεχόμενα του καταλόγου /dev κατά πρώτον ως προς -# τον owner και κατά δεύτερον ως προς το group και αποθηκεύστε το -# output στο αρχείο 'binfiles.txt'. -# -# Аπάντηση: -# Παίρνοντας πληροφορίες για τον owner και το group των αρχείων με την -# 'ls -l /dev' μπορούμε να ταξινομήσουμε τις κατάλληλες στήλες (3 για owner -# και 4 για group). - -ls -l /dev | sort -k 3,4 > binfiles.txt - -# Ερώτηση 24: -# ----------- -# Φτιάξτε ένα αρχείο που θα περιέχει πληροφορίες μόνο για τους συνδεδεμένους -# χρήστες που το username τους αρχίζει από 'ls1', ταξινομημένο ως προς -# την ημερομηνία και ώρα σύνδεσή τους. -# -# Απάντηση: -# ΑΦού φιλτραριστεί το ouput της 'who' ώστε να πάρουμε μόνο τους -# χρήστες που το όνομά τους ξεκινάει από ls1, θα ταξινομήσουμε -# κατά 3η και 4η στήλη επειδή αυτές δείχνουν την ημερομηνία -# και ώρα σύνδεσης. - -who | grep "^ls1" | sort -k 3,4 > userinfo.txt - -# Ερώτηση 25: -# ----------- -# Αλλάξτε στο αρχείο 'ask1.txt' το όνομα 'Nick' (όπου συναντάται) σε 'Nickolaos'. -# -# Απάντηση: -# Με την χρήση της εντολής 'sed' (stream editor) μπορούμε να αλλάξουμε ένα -# pattern κάθε φορά που συναντάται με την παρακάτω σύνταξη -# -# sed "s/PATTERN/NEWPATTERN/g" file -# -# Τo g στο τέλος σημαίνει ότι αυτή η αλλαγή πρέπει να γίνει σε όλο το αρχείο, -# και όχι μόνο την πρώτη φορά που θα συναντήσει το PATTERN. -# Οπότε, στην προκειμένη περίπτωση η εντολή που θα εκτελεστεί είναι - -sed "s/Nick/Nickolaos/g" ask1.txt - -# Εάν θέλουμε οι αλλαγές να αποθηκευτούν στο αρχείο κατευθείαν, μπορούμε -# να εκτελέσουμε την εντολή με την επιλογή -i. - -sed -i "s/Nick/Nickolaos/g" ask1.txt - -# Ερώτηση 26: -# ----------- -# Έστω τα ακόλουθα items του filesystem με protection strings: -# (α) '-rwxr-x--x', -# (β) 'drwxr-x---' και -# (γ) 'drwx--x--x. -# Εξηγείστε τι είδους items είναι και ποια τα δικαιώματα πρόσβασης user, -# group και others σε αυτά. -# -# Απάντηση: -# (α) Το είδος item είναι απλό αρχείο εφόσον το πρώτο πεδίο του protection string -# είναι κενό. Όσο αφορά τα δικαίωματα του, δικαίωμα εγγραφής έχει μόνο ο ιδιοκτήτης -# του αρχείο, διαβάσματος ο ιδιοκτήτης του αρχείου, και όσοι είναι στο ίδιο group με αυτόν. -# Επίσης όλοι οι χρήστες μπορούνε να το εκτελέσουν. -# -# (β) Το είδος είναι directory λόγω του 'd' στο πρώτο πεδίο του string. Δικαίωμα εγγραφής -# έχει μόνο ο ιδιοκτήτης, διαβάσματος και εκτέλεσης ο ιδιοκτήτης και τα μέλη του group - -# οι υπόλοιποι χρήστες δεν έχουν δικαιώματα για το συγκεκριμένο directory. -# -# (γ) Το είδος είναι επίσης directory λόγω του 'd' στο πρώτο πεδίο του string. Δικαίωμα -# εγγραφής και διαβάσματος έχει μόνο ο ιδιοκτήτης και εκτέλεσης όλοι οι χρήστες. -# -# Ερώτηση 27: -# ----------- -# Αλλάξτε τα permissions όλων των αρχείων του καταλόγου 'testdir1' -# έτσι ώστε να έχουν δικαίωμα εκτέλεσης και εγγραφής μόνο ο ιδιοκτήτης, -# ενώ δικαίωμα ανάγνωσης να έχουν όλοι. -# -# Απάντηση: -# Η εντολή 'chmod' μπορεί να αλλάξει permissions. Με την επιλογή 'R' δηλώνουμε -# ότι αυτό θέλουμε να γίνει αναδρομικά εφόσον θέλουμε να αλλάξουμε τα permissions -# όλων των αρχείων του καταλόγου 'testdir1'. Τα υπόλοιπα πεδία σημαίνουν τα εξής: -# a=r - όλοι οι χρήστες έχουν δικαίωμα ανάγνωσης -# u+wx - προσθέτουμε στον ιδιοκτήτη του αρχείου και τα δικαιώματα εγγραφής και εκτέλεσης - -sudo chmod -R a=r,u+wx testdir1 - -# Ερώτηση 28: -# ----------- -# Αλλάξτε τα permissions του καταλόγου 'testdir1' έτσι ώστε να έχουν δικαίωμα -# πρόσβασης μόνο ο ιδιοκτήτης και οι χρήστες του ιδίου με αυτόν group, -# ενώ οι υπόλοιποι χρήστες να μην έχουν (θεωρείστε ότι τα τρέχοντα -# permissions του καταλόγου είναι 755). -# -# Απάντηση: -# Χρησιμοποιώντας πάλι την εντολή 'chmod' μπορούμε να αλλάξουμε και τα permissions -# ενός καταλόγου. Τα πεδία τώρα σημαίνουν τα εξής: -# ug+r - ο ιδιοκτήτης και τα μέλη του group έχουν δικαίωμα διαβάσματος -# o-r - οι υπόλοιποι χρήστες δεν έχουν δικαίωμα διαβάσματος - -sudo chmod ug+r,o-r testdir1 - -# Ερώτηση 29: -# ----------- -# Δημιουργήστε έναν νέο χρήστη στο σύστημά σας με username 'myfriend'. -# Αλλάξτε στη συνέχεια τον ιδιοκτήτη του αρχείου 'ask1.txt' σε 'myfriend' και -# μετακινήστε το στο working directory του. Περιορίστε τέλος το διαθέσιμο -# χώρο αποθήκευσης στο δίσκο για το συγκεκριμένο χρήστη στα 10MB. -# -# Απάντηση: -# Για να φτιάξουμε έναν user χρησιμοποιούμε την εντολή 'useradd'. Σε BSD -# συστήματα η εντολή είναι η 'adduser'. Για να αλλάξουμε ιδιοκτήτη αρχείου -# χρησιμοποιούμε την εντολή 'chown'. Τέλος, για να περιορίσουμε τον χώρο -# αποθηκεύσης στον δίσκο για έναν χρήστη χρησιμοποιούμε την εντολή 'edquota'. - -useradd -m -d /home/myfriend myfriend -chown myfriend ask1.txt -mv ask1.txt /home/myfriend -edquota myfriend - -# Η εντολή 'edquota' θα μάς ανοίξει στον default editor μας ένα αρχείο -# στο οποίο μπορούμε να τροποποιήσουμε τον αποθηκευτικό χώρο για τον χρήστη -# myfriend. Θα πρέπει να δούμε κάτι σαν -# -# Disk quotas for user ice19390133 (uid 1022): -# Filesystem blocks soft hard inodes soft hard -# /dev/vda1 36 10240 13312 11 0 0 -# -# Το 'soft' το θέτουμε σε 10240 (kilobyte), δηλαδή 10MB. -# -# Ερώτηση 30: -# ----------- -# Έστω τα παρακάτω: -# user1@localhost:~$ w -# USER TTY FROM LOGIN@ IDLE JCPU PCPU WHAT -# user1 pts/0 1.2.3.4 03:34 0.00s 0.38s 0.01s w -# user2 pts/1 5.6.7.8 03:45 0.00s 0.38s 0.01s ls -# user3 pts/2 9.7.5.3 03:57 0.00s 0.38s 0.01s ps -# -# user1@localhost:~$ ls -al /dev/pts/* -# crw--w---- 1 user1 tty136, 0 Oct 25 04:04 /dev/pts/0 -# crw--w--w- 1 user2 tty136, 1 Oct 25 04:04 /dev/pts/1 -# crw--w--w- 1 user3 tty136, 2 Oct 25 04:04 /dev/pts/2 -# -# Εξηγήστε τι είδους items του file system είναι τα παραπάνω, -# καθώς και τι θα κάνουν οι παρακάτω εντολές: -# user1@localhost:~$ cat > /dev/pts/1 -# user1@localhost:~$ wall "test" -# -# Απάντηση: -# Σε ένα permission string, το 'c' δηλώνει ότι αυτό το item -# ειναι 'character device', το οποίο πρακτικά σημαίνει συσκευές -# οι οποίες μεταφέρουν δεδομένα σε μορφή κειμένου (bytes). Τέτοιες -# συσκευές είναι για παράδειγμα τα ηχεία. Στην προκειμένη περίπτωση -# το item ειναι 'tty' (από το teletype), δηλαδή είναι terminals. Τα -# συγκεκριμένα terminals ειναι συνδεδεμένα με το πληκτρολόγιο. -# -# Η εντολή 'cat > /dev/pts/1' θα εμφανίζει στο πρώτο terminal που -# ανοίχτηκε οτίδηποτε γράψουμε στο stdin. Στον κατάλογο /dev/pts/ -# εμφανίζονται τα ανοιχτά terminals που τρέχουν αυτή τη στιγμή. - -cat > /dev/pts/1 - -# hello world -# hello world -# -# Η εντολή 'wall "test"' θα στείλει το μήνυμα "test" σε όλους τους -# συνδεδεμένους χρήστες. - -wall "test" - -# Broadcast message from christos@freebsd (pts/1) (Wed Nov 14 23:26:58 2020): -# -# test -# -# -# Ερώτηση 31: -# ----------- -# Δημιουργείστε τα αρχεία f1, f2, f3, f4, f5, f6 ,f7 με τα εξής δικαιώματα: -# f1, 757 -# f2, 313 -# f3, 010 -# f4, 642 -# f5, 551 -# f6, 133 -# f7, 111 -# Με χρήση της εντολής ls –l και διοχετεύοντας τα αποτελέσματά της στην εντολή -# egrep να βρείτε τα αρχεία όπου: -# a. To group έχει δικαιώματα r-x. -# b. Ο user και οι others έχουν ακριβώς τα ίδια δικαιώματα -# c. Ο user, το group και οι others έχουν τα ίδια δικαιώματα για write -# d. Ο user, το group και οι others έχουν τα ίδια δικαιώματα για write και execute -# e. To group και οι others έχουν τα ίδια δικαιώματα για read και execute -# -# Απάντηση: -# Αρχικά θα δημιουργήσουμε τα αρχεία με τα κατάλληλα permissions - -touch f1 && chmod 757 f1 -touch f2 && chmod 313 f2 -touch f3 && chmod 010 f3 -touch f4 && chmod 642 f4 -touch f5 && chmod 551 f5 -touch f6 && chmod 133 f6 -touch f7 && chmod 111 f7 - -# a) Το pattern που θα αναζητήσουμε είναι στο permission string να περιέχονται -# οποιοιδήποτε χαρακτήρες σε όλα τα πεδία αλλά πρέπει οπωσδήποτε τα permissions -# του group να είναι r-x. Το - στην αρχή το βάζουμε για να ψάξουμε μόνο αρχεία και όχι -# τυχόν directories. - -ls -l | egrep "^-...r-x..." - -# Αποτέλεσμα εκτέλεσης της εντολής: -# -# -rwxr-xrwx 1 christos christos 0 Nov 14 22:16 f1 -# -r-xr-x--x 1 christos christos 0 Nov 14 22:16 f5 -# -# b) Θα φτιάξουμε ένα capture group στα πεδια που βρισκονται τα permissions -# του user ώστε να ψάξουμε ό,τι αποθηκεύτηκε στην μεταβλητή 1 -# στο πεδίο που βρίσκονται τα permissions των others. Ένα capture group φτιάχνουμε -# βάζοντας () και γράφοντας μέσα το pattern που θέλουμε. - -ls -l | egrep "^-(...)...\1" - -# Πιο αναλυτικά συμβαίνει το εξής: -# 1. Θέλουμε το pattern να ξεκινάει με - ώστε να είναι αρχείο. -# 2. Αποθηκεύουμε τους 3 επόμενους χαρακτήρες στη μεταβλητή 1. -# 3. Έχουμε φτάσει στο πεδίο του group, οπότε ψάχνουμε για οποιονδήποτε -# χαρακτήρα επειδή δεν μας νοιάζει σε αυτό το παράδειγμα τι permissions έχει το group. -# 4. Тώρα είμαστε στο πεδίο των others. Εμφανίζουμε τη μεταβλητή 1 η οποία έχει κρατήσει -# τα permissions του user. -# -# Αποτέλεσμα εκτέλεσης της εντολής: -# -# -rwxr-xrwx 1 christos christos 0 Nov 14 22:16 f1 -# --wx--x-wx 1 christos christos 0 Nov 14 22:16 f2 -# ------x--- 1 christos christos 0 Nov 14 22:16 f3 -# ---x--x--x 1 christos christos 0 Nov 14 22:16 f7 -# -# c) Με την ίδια λογική όπως στο ερώτημα b, απλώς αυτή τη φορά δεν θα κρατήσουμε όλα τα -# permissions του user, αλλά μόνο τα permissions για write. - -ls -l | egrep "^-.(.)..\1..\1." - -# Αποτέλεσμα εκτέλεσης της εντολής: -# -# ------x--- 1 christos christos 0 Nov 14 22:16 f3 -# -r-xr-x--x 1 christos christos 0 Nov 14 22:16 f5 -# ---x--x--x 1 christos christos 0 Nov 14 22:16 f7 -# -# d) Ξανά με την ίδια λογική, αλλά κρατήσουμε τα πεδία για write και execute. - -ls -l | egrep "^-.(..).\1.\1" - -# Αποτέλεσμα εκτέλεσης της εντολής: -# -# -r-xr-x--x 1 christos christos 0 Nov 14 22:16 f5 -# ---x--x--x 1 christos christos 0 Nov 14 22:16 f7 -# -# e) Αυτή τη φορά θα κρατήσουμε στις μεταβλητές τα permissions από το group, και όχι -# από τον user. - -ls -l | egrep "^-...(.).(.)\1.\2" - -# Αποτέλεσμα εκτέλεσης της εντολής: -# -# -rwxr-xrwx 1 christos christos 0 Nov 14 22:16 f1 -# --wx--x-wx 1 christos christos 0 Nov 14 22:16 f2 -# ---x-wx-wx 1 christos christos 0 Nov 14 22:16 f6 -# ---x--x--x 1 christos christos 0 Nov 14 22:16 f7 -# -# Ερώτηση 32: -# ----------- -# Υποθέστε πως οι γραμμές στο αρχείο /etc/passwd είναι όμοιες με την παρακάτω: -# -# spouneri:x:2107:1067:Pouneridis Sokratis:/home/student/e2021/spouneri:/bin/bash -# -# Στο πέμπτο πεδίο θα υπάρχει πάντα πρώτο το επίθετο και μετά το όνομα του χρήστη. -# Μόνο ένα επίθετο και μόνο ένα όνομα, γραμμένα με λατινικούς χαρακτήρες κεφαλαίους -# ή/και πεζούς. -# -# Τα υπόλοιπα πεδία θα είναι γραμμένα πάντα με πεζούς λατινικούς -# χαρακτήρες. -# -# Ελέγχοντας το αρχείο /etc/passwd και κάνοντας χρήση της εντολής egrep -# βρείτε όλους τους (υποθετικούς) χρήστες του συστήματος όπου: -# -# a. Χρησιμοποιούν για κέλυφος το bash -# b. To HOME DIRECTORY τους βρίσκεται στον κατάλογο /home -# c. To UID τους είναι ίδιο μετο GID τους -# d. Τουλάχιστον τα 5 πρώτα γράμματα του επιθέτου τους αποτελούν μέρος και του username τους -# e. Τουλάχιστον τα 3 πρώτα γράμματα του επιθέτου τους και τα 3 πρώτα γράμματα του -# ονόματός τους αποτελούν μέρος και του username τους. -# -# Απάντηση: -# -# a. Εφόσον το shell βρίσκεται πάντα στο τέλος της γραμμής, μπορούμε να κάνουμε - -egrep "/bin/bash$" /etc/passwd - -# b. Αφού φτάσουμε στο πεδίο όπου βρίσκεται το Home directory, θα φροντίσουμε -# να εμφανιστούνε μόνο οι γραμμές που ξεκινάνε με '/home'. - -egrep "^[a-z]+:.+:[0-9]+:[0-9]+:.+:/home/*" /etc/passwd - -# c. Θα χρησιμοποιήσουμε την ίδια τεχνική με τα capture groups που χρησιμοποίησα -# και στην άσκηση 31. - -egrep "^[a-z]+:.+:([0-9]+):\1" /etc/passwd diff --git a/sh-os1/ex2/bck b/sh-os1/ex2/bck @@ -1,48 +0,0 @@ -#!/bin/sh - -# ΧΡΗΣΤΟΣ ΜΑΡΓΙΩΛΗΣ - [REDACTED] - -main() { - # We could allow more than 4 command line arguments - # since it's not going to make a difference, but for - # safety, we'll exit if they're not exactly 4. - test $# -eq 3 || usage - - # Give readable names to each argument. - username=${1} - src=${2} - dst=${3} - - # Error checks. - # In order for `username` to really be a user's name, it - # has to exist in `/etc/passwd`. - test ! -z "$(grep -w "^${username}" /etc/passwd)" || - err "'${username}' is not in /etc/passwd" - - # The -e options means anything (file, directory, device, etc.). - test -e ${src} || err "${src}: no such file or directory" - test -e ${dst} || err "${dst}: no such file or directory" - - # Create an archive if `dst` is a directory. - test -d ${dst} && tar -cvf "${dst}/${src##*/}.tar" ${src} - - # Append to `dst` only if it is a tar archive. If it's a non-archive - # then we cannot append since that would not make sense. - # `{dst##*.}` means that we want to get only its extension, if any. - test ${dst##*.} = "tar" && tar -rf ${dst} ${src} -} - -usage() { - # `{0##*/}` means the first argument (i.e the script's name) with - # its path stripped, if it exists. - echo "usage: ${0##*/} username src dst" 1>&2 - exit 1 -} - -err() { - echo "${0##*/}: $@" 1>&2 - exit 1 -} - -# Pass all command line arguments to `main`. -main "$@" diff --git a/sh-os1/ex2/createpvs b/sh-os1/ex2/createpvs @@ -1,81 +0,0 @@ -#!/bin/sh - -# ΧΡΗΣΤΟΣ ΜΑΡΓΙΩΛΗΣ - [REDACTED] - -main() { - # We could allow more than 4 command line arguments - # since it's not going to make a difference, but for - # safety, we'll exit if they're not exactly 4. - test $# -eq 4 || usage - - # Give readable names to each argument. - rootdir=${1} - ndbdirs=${2} - ndatadirs=${3} - username=${4} - - # Error checks. - test -d "${rootdir}" || err "${rootdir}: no such directory" - isnumber ${ndbdirs} || err "'${ndbdirs}' is not a number" - isnumber ${ndatadirs} || err "'${ndatadirs}' is not a number" - - # In order for `username` to really be a user's name, it - # has to exist in `/etc/passwd`. - test ! -z "$(grep -w "^${username}" /etc/passwd)" || - err "'${username}' is not in /etc/passwd" - - # The actual exercise. - makedirs "dbfolder" ${ndbdirs} - makedirs "datafolder" ${ndatadirs} -} - -usage() { - # `{0##*/}` means the first argument (i.e the script's name) with - # its path stripped, if it exists. - echo "usage: ${0##*/} root_dir num_dbdirs num_datadirs username" 1>&2 - exit 1 -} - -err() { - echo "${0##*/}: $@" 1>&2 - exit 1 -} - -isnumber() { - # If the argument does not begin *and* end in a number, then - # it's not a number. This also excludes negative numbers, but - # we shouldn't accept negative numbers anyway. - test ! -z "$(echo "${1}" | grep "^[0-9]\+$")" -} - -# Make directories in the following format: dir1, dir2, dir3... -# If there are already directories with the same name (e.g dir1, dir2), we need -# to number the new ones taking the existing ones into account (i.e dir3, dir4....). -makedirs() { - # Number of directories to create. - n=${2} - - # Get the last directory, if any, so that we know what the last number was. - lastdir=$(ls ${rootdir} | grep "${1}" | sed "s/${1}//g" | sort -V | tail -1) - - # If we didn't find any, we'll start numbering them from 1. - test -z ${lastdir} && lastdir=0 - - # If `n` was already 0 we won't do anything. - while ! [ $(expr ${n}) = 0 ]; do - # `lastdir` now holds the next number. - lastdir=$(expr ${lastdir} + 1) - - # Make a directory using the format described above - # and change the owner to `username`. - mkdir "${rootdir}/${1}${lastdir}" && - chown ${username}: "${rootdir}/${1}${lastdir}" - - # Decrement by 1 until we reach `n = 0` so that - # we can exit the loop. - n=$(expr ${n} - 1) - done -} - -# Pass all command line arguments to `main`. -main "$@" diff --git a/sh-os1/ex2/mfproc b/sh-os1/ex2/mfproc @@ -1,110 +0,0 @@ -#!/bin/sh - -# ΧΡΗΣΤΟΣ ΜΑΡΓΙΩΛΗΣ - [REDACTED] - -# Exit codes: -# 0 Success -# 1 No user -# 2 No process -# 3 Usage - -main() { - # Using getopts(1) because it's easier to parse - # optional command line options. getopts(1) works - # by passing it all the available options. If an option - # is followed by a ':', that means that getopts(1) is - # expecting an argument as well. If no argument is passed, - # it exits with an error code of 1. In this case I've - # passed it the string "u:s:" which means that the options - # are '-u' and '-s' and both of them take an argument. - # The argument is always stored in the `OPTARG` environmental - # variable. - while getopts u:s: arg; do - case "${arg}" in - # In order for `username` to really be a user's name, it - # has to exist in `/etc/passwd`. - u) test ! -z "$(grep -w "^${OPTARG}" /etc/passwd)" || - err "'${OPTARG}' is not in /etc/passwd" 1 - # Get UID from username. - uid=$(id -u ${OPTARG}) ;; - s) state="${OPTARG}" - # `state` needs to be either S, R or Z in order - # to be valid. - validstate ${state} || usage ;; - *) usage - esac - done - - count=0 - # Print header. expand(1) will will expand \t to 16 spaces - # in order for the output to be aligned. - printf "Name\tPID\tPPID\tUID\tGID\tState\n" | expand -t 16 - - # Parse each process in `/proc`. This is a slow way to parse it though. - for proc in /proc/*/status; do - procuid=$(getfield "Uid:\s*${uid}" ${proc}) - procgid=$(getfield "Gid" ${proc}) - # If the `-u` option was passed, ignore every UID that - # does not match the UID we gave it as an argument. - # We're using a `continue` command here so that it - # stop searching for anything else in this file since - # we don't need it. - test -z ${uid} || [ "${procuid}" == "${uid}" ] || continue - - procstate=$(getfield "State:\s*${state}" ${proc}) - - # Ignore any state other than S|R|Z - validstate ${procstate} || continue - - # If the `-s` option was passed, ignore every state that does - # not match the one we gave it as an argument. - test -z ${state} || [ "${procstate}" == "${state}" ] || continue - - procname=$(getfield "Name" ${proc}) - procpid=$(getfield "Pid" ${proc}) - procppid=$(getfield "PPid" ${proc}) - - # Print everything in a top(1)-like format. - printf "%s\t%s\t%s\t%s\t%s\t%s\n" \ - ${procname} ${procpid} ${procppid} ${procuid} ${procgid} ${procstate} | - expand -t 16 - - # Increment counter by 1 to keep track of how many processes - # we have printed. If `count` is 0 after the loop, the script - # will exit with error code 2, as is done below. - count=$(expr ${count} + 1) - done - - # We didn't print any process - test ${count} -eq 0 && exit 2 - - # Success! - exit 0 -} - -usage() { - # `{0##*/}` means the first argument (i.e the script's name) with - # its path stripped, if it exists. - echo "usage: ${0##*/} [-u username] [-s S|R|Z]" 1>&2 - exit 3 -} - -err() { - echo "${0##*/}: $@" 1>&2 - exit ${2} -} - -# Check if process is either S, R or Z. -validstate() { - [ "${1}" = "S" ] || [ "${1}" = "R" ] || [ "${1}" = "Z" ] -} - -# Get wanted field. grep(1) will return the line -# that begins with the first argument we passed. -# awk(1) is used to extract the 2nd field in the string. -getfield() { - grep -w "^${1}" ${2} | awk '{print $2}' -} - -# Pass all command line arguments to `main`. -main "$@" diff --git a/sh-os1/ex2/searching b/sh-os1/ex2/searching @@ -1,82 +0,0 @@ -#!/bin/sh - -# ΧΡΗΣΤΟΣ ΜΑΡΓΙΩΛΗΣ - [REDACTED] - -main() { - mode=${1} - days=${2} - # Command line arguments must be 2. - test $# -eq 2 || usage - # Check if `1` and `2` are numbers, otherwise exit. - isnumber ${mode} || err "'${mode}' is not a valid number" - isnumber ${days} || err "'${days}' is not a valid number" - # In order for `mode` to really be a valid mode, `0 <= x <= 7777` must - # satisfied, since permission modes can range from 0 to 7777. - test ${mode} -ge 0 && test ${mode} -le 7777 || err "'${mode}' is not a valid mode" - - # Pretty ugly loop. - sum1=0; sum2=0; sum3=0; sum4=0; sum5=0 - # Exit if `cont` is "n". - while [ ! "${cont}" = "n" ] ; do - read -erp "Directory name: " dir - - # Exit if nothing was typed. - test ! -z "${dir}" || err "please give a directory name" - # Check if `dir` really is a directory. - test -d "${dir}" || err "'${dir}' is not a directory" - - echo "Files with permissions ${mode}: " - find "${dir}" -perm ${mode} 2> /dev/null - sum1=$((${sum1}+$(find "${dir}" -perm ${mode} 2> /dev/null | wc -l))) - echo "" - - echo "Files modified within the last ${days} days: " - find "${dir}" -mtime -${days} 2> /dev/null - sum2=$((${sum2}+$(find "${dir}" -mtime -${days} 2> /dev/null | wc -l))) - echo "" - - echo "Subdirectories accessed within the last ${days} days: " - find "${dir}" -type d -atime -${days} 2> /dev/null - sum3=$((${sum3}+$(find "${dir}" -type d -atime -${days} 2> /dev/null | wc -l))) - echo "" - - echo "Files which all users have read access to: " - ls -l "${dir}" 2> /dev/null | grep "^-r..r..r.." - sum4=$((${sum4}+$(ls -l "${dir}" 2> /dev/null | grep "^-r..r..r.." | wc -l))) - echo "" - - echo "Subdirectories which others have write access to: " - ls -l "${dir}" 2> /dev/null | grep "^d.w..w..w." - sum5=$((${sum5}+$(ls -l "${dir}" 2> /dev/null | grep "^d.w..w..w." | wc -l))) - echo "" - - read -erp "Do you want to continue (y/n)? " cont - test "${cont}" = "n" && - - printf "Total entries found for:\n1. %s\n2. %s\n3. %s\n4. %s\n5. %s\n" \ - "${sum1}" "${sum2}" "${sum3}" "${sum4}" "${sum5}" - done - -} - -usage() { - # `{0##*/}` means the first argument (i.e the script's name) with - # its path stripped, if it exists. - echo "usage: ${0##*/} perms days" 1>&2 - exit 1 -} - -err() { - echo "${0##*/}: $@" 1>&2 - exit 1 -} - -isnumber() { - # If the argument does not begin *and* end in a number, then - # it's not a number. This also excludes negative numbers, but - # we shouldn't accept negative numbers anyway. - test ! -z "$(echo "${1}" | grep "^[0-9]\+$")" -} - -# Pass all command line arguments to `main`. -main "$@" diff --git a/sh-os1/ex2/teldb b/sh-os1/ex2/teldb @@ -1,114 +0,0 @@ -#!/bin/sh - -# ΧΡΗΣΤΟΣ ΜΑΡΓΙΩΛΗΣ - [REDACTED] - -# We'll use this later. -emptylnregex="^\ *$" - -main() { - # Parse command line options, exit if no option was passed. - case ${1} in - -a) newentry ;; - -l) list ;; - -s) sortcol ${2} ;; - -c) filter ${2} ;; - -d) deleteln ${2} ${3} ;; - -n) emptyln ;; - *) usage ;; - esac -} - -usage() { - # `{0##*/}` means the first argument (i.e the script's name) with - # its path stripped, if it exists. - # The {} around the options denote that only one option has to be - # passed to the script. - echo "usage: ${0##*/} {-a | -l | -n | -c keyword | -d keyword {-b | -r} | -s col}" 1>&2 - echo "" 1>&2 - echo "options:" 1>&2 - echo "-a add a new entry" 1>&2 - echo "-l list contents of file" 1>&2 - echo "-n count empty lines and ask if they should be deleted" 1>&2 - echo "-c filter keyword" 1>&2 - echo "-d delete lines containing a keyword followed by one of the options below" 1>&2 - echo " -b replaces line with an empty line" 1>&2 - echo " -r removes line completely" 1>&2 - echo "-s sort based on specified column (e.g ${0##*/} -s 3)" 1>&2 - - exit 1 -} - -# Exit with a `usage` message if the string that was passed is empty. -# This is used to make sure that we'll not write empty fields in `catalog`. -errempty() { - test ! -z "${1}" || usage -} - -# Skip empty lines -skipempty() { - grep -v "${emptylnregex}" -} - -# -a option - Make a new entry for `catalog`. -newentry() { - # Read fields and include an error check so that - # we don't pass an empty field. - read -erp "First name: " fname - errempty "${fname}" - - read -erp "Last name: " lname - errempty "${lname}" - - read -erp "Town: " town - errempty "${town}" - - read -erp "Phone number: " phone - errempty "${phone}" - - # Append all the things we've read to `catalog`. - printf "%s %s %s %s\n" "${fname}" "${lname}" "${town}" "${phone}" >> catalog -} - -# -l option - Print `catalog` with each line numbered. It also skips empty lines. -list() { - nl catalog | skipempty -} - -# -s option - Sort `catalog` by column. We pass the desired column in `main`. -sortcol() { - errempty "${1}" - sort -k "${1}" catalog | skipempty -} - -# -c option - Print only the lines that match a specific keyword. -filter() { - errempty "${1}" - grep "${1}" catalog -} - -# -d option - Delete a line. -deleteln() { - errempty "${1}" - errempty "${2}" - - # Parse sub-options. - case ${2} in - # Replace line with an empty line. - -b) sed -i "s/.*${1}.*//" catalog ;; - # Just delete the line. - -r) sed -i "/${1}/d" catalog ;; - esac -} - -# -n option - Count empty lines and delete them if the user answers with `y`. -emptyln() { - printf "Empty lines in 'catalog': " - grep "${emptylnregex}" catalog | wc -l - read -erp "Delete them (y/n)? " del - # Delete lines using `deleteln` with `-r` option so that it - # just deletes the line, without replacing it with an empty one. - test "${del}" = "y" && deleteln "${emptylnregex}" "-r" -} - -# Pass all command line arguments to `main`. -main "$@" diff --git a/sh-os1/ex3/ex1_cmds b/sh-os1/ex3/ex1_cmds @@ -1,39 +0,0 @@ -#!/bin/sh - -test $# -ne 1 && echo "usage: ${0##*/} gradefile" 1>&2 && exit 1 -test ! -f "${1}" && echo "${0##*/}: ${1}: no such file" 1>&2 && exit 1 - -file="${1}" - -echo "First names starting with K or N:" -awk '$1 ~ /^K|N/ {print $2, $1}' ${file} -echo "" - -echo "Last names starting with C or L:" -awk '$2 ~ /^C|L/ {print $1, $2}' ${file} -echo "" - -echo "Students with their second grade being > 85:" -awk '{if ($5 > 85 && $5 > 85) print}' ${file} -echo "" - -echo "Students in the humanities:" -awk '{if ($3 == "Theo") print}' ${file} -echo "" - -echo "Average ${file}:" -awk '{ -sum = cnt = 0; -for (i = 4; i <= NF; i++) { - sum += $i; - cnt++; -} -print $1, $2, sum / cnt}' ${file} -echo "" - -echo "Students with their third grade being < 70:" -awk 'BEGIN {cnt = 0} {if ($6 < 70) cnt++;} END {print cnt}' ${file} -echo "" - -echo "How many student names end in 'is'?" -awk 'BEGIN {cnt = 0} {if ($2 ~ /is$/) cnt++} END {print cnt}' ${file} diff --git a/sh-os1/ex3/ex2_studavgs.awk b/sh-os1/ex3/ex2_studavgs.awk @@ -1,20 +0,0 @@ -#!/usr/bin/env -S awk -f - -BEGIN { - # Quit if we don't have an input file. - if (ARGC < 2) { - print "usage: ex2_studavgs.awk gradefile"; - exit 1; - } -} - -{ - sum = cnt = 0; - for (i = 4; i <= NF; i++) { - sum += $i; - cnt++; - } - - # We're calling sort(1) from awk(1). - print "Student", NR",", $1, $2",", sum / cnt | "sort -Vrk5"; -} diff --git a/sh-os1/ex3/ex3_courseavgs.awk b/sh-os1/ex3/ex3_courseavgs.awk @@ -1,25 +0,0 @@ -#!/usr/bin/env -S awk -f - -BEGIN { - # Quit if we don't have an input file. - if (ARGC < 2) { - print "usage: ex3_courseavgs.awk gradefile"; - exit 1; - } -} - -{ - # Loop from the 4th field onwards and - # add its value to the sum array. - for (i = 4; i <= NF; i++) - sum[i] += $i; -} - -END { - # `NR` is the number of rows in the file, so - # we divide by that since each column is a - # course. - cnt = 1; - for (i = 4; i <= NF; i++) - print "Course", cnt++":", sum[i] / NR; -} diff --git a/sh-os1/ex3/ex4_rev.awk b/sh-os1/ex3/ex4_rev.awk @@ -1,20 +0,0 @@ -#!/usr/bin/env -S awk -f - -BEGIN { - # Quit if we don't have an input file. - if (ARGC < 2) { - print "usage: ex4_rev.awk file"; - exit 1; - } -} - -{ - # Add all lines to an array. - ln[NR] = $0; -} - -END { - # Print them in reverse. - for (i = NR; i >= 1; i--) - print ln[i]; -} diff --git a/sh-os1/ex3/ex5_filesize b/sh-os1/ex3/ex5_filesize @@ -1,3 +0,0 @@ -#!/bin/sh - -ls -l | grep '^-' | awk '{sum += $5} END{print sum}' diff --git a/sh-os1/ex3/ex6_votes.awk b/sh-os1/ex3/ex6_votes.awk @@ -1,29 +0,0 @@ -#!/usr/bin/env -S awk -f - -BEGIN { - # Quit if we don't have an input file. - if (ARGC != 2) { - print "usage: ex6_votes.awk votefile"; - exit 1; - } - - max = 0; -} - -{ - cnt = 0; - # We're testing only against 'y's, - # no need to check for 'n's. - for (i = 2; i <= NF; i++) - if ($i == "y") - cnt++; - if (cnt > max) { - max = cnt; - winner = $1; - } -} - -END { - print "Winner:", winner; - print "Votes:", max; -} diff --git a/sh-os1/ex3/ex7_countmatch b/sh-os1/ex3/ex7_countmatch @@ -1,20 +0,0 @@ -#!/bin/sh - -main() { - xread "String: " str - test -z "${str}" && echo "${0##*/}: give a non-empty string" 1>&2 && exit 1 - - xread "File: " file - test ! -f "${file}" && echo "${0##*/}: ${file}: no such file" 1>&2 && exit 1 - - awk "/${str}/ {cnt++} END {print cnt}" ${file} -} - -# A portable `read` function with behavior similar to -# `read -erp`. -xread() { - printf "%s" "${1}" && read -r ${2} -} - -# Pass all command line arguments to `main`. -main "$@" diff --git a/sh_os1/ex1/ex1.txt b/sh_os1/ex1/ex1.txt @@ -0,0 +1,750 @@ +# Eργαστήριο ΛΣ 1 / Άσκηση 1 / 2020-21 +# Ονοματεπώνυμο: Χρήστος Μαργιώλης +# ΑΜ: [REDACTED] +# ==================================== +# +# Ερώτηση 1: +# ---------- +# Δημιουργήστε στον τρέχοντα κατάλογο το αρχείο 'ask1.txt' με τα ακόλουθα +# περιεχόμενα(όνομα, επώνυμο, username, ΤΚ, περιοχή, τηλ.), και εμφανίστε +# το στησυνέχεια στην οθόνη, με αριθμημένες τις γραμμές του. +# +# Απάντηση: +# Προκειμένου να δημιουργήσουμε ένα αρχείο χρησιμοποιούμε την εντολή 'touch [FILE...]', +# όπου FILE είναι το όνομα του αρχείου και ... ότι μπορούμε να δώσουμε όσα ορίσματα +# θελουμε. Στην προκειμένη περίπτωση + +touch ask1.txt + +# Αν και θα μπορούσαμε να γράψουμε τα δεδομένα του αρχείο σε έναν +# κειμενογράφο, χρησιμοποιώντας την 'echo' (και οποιαδηποτε παρόμοια εντολή, +# όπως την 'printf'), μπορούμε να ανακατευθύνουμε την έξοδο της στο αρχείο που θέλουμε, +# οπότε μπορούμε με τις παρακάτω εντολές να έχουμε το ίδιο αποτέλεσμα. +# Για χάρην απλότητας στο διάβασμα επέλεξα να καλέσω αρκετές φορές την 'echo' αντί να +# ενώσω τα πάντα με newlines. Από την δεύτερη κλήση της και μετά το >> σημαίνει +# ότι θέλουμε να γράψουμε στο τέλος του αρχείο, όχι να γράψουμε το αρχείο από την αρχή. + +echo "George Pappas george2 12136 Peristeri-------" > ask1.txt +echo "Nick Nikolaoy nick23 12232 Aigaleo 5314555" >> ask1.txt +echo "George Georgioy george583 11132 Athens-------" >> ask1.txt +echo "Helen Georgioy helen3 12136 Peristeri 5748456" >> ask1.txt +echo "Nick Pappas nick4 11223 Aigaleo 5324123" >> ask1.txt +echo "Helen Ioannoy helen367 13222 Athens" ------- >> ask1.txt +echo "Helen Thanoy helen36 11132 Peristeri9718345" >> ask1.txt +echo "Vasilis Mamalis vas32 12345 Dafni 9738383" >> ask1.txt + +# Για να εμφανίσουμε τα περιεχόμενα του αρχείου με αριθμημένες σειρές, +# θα χρησιμοποιηθεί η εντολή 'nl', η οποία αριθμεί σειρές, δέχοντας ως +# input το αρχείο με τα περιεχόμενα. + +nl ask1.txt + +# Αποτέλεσμα εκτέλεσης εντολής: +# +# 1 George Pappas george2 12136 Peristeri------- +# 2 Nick Nikolaoy nick23 12232 Aigaleo 5314555 +# 3 George Georgioy george583 11132 Athens------- +# 4 Helen Georgioy helen3 12136 Peristeri 5748456 +# 5 Nick Pappas nick4 11223 Aigaleo 5324123 +# 6 Helen Ioannoy helen367 13222 Athens ------- +# 7 Helen Thanoy helen36 11132 Peristeri9718345 +# 8 Vasilis Mamalis vas32 12345 Dafni 9738383 +# +# Ερώτηση 2: +# ---------- +# Τρέξτε την εντολή cal -3 > calfile.txt και εξηγείστε τι ακριβώς κάνει. +# +# Απάντηση: +# Η εντολή 'cal' αρχικά εμφανίζει ημερολόγιο του τρέχοντος μήνα. Με την +# εντολή + +cal -3 > calfile.txt + +# Θα εμφανιστεί ο προηγούμενος, τρέχων και επόμενος μήνας, και στην συνέχεια +# το output της εντολής θα γραφτεί στο αρχείο calfile.txt +# +# Ερώτηση 3: +# ---------- +# Συνενώστε τα αρχεία calfile.txt και ask1.txt σε ένα αρχείο με όνομα full.txt +# +# Απάντηση: +# Για την συνένωση των δύο παραπάνω αρχείων - και γενικότερα δύο ή παραπάνω +# αρχειών - χρησιμοποιούμε την εντολή 'cat', οπότε + +cat calfile.txt ask1.txt > full.txt + +# Ερώτηση 4: +# ---------- +# Εμφανίστε στην οθόνη τα πέντε πιο πρόσφατα τροποποιημένα αρχεία του καταλόγου σας. +# +# Απάντηση: +# Για να εμφανίσουμε τα αρχεία του καταλόγου χρησιμοποιούμε την εντολή 'ls'. +# Προκειμένου να εμφανιστούν κατά ημερομηνία τροποποίησης ενεργοποιούμε την +# επιλογή -t. Έπειτα θα κάνουμε pipe το output του 'ls' στην εντολή 'head' για να +# εμφανίσουμε μόνο τα 5 πρώτα αρχεία. + +ls -t | head -6 + +# Ερώτηση 5: +# ---------- +# Δημιουργήστε έναν κατάλογο με όνομα 'mydir1'. Μεταβείτε σε αυτόν και στη +# συνέχεια αντιγράψτε εκεί (χωρίς να αλλάξετε κατάλογο) το αρχείο 'full.txt' +# (από το γονικό κατάλογο). Μετονομάστε το εν συνεχεία σε 'new.txt'. +# Επιστρέψτε στο γονικό κατάλογο. Διαγράψτε τον κατάλογο 'mydir1' και τα +# περιεχόμενά του. +# +# Απάντηση: +# Οι εντολές που θα χρειαστούμε είναι οι εξής: +# mkdir Δημιουργεί κατάλογο +# cd Αλλάζει κατάλογο +# cp Αντιγράφει αρχεία και καταλόγους +# rm -rf Διαγράφει αναδρομικά έναν κατάλογο (εφόσον υπάρχει το -rf) +# +# Στην πρώτη σειρά, το && σημαίνει ότι η επόμενη εντολή θα εκτελεστεί +# μόνο αν η προηγούμενη εντολή εκτελεστεί επιτυχώς. Στην δεύτερη σειρά +# το '.' δηλώνει τον κατάλογο που βρισκόμαστε - το '..' δηλώνει +# τον γονικό κατάλογο. + +mkdir mydir1 && cd mydir1 +cp ../full.txt . +cd .. +rm -rf mydir1 + +# Ερώτηση 6: +# ---------- +# Δώστε τις εντολές που θα εμφανίσουν: +# (α) όλα τα αρχεία του καταλόγου /usr με πληροφορίες για το inode τους και +# το μέγεθος τους σε blocks. +# (β) όλα τα περιεχόμενα του δέντρου καταλόγων και υποκαταλόγων (αναδρομικά) +# που βρίσκονται κάτω από τον κατάλογο /usr, με πλήρεις πληροφορίες για +# κάθε ένα από αυτά και εμφανιζόμενα σταδιακά, σελίδα προς σελίδα. +# +# Απάντηση: +# Και στα δύο υποερωτήματα θα χρησιμοποιηθεί η εντολή 'ls' +# (α) Η επιλογή -i εμφανίζει το inode και η επιλογή +# -s το μέγεθος σε blocks, οπότε + +ls -lsi /usr + +# (β) Η επιλογή -R εμφανίζει αναδρομικά όλα τα περιεχόμενα ενός +# καταλόγου, οπότε + +ls -lR /usr + +# Ερώτηση 7: +# ---------- +# Δημιουργήστε έναν κατάλογο με όνομα 'testdir1'. Μεταβείτε σε αυτόν +# και φτιάξτε εκεί ένα hard link (με το όνομα 'ask1link') προς το αρχείο +# 'ask1.txt' του γονικού καταλόγου. Βεβαιωθείτε (δίνοντας την κατάλληλη +# εντολή και εξηγώντας τι βλέπετε) ότι έχει δημιουργηθεί και ότι δεν είναι +# symbolic (soft) link. +# +# Απάντηση: +# Για να φτιάξουμε hard link θα χρησιμοποιήσουμε την εντολή 'ln'. + +mkdir testdir1 && cd testdir1 +ln ../ask1.txt ask1link + +# Αν εκτελέσουμε την εντολή 'ls -li' στον κατάλογο testdir1 θα δούμε +# ότι σε αντίθεση με το soft link, στο hard link δεν εμφανίζεται +# το -> το οποίο δηλώνει ότι είναι symbolic link. +# +# 11403520 -rw-r--r-- 2 christos wheel 350 Nov 11 12:28 ask1link +# +# Επίσης παρατηρούμε ότι και το ask1link αλλά και το ask1.txt έχουν το ίδιο inode. +# +# 11403520 -rw-r--r-- 2 christos wheel 350 Nov 11 12:28 ask1.txt +# 11403520 -rw-r--r-- 2 christos wheel 350 Nov 11 12:28 ask1link +# +# Ερώτηση 8: +# ---------- +# Μπείτε στο αρχείο 'ask1link' και διαγράψτε την τελευταία του γραμμή. +# Βεβαιωθείτε στη συνέχεια ότι η αλλαγή αυτή έχει γίνει και στο αρχείο 'ask1.txt'. +# +# Απάντηση: +# Εφόσον το ask1link ειναι hardlink στο 'ask1.txt', δηλαδή είναι reference +# στο 'ask1.txt', ό,τι αλλαγή γίνει στο ένα αρχείο, θα γίνει και στο άλλο, +# οπότε αν διαγράψουμε την τελευταία γραμμή από το 'ask1link', η αλλαγή +# πράγματι θα έχει γίνει και στο 'ask1.txt'. Ανοίγουμε το 'ask1link' στο +# Vim και εκτελούμε τις εξής εντολές ώστε να σβήσουμε την τελευταία γραμμή + +# vim ask1link + +# G πάει στην τελευταία γραμμή +# dd την σβήνει +# ZZ βγαίνουμε από το Vim +# +# Τώρα κάνοντας + +cd .. +diff ask1.txt testdir1/ask1link + +# βλέπουμε ότι εντολή δεν βγάζει output, το οποίο σημαίνει ότι τα αρχεία +# είναι ίδια, οπότε η αλλαγή που κάναμε στο ένα αρχείο ίσχυσε και στο άλλο. +# +# Ερώτηση 9: +# ---------- +# Δημιουργήστε ένα κατάλογο kat1 και μέσα σε αυτόν δύο αρχεία, file1 και file2, +# με περιεχόμενο τη λέξη 'one' το ένα και τη λέξη 'two' το άλλο. +# Τρέξτε (μέσα στον κατάλογο kat1) την εντολή 'cp *' και εξηγήστε το αποτέλεσμα. +# Στη συνέχεια τρέξτε την εντολή 'mv *' και εξηγήστε το αποτέλεσμα. +# +# Απάντηση: +# Αρχικά πρέπει να γράψουμε τα περιέχομενα στα κατάλληλα αρχεία. + +mkdir kat1 && cd kat1 +echo "one" > file1 +echo "two" > file2 + +# Αφού τρέξουμε την εντολή 'cp *' στον kat1 θα παρατηρήσουμε ότι και τα +# δύο αρχεία τώρα έχουν την λέξη "one". + +cp * +cat file1 file2 + +# one +# one +# +# Αυτό γίνεται επειδή γράφοντας 'cp *', επιλέγουμε όλα τα αρχεία του +# καταλόγου. Επειδή όμως έχουμε δύο αρχεία η εντολή θα αναπτυχθεί σε +# +# cp file1 file2 +# +# και αυτό που θα γίνει τελικά είναι να αντιγραφεί το file1 στο file2. +# Όταν τρέξουμε την εντολή 'mv *' θα δούμε ότι διαγράφεται το file1, +# επειδή, όπως και με την 'cp *', η εντολή θα αναπτυχθεί σε + +mv file1 file2 +ls +cd .. + +# οπότε το file1 θα μετονομαστεί σε file2, και έτσι θα χαθεί. +# +# Ερώτηση 10: +# ----------- +# Εμφανίστε τις γραμμές του αρχείου 'ask1.txt' οι οποίες τελειώνουν +# με ένα ή περισσότερα συνεχόμενα ψηφία. +# +# Απάντηση: +# Η εντολή 'grep' δέχεται ένα regular expression (regex) και επιστρέφει +# τις γραμμές στο αρχείο στις οποίες βρίσκεται το regex. +# Το regex που θα ψάξουμε θα αποτελείται από τα εξής μέρη: +# +# 1. [0-9] οποιδήποτε ψηφίο από το 0 εώς το 9 +# 2. \+ μία ή παραπάνω επαναλήψεις του προηγούμενου +# 3. $ τέλος γραμμής +# +# Οπότε η τελική εντολή θα είναι + +grep "[0-9]\+$" ask1.txt + +# Ερώτηση 11: +# ----------- +# Εμφανίστε τις γραμμές του αρχείου 'ask1.txt' οι οποίες περιέχουν μεν +# το πρότυπο 'Pap' αλλά δεν περιέχουν το πρότυπο 'Aig'. +# +# Απάντηση: +# Στην εντολή 'grep' η επιλογή -v αποκλείει το δοθέν regex. Προκειμένου +# πρώτα να πάρουμε τις γραμμές που περιέχουν το πρότυπο 'Pap' αλλα όχι +# το πρότυπο 'Aig', θα εκτελέσουμε το 'grep' 2 φορές, ώστε πρώτα να πάρουμε +# όλες τις γραμμές που περιέχουν το 'Pap' και μετά να αποκλείσουμε το 'Aig'. + +grep "Pap" ask1.txt | grep -v "Aig" + +# Ερώτηση 12: +# ----------- +# Εμφανίστε τις γραμμές του αρχείου 'ask1.txt' οι οποίες δεν αρχίζουν +# με 'G' ή 'N' και περιέχουν εν συνεχεία (κάπου στα περιεχόμενά τους) +# τα πρότυπα 'Geo' και 'Per' με αυτή τη σειρά.' +# +# Aπάντηση: +# Όπως και στην ερώτηση 11, θα μπορούσαμε να χρησιμοποιήσουμε την επιλογή +# -v για την εντολή 'grep', αλλα θα χρησιμοποιήσουμε μία διαφορετική σύνταξη. +# Αυτή τη φορά τα regex που θα ψάξουμε είναι τα εξής +# +# Για την πρώτη κλήση: +# 1. ^ ξεκινάει με +# 2. ^[GN] πρεπει να ξεκινάει με G ή N +# 3. ^[^GN] ΔΕΝ πρέπει να ξεκινάει με G ή N +# +# Για την δεύτερη κλήση: +# 1. Geo περιέχει την λέξη 'Geo' +# 2. .* οποιοσδήποτε αριθμός οποιουδήποτε χαρακτήρα +# 3. Per περιέχει την λέξη 'Per' +# +# Οπότε η τελική εντολή είναι (το | ειναι separator) + +grep "^[^GN]" ask1.txt | grep "Geo.*Per" + +# Αποτέλεσμα εκτέλεσης εντολής: +# +# Helen Georgioy helen3 12136 Peristeri 5748456 +# +# Ερώτηση 13: +# ----------- +# Πόσοι χρήστες που το username τους δεν αρχίζει από 'ls1' είναι +# συνδεδεμένοι στο σύστημα; +# +# Απάντηση: +# Η εντολή 'who' μπορεί να μας επιστρέψει μια λίστα με τους χρήστες +# που είναι συνδεδεμένοι. Ο λόγος που χρησιμοποίησα την 'who' αντί +# για την 'w' που κάνει περίπου το ίδιο πράγμα είναι επειδή η 'w' +# έχει και μια γραμμή header στην αρχή, οπότε 'wc -l' θα την μέτραγε. +# Με την χρήση της εντολής 'wc' μπορούμε να μετρήσουμε λέξεις, γραμμές +# και χαρακτήρες. Αν στην εντολή 'wc' δώσουμε την επιλογή -l τότε θα +# μετρήσει μόνο πόσες γραμμές έχει το input που της δώθηκε. + +who | grep -v "^ls1" | wc -l + +# Ερώτηση 14: +# ----------- +# Εμφανίστε όλες τις διεργασίες χρηστών (αλλ/σης) που τρέχουν αυτή +# τη στιγμή στο σύστημα. +# +# Απάντηση: +# Η εντολή 'ps' (process status) εμφανίζει τις τρέχουσες διεργασίες που +# εκτελεί το σύστημα. Επιπλέον θα χρειαστούμε τις επιλογές a και u, οι οποίες +# εμφανίζουν τις διεργασίες που εκτελούνται από όλους τους συνδεδεμένους χρήστες +# αυτή τη στιγμη. Στην εντολή 'ps' χρησιμοποιήσα την BSD σύνταξη. + +ps -au + +# Αποτέλεσμα εκτέλεσης της εντολής: +# +# USER PID %CPU %MEM VSZ RSS TT STAT STARTED TIME COMMAND +# christos 5200 0.1 0.1 18048 7084 2 Ss 21:44 0:09.04 /usr/local/bin/zsh +# christos 1160 0.0 0.1 15072 6016 v0 I 12:19 0:00.07 -zsh (zsh) +# christos 1175 0.0 0.0 11828 3044 v0 I+ 12:19 0:00.00 /bin/sh /usr/local/bin/startx +# christos 1188 0.0 0.0 13164 3240 v0 I+ 12:19 0:00.00 xinit /home/christos/.xinitrc +# christos 1192 0.0 0.1 22152 11360 v0 S 12:19 0:19.69 dwm +# christos 1218 0.0 0.1 17136 8000 0- S 12:20 0:16.20 slstatus +# christos 5005 0.0 0.1 18004 7000 1 Is 21:15 0:00.31 /usr/local/bin/zsh +# christos 5193 0.0 0.2 28028 16288 1 S+ 21:44 0:07.88 nvim ex1.txt +# christos 6849 0.0 0.0 11860 3080 2 R+ 00:22 0:00.00 ps -u +# root 1158 0.0 0.0 10880 2304 v1 Is+ 13:14 0:00.00 /usr/libexec/getty Pc ttyv1 +# root 1159 0.0 0.0 10880 2304 v2 Is+ 13:14 0:00.00 /usr/libexec/getty Pc ttyv2 +# root 1160 0.0 0.0 10880 2304 v3 Is+ 13:14 0:00.00 /usr/libexec/getty Pc ttyv3 +# +# Ερώτηση 15: +# ----------- +# Πόσες διεργασίες χρηστών (αλλ/σης) τρέχουν στο σύστημα και τελειώνει +# το όνομά τους με 'sh' ? +# +# Απάντηση: +# Τρέχοντας την εντολή της ερώτησης 14 (ps -ux) και φιλτράροντας +# το ouput ώστε να πάρουμε μόνο τις γραμμές που τελειώνουν σε +# 'sh', έχω 3 διεργασίες που το όνομα τους τελειώνει σε 'sh' + +ps -au | grep "sh$" | wc -l + +# Συνολικά έχουμε 3 διεργασίες που τελειώνουν σε sh. +# +# Ερώτηση 16: +# ----------- +# Εμφανίστε όλες τις διεργασίες χρηστών (αλλ/σης) που τρέχουν αυτή τη στιγμή στο σύστημα. +# +# Απάντηση: +# Αυτή τη φορά στην εντολή 'ps', πέρα από την επιλογή u, θα δώσουμε και την επιλογή +# x, η οποία εμφναίζει πληροφορίες ακόμα και για διεργασίες που δεν ελέγχουν κάποιο terminal + +ps -aux + +# Το output της εντολής είναι πολύ μεγάλο για να το συμπεριλάβω εδώ. +# +# Ερώτηση 17: +# ----------- +# Πόσα αρχεία του τρέχοντος καταλόγου σας (μόνο του τρέχοντος -όχι και +# των υποκαταλόγων του) έχουν permissions 'rw' από τους πάντες και 'x' +# από κανέναν; +# +# Απάντηση: +# Η 'ls -l' στην αρχή κάθε σειράς εμφανίζει το permission string και με την +# 'grep' μπορούμε να εμφανίσουμε μόνο τις γραμμές που περιέχουν το permission +# που ζητάει η εκφώνηση. Τέλος διοχετεύουμε την έξοδο στην 'wc -l'. + +ls -l | grep "^-rw-rw-rw-" | wc -l + +# Ερώτηση 18: +# ----------- +# Βρείτε τους καταλόγους του συστήματος που το όνομά τους αρχίζει από 'b'. +# +# Απάντηση: +# Η εντολή 'find' είναι μια πιο ανεπτυγμένη μορφή της 'ls' στην οποία μπορούμε +# να δώσουμε πολλές παραπάνω επιλογές. Οι επιλογές που έχουν δωθεί στην παρακάτω εντολή +# σημαίνουν τα εξής: +# /* - η αναζήτηση ξεκινάει από την ρίζα του συστήματος (root directory) +# -type d - αναζήτηση μόνο για directories +# -name "b*" - το όνομα τους πρέπει να ξεκινάει από 'b' + +find /* -type d -name "b*" + +# Ερώτηση 19: +# ----------- +# Να βρείτε και να παρουσιάσετε στην οθόνη με πλήρεις πληροφορίες +# όλα τα αρχεία με όνομα που αρχίζει από tty και βρίσκονται στον κατάλογο /dev. +# +# Απάντηση: +# Η εντολή stat επιστρέφει πλήρεις πληροφορίες για ένα αρχείο. +# Με την εντολή 'grep', όπως έχει ειπωθεί και σε παραπάνω ερωτήσεις, μπορούμε +# να πάρουμε τις γραμμές στις οποίες γίνεται match ένα regular +# expression - έτσι κατά την εμφάνιση των αρχείων του /dev μπορούμε +# να εξάγουμε μόνο όσες γραμμές περιέχουν την λέξη 'tty'. + +stat /dev/* | grep "tty" + +# Ερώτηση 20: +# ----------- +# Ταξινομήστε τα περιεχόμενα του αρχείου 'ask1.txt' ως προς το +# username σε φθίνουσα σειρά. +# +# Απάντηση: +# Θα ταξινομίσουμε το αρχείο με την χρήση της εντολής 'sort'. +# Στην εντολή αυτή μπορούμε να της δώσουμε κατα ποιά στήλη θέλουμε +# να ταξινομηθεί το αρχείο με την επιλογή -k. Εφόσον username +# βρίσκεται στην 3η στήλη, θα δώσουμε την 3η στήλη ως μέσο +# σύγκρισης για ταξινόμηση. Επίσης, προκειμένου να είναι κατα +# φθήνουσα σειρά η ταξινόμηση, θα χρησιμοποιήσουμε την επιλογή -r + +sort -rk 3 ask1.txt + +# Σε περίπτωση που θέλουμε οι αλλαγές να γραφτούν στο αρχείο, μπορούμε +# να γράψουμε την εντολή ως +# +# sort -rk 3 ask1.txt -o ask1.txt +# +# Ερώτηση 21: +# ----------- +# Ταξινομήστε τα '.c' αρχεία του καταλόγου στον οποίον δουλεύετε ως +# προς το μέγεθός τους. +# +# Απάντηση: +# Στην εντολή 'ls' η επιλογή -S ταξινομεί τα αρχεία ανάλογα με το +# μέγεθός του κατα φθήνουσα σειρά (μεγαλύτερο πρώτα), οπότε + +ls -S *.c + +# Ερώτηση 22: +# ----------- +# Ταξινομήστε τα αρχεία του λογαριασμού σας με permissions 644 +# ως προς το μέγεθός τους. +# +# Απάντηση: +# Μπορούμε να εμφανίσουμε αρχεία που έχουν συγκεκριμένα permissions +# με την εντολή 'find' και την επιλογή -perm [PERMISSION] όπου +# το PERMISSION πρέπει να δωθεί σε οκταδικό. Επίσης μέσα στην 'find' +# μπορούμε να εκτελέσουμε και επιπλέον shell commands στο output της με +# την επιλογή -exec [COMMAND] - θα χρησιμοποιήσουμε την 'ls -alS' ώστε +# να ταξινομήσει το output κατα μέγεθος. Η τελική εντολή θα εκτελεστεί +# στον κατάλογο '/usr/home/christos', ο οποίος είναι ο κατάλογος του λογαριασμού +# μου. Το {} \; στο τέλος της εντολής δηλώνει ότι η 'ls -alS' θα εκτελεστεί +# σε κάθε αρχείο που βρίσκεται από την 'find'. + +find /home/christos -perm 644 -exec ls -alS {} \; + +# Ερώτηση 23: +# ----------- +# Ταξινομήστε όλα τα περιεχόμενα του καταλόγου /dev κατά πρώτον ως προς +# τον owner και κατά δεύτερον ως προς το group και αποθηκεύστε το +# output στο αρχείο 'binfiles.txt'. +# +# Аπάντηση: +# Παίρνοντας πληροφορίες για τον owner και το group των αρχείων με την +# 'ls -l /dev' μπορούμε να ταξινομήσουμε τις κατάλληλες στήλες (3 για owner +# και 4 για group). + +ls -l /dev | sort -k 3,4 > binfiles.txt + +# Ερώτηση 24: +# ----------- +# Φτιάξτε ένα αρχείο που θα περιέχει πληροφορίες μόνο για τους συνδεδεμένους +# χρήστες που το username τους αρχίζει από 'ls1', ταξινομημένο ως προς +# την ημερομηνία και ώρα σύνδεσή τους. +# +# Απάντηση: +# ΑΦού φιλτραριστεί το ouput της 'who' ώστε να πάρουμε μόνο τους +# χρήστες που το όνομά τους ξεκινάει από ls1, θα ταξινομήσουμε +# κατά 3η και 4η στήλη επειδή αυτές δείχνουν την ημερομηνία +# και ώρα σύνδεσης. + +who | grep "^ls1" | sort -k 3,4 > userinfo.txt + +# Ερώτηση 25: +# ----------- +# Αλλάξτε στο αρχείο 'ask1.txt' το όνομα 'Nick' (όπου συναντάται) σε 'Nickolaos'. +# +# Απάντηση: +# Με την χρήση της εντολής 'sed' (stream editor) μπορούμε να αλλάξουμε ένα +# pattern κάθε φορά που συναντάται με την παρακάτω σύνταξη +# +# sed "s/PATTERN/NEWPATTERN/g" file +# +# Τo g στο τέλος σημαίνει ότι αυτή η αλλαγή πρέπει να γίνει σε όλο το αρχείο, +# και όχι μόνο την πρώτη φορά που θα συναντήσει το PATTERN. +# Οπότε, στην προκειμένη περίπτωση η εντολή που θα εκτελεστεί είναι + +sed "s/Nick/Nickolaos/g" ask1.txt + +# Εάν θέλουμε οι αλλαγές να αποθηκευτούν στο αρχείο κατευθείαν, μπορούμε +# να εκτελέσουμε την εντολή με την επιλογή -i. + +sed -i "s/Nick/Nickolaos/g" ask1.txt + +# Ερώτηση 26: +# ----------- +# Έστω τα ακόλουθα items του filesystem με protection strings: +# (α) '-rwxr-x--x', +# (β) 'drwxr-x---' και +# (γ) 'drwx--x--x. +# Εξηγείστε τι είδους items είναι και ποια τα δικαιώματα πρόσβασης user, +# group και others σε αυτά. +# +# Απάντηση: +# (α) Το είδος item είναι απλό αρχείο εφόσον το πρώτο πεδίο του protection string +# είναι κενό. Όσο αφορά τα δικαίωματα του, δικαίωμα εγγραφής έχει μόνο ο ιδιοκτήτης +# του αρχείο, διαβάσματος ο ιδιοκτήτης του αρχείου, και όσοι είναι στο ίδιο group με αυτόν. +# Επίσης όλοι οι χρήστες μπορούνε να το εκτελέσουν. +# +# (β) Το είδος είναι directory λόγω του 'd' στο πρώτο πεδίο του string. Δικαίωμα εγγραφής +# έχει μόνο ο ιδιοκτήτης, διαβάσματος και εκτέλεσης ο ιδιοκτήτης και τα μέλη του group - +# οι υπόλοιποι χρήστες δεν έχουν δικαιώματα για το συγκεκριμένο directory. +# +# (γ) Το είδος είναι επίσης directory λόγω του 'd' στο πρώτο πεδίο του string. Δικαίωμα +# εγγραφής και διαβάσματος έχει μόνο ο ιδιοκτήτης και εκτέλεσης όλοι οι χρήστες. +# +# Ερώτηση 27: +# ----------- +# Αλλάξτε τα permissions όλων των αρχείων του καταλόγου 'testdir1' +# έτσι ώστε να έχουν δικαίωμα εκτέλεσης και εγγραφής μόνο ο ιδιοκτήτης, +# ενώ δικαίωμα ανάγνωσης να έχουν όλοι. +# +# Απάντηση: +# Η εντολή 'chmod' μπορεί να αλλάξει permissions. Με την επιλογή 'R' δηλώνουμε +# ότι αυτό θέλουμε να γίνει αναδρομικά εφόσον θέλουμε να αλλάξουμε τα permissions +# όλων των αρχείων του καταλόγου 'testdir1'. Τα υπόλοιπα πεδία σημαίνουν τα εξής: +# a=r - όλοι οι χρήστες έχουν δικαίωμα ανάγνωσης +# u+wx - προσθέτουμε στον ιδιοκτήτη του αρχείου και τα δικαιώματα εγγραφής και εκτέλεσης + +sudo chmod -R a=r,u+wx testdir1 + +# Ερώτηση 28: +# ----------- +# Αλλάξτε τα permissions του καταλόγου 'testdir1' έτσι ώστε να έχουν δικαίωμα +# πρόσβασης μόνο ο ιδιοκτήτης και οι χρήστες του ιδίου με αυτόν group, +# ενώ οι υπόλοιποι χρήστες να μην έχουν (θεωρείστε ότι τα τρέχοντα +# permissions του καταλόγου είναι 755). +# +# Απάντηση: +# Χρησιμοποιώντας πάλι την εντολή 'chmod' μπορούμε να αλλάξουμε και τα permissions +# ενός καταλόγου. Τα πεδία τώρα σημαίνουν τα εξής: +# ug+r - ο ιδιοκτήτης και τα μέλη του group έχουν δικαίωμα διαβάσματος +# o-r - οι υπόλοιποι χρήστες δεν έχουν δικαίωμα διαβάσματος + +sudo chmod ug+r,o-r testdir1 + +# Ερώτηση 29: +# ----------- +# Δημιουργήστε έναν νέο χρήστη στο σύστημά σας με username 'myfriend'. +# Αλλάξτε στη συνέχεια τον ιδιοκτήτη του αρχείου 'ask1.txt' σε 'myfriend' και +# μετακινήστε το στο working directory του. Περιορίστε τέλος το διαθέσιμο +# χώρο αποθήκευσης στο δίσκο για το συγκεκριμένο χρήστη στα 10MB. +# +# Απάντηση: +# Για να φτιάξουμε έναν user χρησιμοποιούμε την εντολή 'useradd'. Σε BSD +# συστήματα η εντολή είναι η 'adduser'. Για να αλλάξουμε ιδιοκτήτη αρχείου +# χρησιμοποιούμε την εντολή 'chown'. Τέλος, για να περιορίσουμε τον χώρο +# αποθηκεύσης στον δίσκο για έναν χρήστη χρησιμοποιούμε την εντολή 'edquota'. + +useradd -m -d /home/myfriend myfriend +chown myfriend ask1.txt +mv ask1.txt /home/myfriend +edquota myfriend + +# Η εντολή 'edquota' θα μάς ανοίξει στον default editor μας ένα αρχείο +# στο οποίο μπορούμε να τροποποιήσουμε τον αποθηκευτικό χώρο για τον χρήστη +# myfriend. Θα πρέπει να δούμε κάτι σαν +# +# Disk quotas for user ice19390133 (uid 1022): +# Filesystem blocks soft hard inodes soft hard +# /dev/vda1 36 10240 13312 11 0 0 +# +# Το 'soft' το θέτουμε σε 10240 (kilobyte), δηλαδή 10MB. +# +# Ερώτηση 30: +# ----------- +# Έστω τα παρακάτω: +# user1@localhost:~$ w +# USER TTY FROM LOGIN@ IDLE JCPU PCPU WHAT +# user1 pts/0 1.2.3.4 03:34 0.00s 0.38s 0.01s w +# user2 pts/1 5.6.7.8 03:45 0.00s 0.38s 0.01s ls +# user3 pts/2 9.7.5.3 03:57 0.00s 0.38s 0.01s ps +# +# user1@localhost:~$ ls -al /dev/pts/* +# crw--w---- 1 user1 tty136, 0 Oct 25 04:04 /dev/pts/0 +# crw--w--w- 1 user2 tty136, 1 Oct 25 04:04 /dev/pts/1 +# crw--w--w- 1 user3 tty136, 2 Oct 25 04:04 /dev/pts/2 +# +# Εξηγήστε τι είδους items του file system είναι τα παραπάνω, +# καθώς και τι θα κάνουν οι παρακάτω εντολές: +# user1@localhost:~$ cat > /dev/pts/1 +# user1@localhost:~$ wall "test" +# +# Απάντηση: +# Σε ένα permission string, το 'c' δηλώνει ότι αυτό το item +# ειναι 'character device', το οποίο πρακτικά σημαίνει συσκευές +# οι οποίες μεταφέρουν δεδομένα σε μορφή κειμένου (bytes). Τέτοιες +# συσκευές είναι για παράδειγμα τα ηχεία. Στην προκειμένη περίπτωση +# το item ειναι 'tty' (από το teletype), δηλαδή είναι terminals. Τα +# συγκεκριμένα terminals ειναι συνδεδεμένα με το πληκτρολόγιο. +# +# Η εντολή 'cat > /dev/pts/1' θα εμφανίζει στο πρώτο terminal που +# ανοίχτηκε οτίδηποτε γράψουμε στο stdin. Στον κατάλογο /dev/pts/ +# εμφανίζονται τα ανοιχτά terminals που τρέχουν αυτή τη στιγμή. + +cat > /dev/pts/1 + +# hello world +# hello world +# +# Η εντολή 'wall "test"' θα στείλει το μήνυμα "test" σε όλους τους +# συνδεδεμένους χρήστες. + +wall "test" + +# Broadcast message from christos@freebsd (pts/1) (Wed Nov 14 23:26:58 2020): +# +# test +# +# +# Ερώτηση 31: +# ----------- +# Δημιουργείστε τα αρχεία f1, f2, f3, f4, f5, f6 ,f7 με τα εξής δικαιώματα: +# f1, 757 +# f2, 313 +# f3, 010 +# f4, 642 +# f5, 551 +# f6, 133 +# f7, 111 +# Με χρήση της εντολής ls –l και διοχετεύοντας τα αποτελέσματά της στην εντολή +# egrep να βρείτε τα αρχεία όπου: +# a. To group έχει δικαιώματα r-x. +# b. Ο user και οι others έχουν ακριβώς τα ίδια δικαιώματα +# c. Ο user, το group και οι others έχουν τα ίδια δικαιώματα για write +# d. Ο user, το group και οι others έχουν τα ίδια δικαιώματα για write και execute +# e. To group και οι others έχουν τα ίδια δικαιώματα για read και execute +# +# Απάντηση: +# Αρχικά θα δημιουργήσουμε τα αρχεία με τα κατάλληλα permissions + +touch f1 && chmod 757 f1 +touch f2 && chmod 313 f2 +touch f3 && chmod 010 f3 +touch f4 && chmod 642 f4 +touch f5 && chmod 551 f5 +touch f6 && chmod 133 f6 +touch f7 && chmod 111 f7 + +# a) Το pattern που θα αναζητήσουμε είναι στο permission string να περιέχονται +# οποιοιδήποτε χαρακτήρες σε όλα τα πεδία αλλά πρέπει οπωσδήποτε τα permissions +# του group να είναι r-x. Το - στην αρχή το βάζουμε για να ψάξουμε μόνο αρχεία και όχι +# τυχόν directories. + +ls -l | egrep "^-...r-x..." + +# Αποτέλεσμα εκτέλεσης της εντολής: +# +# -rwxr-xrwx 1 christos christos 0 Nov 14 22:16 f1 +# -r-xr-x--x 1 christos christos 0 Nov 14 22:16 f5 +# +# b) Θα φτιάξουμε ένα capture group στα πεδια που βρισκονται τα permissions +# του user ώστε να ψάξουμε ό,τι αποθηκεύτηκε στην μεταβλητή 1 +# στο πεδίο που βρίσκονται τα permissions των others. Ένα capture group φτιάχνουμε +# βάζοντας () και γράφοντας μέσα το pattern που θέλουμε. + +ls -l | egrep "^-(...)...\1" + +# Πιο αναλυτικά συμβαίνει το εξής: +# 1. Θέλουμε το pattern να ξεκινάει με - ώστε να είναι αρχείο. +# 2. Αποθηκεύουμε τους 3 επόμενους χαρακτήρες στη μεταβλητή 1. +# 3. Έχουμε φτάσει στο πεδίο του group, οπότε ψάχνουμε για οποιονδήποτε +# χαρακτήρα επειδή δεν μας νοιάζει σε αυτό το παράδειγμα τι permissions έχει το group. +# 4. Тώρα είμαστε στο πεδίο των others. Εμφανίζουμε τη μεταβλητή 1 η οποία έχει κρατήσει +# τα permissions του user. +# +# Αποτέλεσμα εκτέλεσης της εντολής: +# +# -rwxr-xrwx 1 christos christos 0 Nov 14 22:16 f1 +# --wx--x-wx 1 christos christos 0 Nov 14 22:16 f2 +# ------x--- 1 christos christos 0 Nov 14 22:16 f3 +# ---x--x--x 1 christos christos 0 Nov 14 22:16 f7 +# +# c) Με την ίδια λογική όπως στο ερώτημα b, απλώς αυτή τη φορά δεν θα κρατήσουμε όλα τα +# permissions του user, αλλά μόνο τα permissions για write. + +ls -l | egrep "^-.(.)..\1..\1." + +# Αποτέλεσμα εκτέλεσης της εντολής: +# +# ------x--- 1 christos christos 0 Nov 14 22:16 f3 +# -r-xr-x--x 1 christos christos 0 Nov 14 22:16 f5 +# ---x--x--x 1 christos christos 0 Nov 14 22:16 f7 +# +# d) Ξανά με την ίδια λογική, αλλά κρατήσουμε τα πεδία για write και execute. + +ls -l | egrep "^-.(..).\1.\1" + +# Αποτέλεσμα εκτέλεσης της εντολής: +# +# -r-xr-x--x 1 christos christos 0 Nov 14 22:16 f5 +# ---x--x--x 1 christos christos 0 Nov 14 22:16 f7 +# +# e) Αυτή τη φορά θα κρατήσουμε στις μεταβλητές τα permissions από το group, και όχι +# από τον user. + +ls -l | egrep "^-...(.).(.)\1.\2" + +# Αποτέλεσμα εκτέλεσης της εντολής: +# +# -rwxr-xrwx 1 christos christos 0 Nov 14 22:16 f1 +# --wx--x-wx 1 christos christos 0 Nov 14 22:16 f2 +# ---x-wx-wx 1 christos christos 0 Nov 14 22:16 f6 +# ---x--x--x 1 christos christos 0 Nov 14 22:16 f7 +# +# Ερώτηση 32: +# ----------- +# Υποθέστε πως οι γραμμές στο αρχείο /etc/passwd είναι όμοιες με την παρακάτω: +# +# spouneri:x:2107:1067:Pouneridis Sokratis:/home/student/e2021/spouneri:/bin/bash +# +# Στο πέμπτο πεδίο θα υπάρχει πάντα πρώτο το επίθετο και μετά το όνομα του χρήστη. +# Μόνο ένα επίθετο και μόνο ένα όνομα, γραμμένα με λατινικούς χαρακτήρες κεφαλαίους +# ή/και πεζούς. +# +# Τα υπόλοιπα πεδία θα είναι γραμμένα πάντα με πεζούς λατινικούς +# χαρακτήρες. +# +# Ελέγχοντας το αρχείο /etc/passwd και κάνοντας χρήση της εντολής egrep +# βρείτε όλους τους (υποθετικούς) χρήστες του συστήματος όπου: +# +# a. Χρησιμοποιούν για κέλυφος το bash +# b. To HOME DIRECTORY τους βρίσκεται στον κατάλογο /home +# c. To UID τους είναι ίδιο μετο GID τους +# d. Τουλάχιστον τα 5 πρώτα γράμματα του επιθέτου τους αποτελούν μέρος και του username τους +# e. Τουλάχιστον τα 3 πρώτα γράμματα του επιθέτου τους και τα 3 πρώτα γράμματα του +# ονόματός τους αποτελούν μέρος και του username τους. +# +# Απάντηση: +# +# a. Εφόσον το shell βρίσκεται πάντα στο τέλος της γραμμής, μπορούμε να κάνουμε + +egrep "/bin/bash$" /etc/passwd + +# b. Αφού φτάσουμε στο πεδίο όπου βρίσκεται το Home directory, θα φροντίσουμε +# να εμφανιστούνε μόνο οι γραμμές που ξεκινάνε με '/home'. + +egrep "^[a-z]+:.+:[0-9]+:[0-9]+:.+:/home/*" /etc/passwd + +# c. Θα χρησιμοποιήσουμε την ίδια τεχνική με τα capture groups που χρησιμοποίησα +# και στην άσκηση 31. + +egrep "^[a-z]+:.+:([0-9]+):\1" /etc/passwd diff --git a/sh_os1/ex2/bck b/sh_os1/ex2/bck @@ -0,0 +1,48 @@ +#!/bin/sh + +# ΧΡΗΣΤΟΣ ΜΑΡΓΙΩΛΗΣ - [REDACTED] + +main() { + # We could allow more than 4 command line arguments + # since it's not going to make a difference, but for + # safety, we'll exit if they're not exactly 4. + test $# -eq 3 || usage + + # Give readable names to each argument. + username=${1} + src=${2} + dst=${3} + + # Error checks. + # In order for `username` to really be a user's name, it + # has to exist in `/etc/passwd`. + test ! -z "$(grep -w "^${username}" /etc/passwd)" || + err "'${username}' is not in /etc/passwd" + + # The -e options means anything (file, directory, device, etc.). + test -e ${src} || err "${src}: no such file or directory" + test -e ${dst} || err "${dst}: no such file or directory" + + # Create an archive if `dst` is a directory. + test -d ${dst} && tar -cvf "${dst}/${src##*/}.tar" ${src} + + # Append to `dst` only if it is a tar archive. If it's a non-archive + # then we cannot append since that would not make sense. + # `{dst##*.}` means that we want to get only its extension, if any. + test ${dst##*.} = "tar" && tar -rf ${dst} ${src} +} + +usage() { + # `{0##*/}` means the first argument (i.e the script's name) with + # its path stripped, if it exists. + echo "usage: ${0##*/} username src dst" 1>&2 + exit 1 +} + +err() { + echo "${0##*/}: $@" 1>&2 + exit 1 +} + +# Pass all command line arguments to `main`. +main "$@" diff --git a/sh_os1/ex2/createpvs b/sh_os1/ex2/createpvs @@ -0,0 +1,81 @@ +#!/bin/sh + +# ΧΡΗΣΤΟΣ ΜΑΡΓΙΩΛΗΣ - [REDACTED] + +main() { + # We could allow more than 4 command line arguments + # since it's not going to make a difference, but for + # safety, we'll exit if they're not exactly 4. + test $# -eq 4 || usage + + # Give readable names to each argument. + rootdir=${1} + ndbdirs=${2} + ndatadirs=${3} + username=${4} + + # Error checks. + test -d "${rootdir}" || err "${rootdir}: no such directory" + isnumber ${ndbdirs} || err "'${ndbdirs}' is not a number" + isnumber ${ndatadirs} || err "'${ndatadirs}' is not a number" + + # In order for `username` to really be a user's name, it + # has to exist in `/etc/passwd`. + test ! -z "$(grep -w "^${username}" /etc/passwd)" || + err "'${username}' is not in /etc/passwd" + + # The actual exercise. + makedirs "dbfolder" ${ndbdirs} + makedirs "datafolder" ${ndatadirs} +} + +usage() { + # `{0##*/}` means the first argument (i.e the script's name) with + # its path stripped, if it exists. + echo "usage: ${0##*/} root_dir num_dbdirs num_datadirs username" 1>&2 + exit 1 +} + +err() { + echo "${0##*/}: $@" 1>&2 + exit 1 +} + +isnumber() { + # If the argument does not begin *and* end in a number, then + # it's not a number. This also excludes negative numbers, but + # we shouldn't accept negative numbers anyway. + test ! -z "$(echo "${1}" | grep "^[0-9]\+$")" +} + +# Make directories in the following format: dir1, dir2, dir3... +# If there are already directories with the same name (e.g dir1, dir2), we need +# to number the new ones taking the existing ones into account (i.e dir3, dir4....). +makedirs() { + # Number of directories to create. + n=${2} + + # Get the last directory, if any, so that we know what the last number was. + lastdir=$(ls ${rootdir} | grep "${1}" | sed "s/${1}//g" | sort -V | tail -1) + + # If we didn't find any, we'll start numbering them from 1. + test -z ${lastdir} && lastdir=0 + + # If `n` was already 0 we won't do anything. + while ! [ $(expr ${n}) = 0 ]; do + # `lastdir` now holds the next number. + lastdir=$(expr ${lastdir} + 1) + + # Make a directory using the format described above + # and change the owner to `username`. + mkdir "${rootdir}/${1}${lastdir}" && + chown ${username}: "${rootdir}/${1}${lastdir}" + + # Decrement by 1 until we reach `n = 0` so that + # we can exit the loop. + n=$(expr ${n} - 1) + done +} + +# Pass all command line arguments to `main`. +main "$@" diff --git a/sh_os1/ex2/mfproc b/sh_os1/ex2/mfproc @@ -0,0 +1,110 @@ +#!/bin/sh + +# ΧΡΗΣΤΟΣ ΜΑΡΓΙΩΛΗΣ - [REDACTED] + +# Exit codes: +# 0 Success +# 1 No user +# 2 No process +# 3 Usage + +main() { + # Using getopts(1) because it's easier to parse + # optional command line options. getopts(1) works + # by passing it all the available options. If an option + # is followed by a ':', that means that getopts(1) is + # expecting an argument as well. If no argument is passed, + # it exits with an error code of 1. In this case I've + # passed it the string "u:s:" which means that the options + # are '-u' and '-s' and both of them take an argument. + # The argument is always stored in the `OPTARG` environmental + # variable. + while getopts u:s: arg; do + case "${arg}" in + # In order for `username` to really be a user's name, it + # has to exist in `/etc/passwd`. + u) test ! -z "$(grep -w "^${OPTARG}" /etc/passwd)" || + err "'${OPTARG}' is not in /etc/passwd" 1 + # Get UID from username. + uid=$(id -u ${OPTARG}) ;; + s) state="${OPTARG}" + # `state` needs to be either S, R or Z in order + # to be valid. + validstate ${state} || usage ;; + *) usage + esac + done + + count=0 + # Print header. expand(1) will will expand \t to 16 spaces + # in order for the output to be aligned. + printf "Name\tPID\tPPID\tUID\tGID\tState\n" | expand -t 16 + + # Parse each process in `/proc`. This is a slow way to parse it though. + for proc in /proc/*/status; do + procuid=$(getfield "Uid:\s*${uid}" ${proc}) + procgid=$(getfield "Gid" ${proc}) + # If the `-u` option was passed, ignore every UID that + # does not match the UID we gave it as an argument. + # We're using a `continue` command here so that it + # stop searching for anything else in this file since + # we don't need it. + test -z ${uid} || [ "${procuid}" == "${uid}" ] || continue + + procstate=$(getfield "State:\s*${state}" ${proc}) + + # Ignore any state other than S|R|Z + validstate ${procstate} || continue + + # If the `-s` option was passed, ignore every state that does + # not match the one we gave it as an argument. + test -z ${state} || [ "${procstate}" == "${state}" ] || continue + + procname=$(getfield "Name" ${proc}) + procpid=$(getfield "Pid" ${proc}) + procppid=$(getfield "PPid" ${proc}) + + # Print everything in a top(1)-like format. + printf "%s\t%s\t%s\t%s\t%s\t%s\n" \ + ${procname} ${procpid} ${procppid} ${procuid} ${procgid} ${procstate} | + expand -t 16 + + # Increment counter by 1 to keep track of how many processes + # we have printed. If `count` is 0 after the loop, the script + # will exit with error code 2, as is done below. + count=$(expr ${count} + 1) + done + + # We didn't print any process + test ${count} -eq 0 && exit 2 + + # Success! + exit 0 +} + +usage() { + # `{0##*/}` means the first argument (i.e the script's name) with + # its path stripped, if it exists. + echo "usage: ${0##*/} [-u username] [-s S|R|Z]" 1>&2 + exit 3 +} + +err() { + echo "${0##*/}: $@" 1>&2 + exit ${2} +} + +# Check if process is either S, R or Z. +validstate() { + [ "${1}" = "S" ] || [ "${1}" = "R" ] || [ "${1}" = "Z" ] +} + +# Get wanted field. grep(1) will return the line +# that begins with the first argument we passed. +# awk(1) is used to extract the 2nd field in the string. +getfield() { + grep -w "^${1}" ${2} | awk '{print $2}' +} + +# Pass all command line arguments to `main`. +main "$@" diff --git a/sh_os1/ex2/searching b/sh_os1/ex2/searching @@ -0,0 +1,82 @@ +#!/bin/sh + +# ΧΡΗΣΤΟΣ ΜΑΡΓΙΩΛΗΣ - [REDACTED] + +main() { + mode=${1} + days=${2} + # Command line arguments must be 2. + test $# -eq 2 || usage + # Check if `1` and `2` are numbers, otherwise exit. + isnumber ${mode} || err "'${mode}' is not a valid number" + isnumber ${days} || err "'${days}' is not a valid number" + # In order for `mode` to really be a valid mode, `0 <= x <= 7777` must + # satisfied, since permission modes can range from 0 to 7777. + test ${mode} -ge 0 && test ${mode} -le 7777 || err "'${mode}' is not a valid mode" + + # Pretty ugly loop. + sum1=0; sum2=0; sum3=0; sum4=0; sum5=0 + # Exit if `cont` is "n". + while [ ! "${cont}" = "n" ] ; do + read -erp "Directory name: " dir + + # Exit if nothing was typed. + test ! -z "${dir}" || err "please give a directory name" + # Check if `dir` really is a directory. + test -d "${dir}" || err "'${dir}' is not a directory" + + echo "Files with permissions ${mode}: " + find "${dir}" -perm ${mode} 2> /dev/null + sum1=$((${sum1}+$(find "${dir}" -perm ${mode} 2> /dev/null | wc -l))) + echo "" + + echo "Files modified within the last ${days} days: " + find "${dir}" -mtime -${days} 2> /dev/null + sum2=$((${sum2}+$(find "${dir}" -mtime -${days} 2> /dev/null | wc -l))) + echo "" + + echo "Subdirectories accessed within the last ${days} days: " + find "${dir}" -type d -atime -${days} 2> /dev/null + sum3=$((${sum3}+$(find "${dir}" -type d -atime -${days} 2> /dev/null | wc -l))) + echo "" + + echo "Files which all users have read access to: " + ls -l "${dir}" 2> /dev/null | grep "^-r..r..r.." + sum4=$((${sum4}+$(ls -l "${dir}" 2> /dev/null | grep "^-r..r..r.." | wc -l))) + echo "" + + echo "Subdirectories which others have write access to: " + ls -l "${dir}" 2> /dev/null | grep "^d.w..w..w." + sum5=$((${sum5}+$(ls -l "${dir}" 2> /dev/null | grep "^d.w..w..w." | wc -l))) + echo "" + + read -erp "Do you want to continue (y/n)? " cont + test "${cont}" = "n" && + + printf "Total entries found for:\n1. %s\n2. %s\n3. %s\n4. %s\n5. %s\n" \ + "${sum1}" "${sum2}" "${sum3}" "${sum4}" "${sum5}" + done + +} + +usage() { + # `{0##*/}` means the first argument (i.e the script's name) with + # its path stripped, if it exists. + echo "usage: ${0##*/} perms days" 1>&2 + exit 1 +} + +err() { + echo "${0##*/}: $@" 1>&2 + exit 1 +} + +isnumber() { + # If the argument does not begin *and* end in a number, then + # it's not a number. This also excludes negative numbers, but + # we shouldn't accept negative numbers anyway. + test ! -z "$(echo "${1}" | grep "^[0-9]\+$")" +} + +# Pass all command line arguments to `main`. +main "$@" diff --git a/sh_os1/ex2/teldb b/sh_os1/ex2/teldb @@ -0,0 +1,114 @@ +#!/bin/sh + +# ΧΡΗΣΤΟΣ ΜΑΡΓΙΩΛΗΣ - [REDACTED] + +# We'll use this later. +emptylnregex="^\ *$" + +main() { + # Parse command line options, exit if no option was passed. + case ${1} in + -a) newentry ;; + -l) list ;; + -s) sortcol ${2} ;; + -c) filter ${2} ;; + -d) deleteln ${2} ${3} ;; + -n) emptyln ;; + *) usage ;; + esac +} + +usage() { + # `{0##*/}` means the first argument (i.e the script's name) with + # its path stripped, if it exists. + # The {} around the options denote that only one option has to be + # passed to the script. + echo "usage: ${0##*/} {-a | -l | -n | -c keyword | -d keyword {-b | -r} | -s col}" 1>&2 + echo "" 1>&2 + echo "options:" 1>&2 + echo "-a add a new entry" 1>&2 + echo "-l list contents of file" 1>&2 + echo "-n count empty lines and ask if they should be deleted" 1>&2 + echo "-c filter keyword" 1>&2 + echo "-d delete lines containing a keyword followed by one of the options below" 1>&2 + echo " -b replaces line with an empty line" 1>&2 + echo " -r removes line completely" 1>&2 + echo "-s sort based on specified column (e.g ${0##*/} -s 3)" 1>&2 + + exit 1 +} + +# Exit with a `usage` message if the string that was passed is empty. +# This is used to make sure that we'll not write empty fields in `catalog`. +errempty() { + test ! -z "${1}" || usage +} + +# Skip empty lines +skipempty() { + grep -v "${emptylnregex}" +} + +# -a option - Make a new entry for `catalog`. +newentry() { + # Read fields and include an error check so that + # we don't pass an empty field. + read -erp "First name: " fname + errempty "${fname}" + + read -erp "Last name: " lname + errempty "${lname}" + + read -erp "Town: " town + errempty "${town}" + + read -erp "Phone number: " phone + errempty "${phone}" + + # Append all the things we've read to `catalog`. + printf "%s %s %s %s\n" "${fname}" "${lname}" "${town}" "${phone}" >> catalog +} + +# -l option - Print `catalog` with each line numbered. It also skips empty lines. +list() { + nl catalog | skipempty +} + +# -s option - Sort `catalog` by column. We pass the desired column in `main`. +sortcol() { + errempty "${1}" + sort -k "${1}" catalog | skipempty +} + +# -c option - Print only the lines that match a specific keyword. +filter() { + errempty "${1}" + grep "${1}" catalog +} + +# -d option - Delete a line. +deleteln() { + errempty "${1}" + errempty "${2}" + + # Parse sub-options. + case ${2} in + # Replace line with an empty line. + -b) sed -i "s/.*${1}.*//" catalog ;; + # Just delete the line. + -r) sed -i "/${1}/d" catalog ;; + esac +} + +# -n option - Count empty lines and delete them if the user answers with `y`. +emptyln() { + printf "Empty lines in 'catalog': " + grep "${emptylnregex}" catalog | wc -l + read -erp "Delete them (y/n)? " del + # Delete lines using `deleteln` with `-r` option so that it + # just deletes the line, without replacing it with an empty one. + test "${del}" = "y" && deleteln "${emptylnregex}" "-r" +} + +# Pass all command line arguments to `main`. +main "$@" diff --git a/sh_os1/ex3/ex1_cmds b/sh_os1/ex3/ex1_cmds @@ -0,0 +1,39 @@ +#!/bin/sh + +test $# -ne 1 && echo "usage: ${0##*/} gradefile" 1>&2 && exit 1 +test ! -f "${1}" && echo "${0##*/}: ${1}: no such file" 1>&2 && exit 1 + +file="${1}" + +echo "First names starting with K or N:" +awk '$1 ~ /^K|N/ {print $2, $1}' ${file} +echo "" + +echo "Last names starting with C or L:" +awk '$2 ~ /^C|L/ {print $1, $2}' ${file} +echo "" + +echo "Students with their second grade being > 85:" +awk '{if ($5 > 85 && $5 > 85) print}' ${file} +echo "" + +echo "Students in the humanities:" +awk '{if ($3 == "Theo") print}' ${file} +echo "" + +echo "Average ${file}:" +awk '{ +sum = cnt = 0; +for (i = 4; i <= NF; i++) { + sum += $i; + cnt++; +} +print $1, $2, sum / cnt}' ${file} +echo "" + +echo "Students with their third grade being < 70:" +awk 'BEGIN {cnt = 0} {if ($6 < 70) cnt++;} END {print cnt}' ${file} +echo "" + +echo "How many student names end in 'is'?" +awk 'BEGIN {cnt = 0} {if ($2 ~ /is$/) cnt++} END {print cnt}' ${file} diff --git a/sh_os1/ex3/ex2_studavgs.awk b/sh_os1/ex3/ex2_studavgs.awk @@ -0,0 +1,20 @@ +#!/usr/bin/env -S awk -f + +BEGIN { + # Quit if we don't have an input file. + if (ARGC < 2) { + print "usage: ex2_studavgs.awk gradefile"; + exit 1; + } +} + +{ + sum = cnt = 0; + for (i = 4; i <= NF; i++) { + sum += $i; + cnt++; + } + + # We're calling sort(1) from awk(1). + print "Student", NR",", $1, $2",", sum / cnt | "sort -Vrk5"; +} diff --git a/sh_os1/ex3/ex3_courseavgs.awk b/sh_os1/ex3/ex3_courseavgs.awk @@ -0,0 +1,25 @@ +#!/usr/bin/env -S awk -f + +BEGIN { + # Quit if we don't have an input file. + if (ARGC < 2) { + print "usage: ex3_courseavgs.awk gradefile"; + exit 1; + } +} + +{ + # Loop from the 4th field onwards and + # add its value to the sum array. + for (i = 4; i <= NF; i++) + sum[i] += $i; +} + +END { + # `NR` is the number of rows in the file, so + # we divide by that since each column is a + # course. + cnt = 1; + for (i = 4; i <= NF; i++) + print "Course", cnt++":", sum[i] / NR; +} diff --git a/sh_os1/ex3/ex4_rev.awk b/sh_os1/ex3/ex4_rev.awk @@ -0,0 +1,20 @@ +#!/usr/bin/env -S awk -f + +BEGIN { + # Quit if we don't have an input file. + if (ARGC < 2) { + print "usage: ex4_rev.awk file"; + exit 1; + } +} + +{ + # Add all lines to an array. + ln[NR] = $0; +} + +END { + # Print them in reverse. + for (i = NR; i >= 1; i--) + print ln[i]; +} diff --git a/sh_os1/ex3/ex5_filesize b/sh_os1/ex3/ex5_filesize @@ -0,0 +1,3 @@ +#!/bin/sh + +ls -l | grep '^-' | awk '{sum += $5} END{print sum}' diff --git a/sh_os1/ex3/ex6_votes.awk b/sh_os1/ex3/ex6_votes.awk @@ -0,0 +1,29 @@ +#!/usr/bin/env -S awk -f + +BEGIN { + # Quit if we don't have an input file. + if (ARGC != 2) { + print "usage: ex6_votes.awk votefile"; + exit 1; + } + + max = 0; +} + +{ + cnt = 0; + # We're testing only against 'y's, + # no need to check for 'n's. + for (i = 2; i <= NF; i++) + if ($i == "y") + cnt++; + if (cnt > max) { + max = cnt; + winner = $1; + } +} + +END { + print "Winner:", winner; + print "Votes:", max; +} diff --git a/sh_os1/ex3/ex7_countmatch b/sh_os1/ex3/ex7_countmatch @@ -0,0 +1,20 @@ +#!/bin/sh + +main() { + xread "String: " str + test -z "${str}" && echo "${0##*/}: give a non-empty string" 1>&2 && exit 1 + + xread "File: " file + test ! -f "${file}" && echo "${0##*/}: ${file}: no such file" 1>&2 && exit 1 + + awk "/${str}/ {cnt++} END {print cnt}" ${file} +} + +# A portable `read` function with behavior similar to +# `read -erp`. +xread() { + printf "%s" "${1}" && read -r ${2} +} + +# Pass all command line arguments to `main`. +main "$@" diff --git a/sql-databases/ex1_new_personnel.sql b/sql-databases/ex1_new_personnel.sql @@ -1,133 +0,0 @@ -CREATE TABLE DEPT ( - DEPTNO INT(2) NOT NULL, - DNAME VARCHAR, - LOC VARCHAR, - PRIMARY KEY(DEPTNO) -); - -CREATE TABLE EMP ( - EMPNO INT(2) NOT NULL, - ENAME VARCHAR, - JOB VARCHAR, - HIERDATE DATE, - MGR INT(2), - SAL FLOAT(7,2), - COMM FLOAT(7,2), - DEPTNO INT(2) NOT NULL, - PRIMARY KEY(EMPNO), - FOREIGN KEY(DEPTNO) REFERENCES DEPT(DEPTNO) -); - -CREATE TABLE PROJ ( - PROJ_CODE INT(3) NOT NULL, - DESCRIPTION VARCHAR, - PRIMARY KEY(PROJ_CODE) -); - -CREATE TABLE ASSIGN ( - EMPNO INT(2) NOT NULL, - PROJ_CODE INT(3), - A_TIME INT(3), - PRIMARY KEY(EMPNO, PROJ_CODE), - FOREIGN KEY(EMPNO) REFERENCES EMP(EMPNO), - FOREIGN KEY(PROJ_CODE) REFERENCES PROJ(PROJ_CODE) -); - -INSERT INTO DEPT VALUES - (10, 'ACCOUNTING', 'ATHENS'), - (20, 'SALES', 'LONDON'), - (30, 'RESEARCH', 'ATHENS'), - (40, 'PAYROLL', 'LONDON'); - -INSERT INTO EMP VALUES - (10, 'CODD', 'ANALYST', '1/1/89', 15, 3000, NULL, 10), - (15, 'ELMASRI', 'ANALYST', '2/5/95', 15, 1200, 150, 10), - (20, 'NAVATHE', 'SALESMAN', '7/7/77', 20, 2000, NULL, 20), - (30, 'DATE', 'PROGRAMMER', '4/5/04', 15, 1800, 200, 10); - -INSERT INTO PROJ VALUES - (100, 'PAYROLL'), - (200, 'PERSONELL'), - (300, 'SALES'); - -INSERT INTO ASSIGN VALUES - (10, 100, 40), - (10, 200, 60), - (15, 100, 100), - (20, 200, 100), - (30, 100, 100); - -/* Using SQLite3 syntax*/ - -/* .schema -> DESCRIBE */ -.schema - -/* Make output pretty */ -.header on -.mode column - -/* Show contents of every table */ -SELECT * FROM DEPT; -SELECT * FROM EMP; -SELECT * FROM PROJ; -SELECT * FROM ASSIGN; - -/* - * Output after execution (`sqlite3 -init new_personnel.sql`): - * - * CREATE TABLE DEPT ( - * DEPTNO INT(2) NOT NULL, - * DNAME VARCHAR, - * LOC VARCHAR, - * PRIMARY KEY(DEPTNO) - * ); - * CREATE TABLE EMP ( - * EMPNO INT(2) NOT NULL, - * ENAME VARCHAR, - * JOB VARCHAR, - * HIERDATE DATE, - * MGR INT(2), - * SAL FLOAT(7,2), - * COMM FLOAT(7,2), - * DEPTNO INT(2) NOT NULL, - * PRIMARY KEY(EMPNO), - * FOREIGN KEY(DEPTNO) REFERENCES DEPT(DEPTNO) - * ); - * CREATE TABLE PROJ ( - * PROJ_CODE INT(3) NOT NULL, - * DESCRIPTION VARCHAR, - * PRIMARY KEY(PROJ_CODE) - * ); - * CREATE TABLE ASSIGN ( - * EMPNO INT(2) NOT NULL, - * PROJ_CODE INT(3), - * A_TIME INT(3), - * PRIMARY KEY(EMPNO, PROJ_CODE), - * FOREIGN KEY(EMPNO) REFERENCES EMP(EMPNO), - * FOREIGN KEY(PROJ_CODE) REFERENCES PROJ(PROJ_CODE) - * ); - * DEPTNO DNAME LOC - * ------ ---------- ------ - * 10 ACCOUNTING ATHENS - * 20 SALES LONDON - * 30 RESEARCH ATHENS - * 40 PAYROLL LONDON - * EMPNO ENAME JOB HIERDATE MGR SAL COMM DEPTNO - * ----- ------- ---------- -------- --- ------ ----- ------ - * 10 CODD ANALYST 1/1/89 15 3000.0 10 - * 15 ELMASRI ANALYST 2/5/95 15 1200.0 150.0 10 - * 20 NAVATHE SALESMAN 7/7/77 20 2000.0 20 - * 30 DATE PROGRAMMER 4/5/04 15 1800.0 200.0 10 - * PROJ_CODE DESCRIPTION - * --------- ----------- - * 100 PAYROLL - * 200 PERSONELL - * 300 SALES - * EMPNO PROJ_CODE A_TIME - * ----- --------- ------ - * 10 100 40 - * 10 200 60 - * 15 100 100 - * 20 200 100 - * 30 100 100 - */ diff --git a/sql-databases/ex2_new_personnel.sql b/sql-databases/ex2_new_personnel.sql @@ -1,135 +0,0 @@ -CREATE TABLE DEPT ( - DEPTNO INT(2) NOT NULL, - DNAME VARCHAR, - LOC VARCHAR, - PRIMARY KEY(DEPTNO) -); - -CREATE TABLE EMP ( - EMPNO INT(2) NOT NULL, - ENAME VARCHAR, - JOB VARCHAR, - HIERDATE DATE, - MGR INT(2), - SAL FLOAT(7,2), - COMM FLOAT(7,2), - DEPTNO INT(2) NOT NULL, - PRIMARY KEY(EMPNO), - FOREIGN KEY(DEPTNO) REFERENCES DEPT(DEPTNO) -); - -CREATE TABLE PROJ ( - PROJ_CODE INT(3) NOT NULL, - DESCRIPTION VARCHAR, - PRIMARY KEY(PROJ_CODE) -); - -CREATE TABLE ASSIGN ( - EMPNO INT(2) NOT NULL, - PROJ_CODE INT(3), - A_TIME INT(3), - PRIMARY KEY(EMPNO, PROJ_CODE), - FOREIGN KEY(EMPNO) REFERENCES EMP(EMPNO), - FOREIGN KEY(PROJ_CODE) REFERENCES PROJ(PROJ_CODE) -); - -INSERT INTO DEPT VALUES - (10, 'ACCOUNTING', 'ATHENS'), - (20, 'SALES', 'LONDON'), - (30, 'RESEARCH', 'ATHENS'), - (40, 'PAYROLL', 'LONDON'); - -INSERT INTO EMP VALUES - (10, 'CODD', 'ANALYST', '1989-01-01', 15, 3000, NULL, 10), - (15, 'ELMASRI', 'ANALYST', '1995-05-02', 15, 1200, 150, 10), - (20, 'NAVATHE', 'SALESMAN', '1977-07-07', 20, 2000, NULL, 20), - (30, 'DATE', 'PROGRAMMER', '2004-05-04', 15, 1800, 200, 10); - -INSERT INTO PROJ VALUES - (100, 'PAYROLL'), - (200, 'PERSONELL'), - (300, 'SALES'); - -INSERT INTO ASSIGN VALUES - (10, 100, 40), - (10, 200, 60), - (15, 100, 100), - (20, 200, 100), - (30, 100, 100); - --- Using SQLite3 syntax -.header on -.mode column - --- Question 1 -SELECT ENAME, - SAL AS ΜΙΣΘΟΣ, - COMM AS ΠΡΟΜΗΘΕΙΑ, - IFNULL(ROUND(COMM * 100 / SAL, 1) || "%", "0.00%") AS ΠΟΣΟΣΤΟ - FROM EMP; - --- Question 2 -SELECT ENAME AS ΕΠΩΝΥΜΟ, - SAL AS "ΜΗΝΙΑΙΕΣ ΑΠΟΔΟΧΕΣ", - strftime("%Y", "now") - strftime("%Y", HIERDATE) AS ПРОΥΠΗΡΕΣΙΑ - FROM EMP; - --- Question 3 -SELECT ENAME AS ΕΠΩΝΥΜΟ, - JOB AS ΘΕΣΗ, - HIERDATE AS ΠΡΟΣΛΗΨΗ - FROM EMP - WHERE strftime("%d", HIERDATE) <= "05"; - --- Question 4 -SELECT ENAME AS ΕΠΩΝΥΜΟ - FROM EMP - INNER JOIN DEPT ON - DEPT.DEPTNO = EMP.DEPTNO AND - DEPT.DNAME = "ACCOUNTING"; - --- Question 5 -SELECT ENAME AS ΕΠΩΝΥΜΟ, - MAX( - (strftime("%Y", "now") - strftime("%Y", HIERDATE)) * - 12 * SAL - ) AS "ΣΥΝΟΛΙΚΟΣ ΜΙΣΘΟΣ" - FROM EMP; - - --- Output - --- Question 1: --- ENAME ΜΙΣΘΟΣ ΠΡΟΜΗΘΕΙΑ ΠΟΣΟΣΤΟ --- ------- ------ --------- ------- --- CODD 3000.0 0.00% --- ELMASRI 1200.0 150.0 12.5% --- NAVATHE 2000.0 0.00% --- DATE 1800.0 200.0 11.1% - --- Question 2: --- ΕΠΩΝΥΜΟ ΜΗΝΙΑΙΕΣ ΑΠΟΔΟΧΕΣ ПРОΥΠΗΡΕΣΙΑ --- ------- ----------------- ----------- --- CODD 3000.0 32 --- ELMASRI 1200.0 26 --- NAVATHE 2000.0 44 --- DATE 1800.0 17 - --- Question 3: --- ΕΠΩΝΥΜΟ ΘΕΣΗ ΠΡΟΣΛΗΨΗ --- ------- ---------- ---------- --- CODD ANALYST 1989-01-01 --- ELMASRI ANALYST 1995-05-02 --- DATE PROGRAMMER 2004-05-04 - --- Question 4: --- ΕΠΩΝΥΜΟ --- ------- --- CODD --- ELMASRI --- DATE - --- Question 5: --- ΕΠΩΝΥΜΟ ΣΥΝΟΛΙΚΟΣ ΜΙΣΘΟΣ --- ------- ---------------- --- CODD 1152000.0 diff --git a/sql_databases1/ex1_new_personnel.sql b/sql_databases1/ex1_new_personnel.sql @@ -0,0 +1,133 @@ +CREATE TABLE DEPT ( + DEPTNO INT(2) NOT NULL, + DNAME VARCHAR, + LOC VARCHAR, + PRIMARY KEY(DEPTNO) +); + +CREATE TABLE EMP ( + EMPNO INT(2) NOT NULL, + ENAME VARCHAR, + JOB VARCHAR, + HIERDATE DATE, + MGR INT(2), + SAL FLOAT(7,2), + COMM FLOAT(7,2), + DEPTNO INT(2) NOT NULL, + PRIMARY KEY(EMPNO), + FOREIGN KEY(DEPTNO) REFERENCES DEPT(DEPTNO) +); + +CREATE TABLE PROJ ( + PROJ_CODE INT(3) NOT NULL, + DESCRIPTION VARCHAR, + PRIMARY KEY(PROJ_CODE) +); + +CREATE TABLE ASSIGN ( + EMPNO INT(2) NOT NULL, + PROJ_CODE INT(3), + A_TIME INT(3), + PRIMARY KEY(EMPNO, PROJ_CODE), + FOREIGN KEY(EMPNO) REFERENCES EMP(EMPNO), + FOREIGN KEY(PROJ_CODE) REFERENCES PROJ(PROJ_CODE) +); + +INSERT INTO DEPT VALUES + (10, 'ACCOUNTING', 'ATHENS'), + (20, 'SALES', 'LONDON'), + (30, 'RESEARCH', 'ATHENS'), + (40, 'PAYROLL', 'LONDON'); + +INSERT INTO EMP VALUES + (10, 'CODD', 'ANALYST', '1/1/89', 15, 3000, NULL, 10), + (15, 'ELMASRI', 'ANALYST', '2/5/95', 15, 1200, 150, 10), + (20, 'NAVATHE', 'SALESMAN', '7/7/77', 20, 2000, NULL, 20), + (30, 'DATE', 'PROGRAMMER', '4/5/04', 15, 1800, 200, 10); + +INSERT INTO PROJ VALUES + (100, 'PAYROLL'), + (200, 'PERSONELL'), + (300, 'SALES'); + +INSERT INTO ASSIGN VALUES + (10, 100, 40), + (10, 200, 60), + (15, 100, 100), + (20, 200, 100), + (30, 100, 100); + +/* Using SQLite3 syntax*/ + +/* .schema -> DESCRIBE */ +.schema + +/* Make output pretty */ +.header on +.mode column + +/* Show contents of every table */ +SELECT * FROM DEPT; +SELECT * FROM EMP; +SELECT * FROM PROJ; +SELECT * FROM ASSIGN; + +/* + * Output after execution (`sqlite3 -init new_personnel.sql`): + * + * CREATE TABLE DEPT ( + * DEPTNO INT(2) NOT NULL, + * DNAME VARCHAR, + * LOC VARCHAR, + * PRIMARY KEY(DEPTNO) + * ); + * CREATE TABLE EMP ( + * EMPNO INT(2) NOT NULL, + * ENAME VARCHAR, + * JOB VARCHAR, + * HIERDATE DATE, + * MGR INT(2), + * SAL FLOAT(7,2), + * COMM FLOAT(7,2), + * DEPTNO INT(2) NOT NULL, + * PRIMARY KEY(EMPNO), + * FOREIGN KEY(DEPTNO) REFERENCES DEPT(DEPTNO) + * ); + * CREATE TABLE PROJ ( + * PROJ_CODE INT(3) NOT NULL, + * DESCRIPTION VARCHAR, + * PRIMARY KEY(PROJ_CODE) + * ); + * CREATE TABLE ASSIGN ( + * EMPNO INT(2) NOT NULL, + * PROJ_CODE INT(3), + * A_TIME INT(3), + * PRIMARY KEY(EMPNO, PROJ_CODE), + * FOREIGN KEY(EMPNO) REFERENCES EMP(EMPNO), + * FOREIGN KEY(PROJ_CODE) REFERENCES PROJ(PROJ_CODE) + * ); + * DEPTNO DNAME LOC + * ------ ---------- ------ + * 10 ACCOUNTING ATHENS + * 20 SALES LONDON + * 30 RESEARCH ATHENS + * 40 PAYROLL LONDON + * EMPNO ENAME JOB HIERDATE MGR SAL COMM DEPTNO + * ----- ------- ---------- -------- --- ------ ----- ------ + * 10 CODD ANALYST 1/1/89 15 3000.0 10 + * 15 ELMASRI ANALYST 2/5/95 15 1200.0 150.0 10 + * 20 NAVATHE SALESMAN 7/7/77 20 2000.0 20 + * 30 DATE PROGRAMMER 4/5/04 15 1800.0 200.0 10 + * PROJ_CODE DESCRIPTION + * --------- ----------- + * 100 PAYROLL + * 200 PERSONELL + * 300 SALES + * EMPNO PROJ_CODE A_TIME + * ----- --------- ------ + * 10 100 40 + * 10 200 60 + * 15 100 100 + * 20 200 100 + * 30 100 100 + */ diff --git a/sql_databases1/ex2_new_personnel.sql b/sql_databases1/ex2_new_personnel.sql @@ -0,0 +1,135 @@ +CREATE TABLE DEPT ( + DEPTNO INT(2) NOT NULL, + DNAME VARCHAR, + LOC VARCHAR, + PRIMARY KEY(DEPTNO) +); + +CREATE TABLE EMP ( + EMPNO INT(2) NOT NULL, + ENAME VARCHAR, + JOB VARCHAR, + HIERDATE DATE, + MGR INT(2), + SAL FLOAT(7,2), + COMM FLOAT(7,2), + DEPTNO INT(2) NOT NULL, + PRIMARY KEY(EMPNO), + FOREIGN KEY(DEPTNO) REFERENCES DEPT(DEPTNO) +); + +CREATE TABLE PROJ ( + PROJ_CODE INT(3) NOT NULL, + DESCRIPTION VARCHAR, + PRIMARY KEY(PROJ_CODE) +); + +CREATE TABLE ASSIGN ( + EMPNO INT(2) NOT NULL, + PROJ_CODE INT(3), + A_TIME INT(3), + PRIMARY KEY(EMPNO, PROJ_CODE), + FOREIGN KEY(EMPNO) REFERENCES EMP(EMPNO), + FOREIGN KEY(PROJ_CODE) REFERENCES PROJ(PROJ_CODE) +); + +INSERT INTO DEPT VALUES + (10, 'ACCOUNTING', 'ATHENS'), + (20, 'SALES', 'LONDON'), + (30, 'RESEARCH', 'ATHENS'), + (40, 'PAYROLL', 'LONDON'); + +INSERT INTO EMP VALUES + (10, 'CODD', 'ANALYST', '1989-01-01', 15, 3000, NULL, 10), + (15, 'ELMASRI', 'ANALYST', '1995-05-02', 15, 1200, 150, 10), + (20, 'NAVATHE', 'SALESMAN', '1977-07-07', 20, 2000, NULL, 20), + (30, 'DATE', 'PROGRAMMER', '2004-05-04', 15, 1800, 200, 10); + +INSERT INTO PROJ VALUES + (100, 'PAYROLL'), + (200, 'PERSONELL'), + (300, 'SALES'); + +INSERT INTO ASSIGN VALUES + (10, 100, 40), + (10, 200, 60), + (15, 100, 100), + (20, 200, 100), + (30, 100, 100); + +-- Using SQLite3 syntax +.header on +.mode column + +-- Question 1 +SELECT ENAME, + SAL AS ΜΙΣΘΟΣ, + COMM AS ΠΡΟΜΗΘΕΙΑ, + IFNULL(ROUND(COMM * 100 / SAL, 1) || "%", "0.00%") AS ΠΟΣΟΣΤΟ + FROM EMP; + +-- Question 2 +SELECT ENAME AS ΕΠΩΝΥΜΟ, + SAL AS "ΜΗΝΙΑΙΕΣ ΑΠΟΔΟΧΕΣ", + strftime("%Y", "now") - strftime("%Y", HIERDATE) AS ПРОΥΠΗΡΕΣΙΑ + FROM EMP; + +-- Question 3 +SELECT ENAME AS ΕΠΩΝΥΜΟ, + JOB AS ΘΕΣΗ, + HIERDATE AS ΠΡΟΣΛΗΨΗ + FROM EMP + WHERE strftime("%d", HIERDATE) <= "05"; + +-- Question 4 +SELECT ENAME AS ΕΠΩΝΥΜΟ + FROM EMP + INNER JOIN DEPT ON + DEPT.DEPTNO = EMP.DEPTNO AND + DEPT.DNAME = "ACCOUNTING"; + +-- Question 5 +SELECT ENAME AS ΕΠΩΝΥΜΟ, + MAX( + (strftime("%Y", "now") - strftime("%Y", HIERDATE)) * + 12 * SAL + ) AS "ΣΥΝΟΛΙΚΟΣ ΜΙΣΘΟΣ" + FROM EMP; + + +-- Output + +-- Question 1: +-- ENAME ΜΙΣΘΟΣ ΠΡΟΜΗΘΕΙΑ ΠΟΣΟΣΤΟ +-- ------- ------ --------- ------- +-- CODD 3000.0 0.00% +-- ELMASRI 1200.0 150.0 12.5% +-- NAVATHE 2000.0 0.00% +-- DATE 1800.0 200.0 11.1% + +-- Question 2: +-- ΕΠΩΝΥΜΟ ΜΗΝΙΑΙΕΣ ΑΠΟΔΟΧΕΣ ПРОΥΠΗΡΕΣΙΑ +-- ------- ----------------- ----------- +-- CODD 3000.0 32 +-- ELMASRI 1200.0 26 +-- NAVATHE 2000.0 44 +-- DATE 1800.0 17 + +-- Question 3: +-- ΕΠΩΝΥΜΟ ΘΕΣΗ ΠΡΟΣΛΗΨΗ +-- ------- ---------- ---------- +-- CODD ANALYST 1989-01-01 +-- ELMASRI ANALYST 1995-05-02 +-- DATE PROGRAMMER 2004-05-04 + +-- Question 4: +-- ΕΠΩΝΥΜΟ +-- ------- +-- CODD +-- ELMASRI +-- DATE + +-- Question 5: +-- ΕΠΩΝΥΜΟ ΣΥΝΟΛΙΚΟΣ ΜΙΣΘΟΣ +-- ------- ---------------- +-- CODD 1152000.0 diff --git a/vhdl-digital-design/Makefile b/vhdl-digital-design/Makefile @@ -1,10 +0,0 @@ -all: - ghdl -a ${IN}.vhd - ghdl -e ${IN} - ghdl -r ${IN} --vcd=${IN}.vcd - -sim: - gtkwave ${IN}.vcd - -clean: - rm -f *.o *.cf *.vcd ${IN} diff --git a/vhdl-digital-design/ex1/Makefile b/vhdl-digital-design/ex1/Makefile @@ -1 +0,0 @@ -include ../Makefile diff --git a/vhdl-digital-design/ex1/adder4.vhd b/vhdl-digital-design/ex1/adder4.vhd @@ -1,23 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; -use work.all; - -entity adder4 is port ( - a, b: in std_logic_vector(3 downto 0); - cin: in std_logic; - s: out std_logic_vector(3 downto 0); - cout: out std_logic -); -end adder4; - -architecture struct of adder4 is - -signal y: std_logic_vector(4 downto 0); - -begin - y(0) <= cin; - cout <= y(4); - u: for i in 0 to 3 generate - p: entity work.fa(dataflow) port map (a(i), b(i), cin, s(i), cout => y(i+1)); - end generate; -end struct; diff --git a/vhdl-digital-design/ex1/adder4_tb.vhd b/vhdl-digital-design/ex1/adder4_tb.vhd @@ -1,67 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity adder4_tb is -end adder4_tb; - -architecture behav of adder4_tb is - -signal a1, b1: std_logic_vector(3 downto 0); -signal cin1: std_logic; -signal s1: std_logic_vector(3 downto 0); -signal cout1: std_logic; - -component adder4 is port ( - a, b: in std_logic_vector(3 downto 0); - cin: in std_logic; - s: out std_logic_vector(3 downto 0); - cout: out std_logic -); -end component; - -begin - uut: adder4 port map ( - a => a1, - b => b1, - cin => cin1, - s => s1, - cout => cout1 - ); - - process begin - a1 <= "0000"; - b1 <= "0000"; - cin1 <= '0'; - wait for 20 ps; - - a1 <= "1111"; - b1 <= "1111"; - cin1 <= '0'; - wait for 20 ps; - - a1 <= "1111"; - b1 <= "1111"; - cin1 <= '1'; - wait for 20 ps; - - -- 3 + 5 (overflow) - a1 <= "0011"; - b1 <= "0101"; - cin1 <= '0'; - wait for 20 ps; - - -- -2 + 3 - -- 2 -> 0010 -> (2's complement) -> ~0010 | 0001 -> - -- 1101 | 0001 -> 1101 (+ cin) - a1 <= not "0010" or "0001"; - b1 <= "0011"; - cin1 <= '1'; - wait for 20 ps; - - -- -8 + 7 (~1000 | 0001 + cin) - a1 <= not "1000" or "0001"; - b1 <= "0111"; - cin1 <= '1'; - wait for 20 ps; - end process; -end behav; diff --git a/vhdl-digital-design/ex1/dec2to4.vhd b/vhdl-digital-design/ex1/dec2to4.vhd @@ -1,16 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity dec2to4 is port ( - a: in std_logic_vector(1 downto 0); - d: out std_logic_vector(3 downto 0) -); -end dec2to4; - -architecture dataflow of dec2to4 is -begin - d(0) <= not a(0) and not a(1); - d(1) <= not a(0) and a(1); - d(2) <= a(0) and not a(1); - d(3) <= a(0) and a(1); -end dataflow; diff --git a/vhdl-digital-design/ex1/dec2to4_tb.vhd b/vhdl-digital-design/ex1/dec2to4_tb.vhd @@ -1,37 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity dec2to4_tb is -end dec2to4_tb; - -architecture behav of dec2to4_tb is - -signal a1: std_logic_vector(1 downto 0); -signal d1: std_logic_vector(3 downto 0); - -component dec2to4 is port ( - a: in std_logic_vector(1 downto 0); - d: out std_logic_vector(3 downto 0) -); -end component; - -begin - uut: dec2to4 port map ( - a => a1, - d => d1 - ); - - process begin - a1 <= "00"; - wait for 20 ps; - - a1 <= "01"; - wait for 20 ps; - - a1 <= "10"; - wait for 20 ps; - - a1 <= "11"; - wait for 20 ps; - end process; -end behav; diff --git a/vhdl-digital-design/ex1/dec2to4en.vhd b/vhdl-digital-design/ex1/dec2to4en.vhd @@ -1,17 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity dec2to4en is port ( - a: in std_logic_vector(1 downto 0); - en: in std_logic; - d: out std_logic_vector(3 downto 0) -); -end dec2to4en; - -architecture dataflow of dec2to4en is -begin - d(0) <= not a(0) and not a(1) and en; - d(1) <= a(0) and not a(1) and en; - d(2) <= not a(0) and a(1) and en; - d(3) <= a(0) and a(1) and en; -end dataflow; diff --git a/vhdl-digital-design/ex1/dec2to4en_tb.vhd b/vhdl-digital-design/ex1/dec2to4en_tb.vhd @@ -1,60 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity dec2to4en_tb is -end dec2to4en_tb; - -architecture behav of dec2to4en_tb is - -signal a1: std_logic_vector(1 downto 0); -signal en1: std_logic; -signal d1: std_logic_vector(3 downto 0); - -component dec2to4en is port ( - a: in std_logic_vector(1 downto 0); - en: in std_logic; - d: out std_logic_vector(3 downto 0) -); -end component; - -begin - uut: dec2to4en port map ( - a => a1, - en => en1, - d => d1 - ); - - process begin - a1 <= "00"; - en1 <= '0'; - wait for 20 ps; - - a1 <= "01"; - en1 <= '0'; - wait for 20 ps; - - a1 <= "10"; - en1 <= '0'; - wait for 20 ps; - - a1 <= "11"; - en1 <= '0'; - wait for 20 ps; - - a1 <= "00"; - en1 <= '1'; - wait for 20 ps; - - a1 <= "01"; - en1 <= '1'; - wait for 20 ps; - - a1 <= "10"; - en1 <= '1'; - wait for 20 ps; - - a1 <= "11"; - en1 <= '1'; - wait for 20 ps; - end process; -end behav; diff --git a/vhdl-digital-design/ex1/dec4to16.vhd b/vhdl-digital-design/ex1/dec4to16.vhd @@ -1,28 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity dec4to16 is port ( - a: in std_logic_vector(3 downto 0); - d: out std_logic_vector(15 downto 0) -); -end dec4to16; - -architecture dataflow of dec4to16 is -begin - d(0) <= not a(3) and not a(2) and not a(1) and not a(0); - d(1) <= not a(3) and not a(2) and not a(1) and a(0); - d(2) <= not a(3) and not a(2) and a(1) and not a(0); - d(3) <= not a(3) and not a(2) and a(1) and a(0); - d(4) <= not a(3) and a(2) and not a(1) and not a(0); - d(5) <= not a(3) and a(2) and not a(1) and a(0); - d(6) <= not a(3) and a(2) and a(1) and not a(0); - d(7) <= not a(3) and a(2) and a(1) and a(0); - d(8) <= a(3) and not a(2) and not a(1) and not a(0); - d(9) <= a(3) and not a(2) and not a(1) and a(0); - d(10) <= a(3) and not a(2) and a(1) and not a(0); - d(11) <= a(3) and not a(2) and a(1) and a(0); - d(12) <= a(3) and a(2) and not a(1) and not a(0); - d(13) <= a(3) and a(2) and not a(1) and a(0); - d(14) <= a(3) and a(2) and a(1) and not a(0); - d(15) <= a(3) and a(2) and a(1) and a(0); -end dataflow; diff --git a/vhdl-digital-design/ex1/dec4to16_tb.vhd b/vhdl-digital-design/ex1/dec4to16_tb.vhd @@ -1,73 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity dec4to16_tb is -end dec4to16_tb; - -architecture behav of dec4to16_tb is - -signal a1: std_logic_vector(3 downto 0); -signal d1: std_logic_vector(15 downto 0); - -component dec4to16 is port ( - a: in std_logic_vector(3 downto 0); - d: out std_logic_vector(15 downto 0) -); -end component; - -begin - uut: dec4to16 port map ( - a => a1, - d => d1 - ); - - process begin - a1 <= "0000"; - wait for 20 ps; - - a1 <= "0001"; - wait for 20 ps; - - a1 <= "0010"; - wait for 20 ps; - - a1 <= "0011"; - wait for 20 ps; - - a1 <= "0100"; - wait for 20 ps; - - a1 <= "0101"; - wait for 20 ps; - - a1 <= "0110"; - wait for 20 ps; - - a1 <= "0111"; - wait for 20 ps; - - a1 <= "1000"; - wait for 20 ps; - - a1 <= "1001"; - wait for 20 ps; - - a1 <= "1010"; - wait for 20 ps; - - a1 <= "1011"; - wait for 20 ps; - - a1 <= "1100"; - wait for 20 ps; - - a1 <= "1101"; - wait for 20 ps; - - a1 <= "1110"; - wait for 20 ps; - - a1 <= "1111"; - wait for 20 ps; - end process; -end behav; diff --git a/vhdl-digital-design/ex1/fa.vhd b/vhdl-digital-design/ex1/fa.vhd @@ -1,14 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity fa is port ( - a, b, cin: in std_logic; - s, cout: out std_logic -); -end fa; - -architecture dataflow of fa is -begin - s <= a xor b xor cin; - cout <= (a and b) or (cin and (a xor b)); -end dataflow; diff --git a/vhdl-digital-design/ex1/fa_tb.vhd b/vhdl-digital-design/ex1/fa_tb.vhd @@ -1,68 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity fa_tb is -end fa_tb; - -architecture behav of fa_tb is - -signal a1, b1, cin1: std_logic; -signal s1, cout1: std_logic; - -component fa is port ( - a, b, cin: in std_logic; - s, cout: out std_logic -); -end component; - -begin - uut: fa port map ( - a => a1, - b => b1, - cin => cin1, - s => s1, - cout => cout1 - ); - - process begin - a1 <= '0'; - b1 <= '0'; - cin1 <= '0'; - wait for 20 ps; - - a1 <= '0'; - b1 <= '0'; - cin1 <= '1'; - wait for 20 ps; - - a1 <= '0'; - b1 <= '1'; - cin1 <= '0'; - wait for 20 ps; - - a1 <= '0'; - b1 <= '1'; - cin1 <= '1'; - wait for 20 ps; - - a1 <= '1'; - b1 <= '0'; - cin1 <= '0'; - wait for 20 ps; - - a1 <= '1'; - b1 <= '0'; - cin1 <= '1'; - wait for 20 ps; - - a1 <= '1'; - b1 <= '1'; - cin1 <= '0'; - wait for 20 ps; - - a1 <= '1'; - b1 <= '1'; - cin1 <= '1'; - wait for 20 ps; - end process; -end behav; diff --git a/vhdl-digital-design/ex1/ha.vhd b/vhdl-digital-design/ex1/ha.vhd @@ -1,14 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity ha is port ( - a, b: in bit; - s, c: out bit -); -end ha; - -architecture dataflow of ha is -begin - s <= a xor b; - c <= a and b; -end dataflow; diff --git a/vhdl-digital-design/ex1/ha_tb.vhd b/vhdl-digital-design/ex1/ha_tb.vhd @@ -1,43 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity ha_tb is -end ha_tb; - -architecture behav of ha_tb is - -signal a1, b1: bit; -signal s1, c1: bit; - -component ha is port ( - a, b: in bit; - s, c: out bit -); -end component; - -begin - uut: ha port map ( - a => a1, - b => b1, - s => s1, - c => c1 - ); - - process begin - a1 <= '0'; - b1 <= '0'; - wait for 20 ps; - - a1 <= '0'; - b1 <= '1'; - wait for 20 ps; - - a1 <= '1'; - b1 <= '0'; - wait for 20 ps; - - a1 <= '1'; - b1 <= '1'; - wait for 20 ps; - end process; -end behav; diff --git a/vhdl-digital-design/ex1/mux2to1.vhd b/vhdl-digital-design/ex1/mux2to1.vhd @@ -1,15 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity mux2to1 is -port ( - a, b, s: in bit; - c: out bit -); -end mux2to1; - -architecture dataflow of mux2to1 is -begin - c <= a when s = '1' else b; - --c <= (a and s) or (b and (not s)); -- logic form -end dataflow; diff --git a/vhdl-digital-design/ex1/mux2to1_tb.vhd b/vhdl-digital-design/ex1/mux2to1_tb.vhd @@ -1,33 +0,0 @@ -entity mux2to1_tb is -end mux2to1_tb; - -architecture tb of mux2to1_tb is - -signal a1, b1, s1, c1: bit; - -component mux2to1 -port ( - a, b, s: in bit; - c: out bit -); -end component; - -begin - m1: mux2to1 port map ( - a => a1, - b => b1, - s => s1, - c => c1 - ); - process begin - a1 <= '1'; - b1 <= '0'; - s1 <= '1'; - wait for 20 ps; - - a1 <= '1'; - b1 <= '0'; - s1 <= '0'; - wait for 20 ps; - end process; -end tb; diff --git a/vhdl-digital-design/ex1/mux4to1.vhd b/vhdl-digital-design/ex1/mux4to1.vhd @@ -1,22 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity mux4to1 is port ( - a: in std_logic_vector(3 downto 0); - s: in std_logic_vector(1 downto 0); - d: out std_logic -); -end mux4to1; - -architecture behav of mux4to1 is -begin - process (a, s) begin - case s is - when "00" => d <= a(0); - when "01" => d <= a(1); - when "10" => d <= a(2); - when "11" => d <= a(3); - when others => d <= 'X'; - end case; - end process; -end behav; diff --git a/vhdl-digital-design/ex1/mux4to1_tb.vhd b/vhdl-digital-design/ex1/mux4to1_tb.vhd @@ -1,44 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity mux4to1_tb is -end mux4to1_tb; - -architecture behav of mux4to1_tb is - -signal a1: std_logic_vector(3 downto 0); -signal s1: std_logic_vector(1 downto 0); -signal d1: std_logic; - -component mux4to1 port ( - a: in std_logic_vector(3 downto 0); - s: in std_logic_vector(1 downto 0); - d: out std_logic -); -end component; - -begin - uut: mux4to1 port map ( - a => a1, - s => s1, - d => d1 - ); - - process begin - a1 <= "0000"; - s1 <= "00"; - wait for 20 ps; - - a1 <= "0101"; - s1 <= "01"; - wait for 20 ps; - - a1 <= "1010"; - s1 <= "10"; - wait for 20 ps; - - a1 <= "1100"; - s1 <= "11"; - wait for 20 ps; - end process; -end behav; diff --git a/vhdl-digital-design/ex1/mux_triple_2to1.vhd b/vhdl-digital-design/ex1/mux_triple_2to1.vhd @@ -1,14 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity mux_triple_2to1 is port ( - a, b: in std_logic_vector(2 downto 0); - s: in std_logic; - d: out std_logic_vector(2 downto 0) -); -end mux_triple_2to1; - -architecture dataflow of mux_triple_2to1 is -begin - d <= a when s = '1' else b; -end dataflow; diff --git a/vhdl-digital-design/ex1/mux_triple_2to1_tb.vhd b/vhdl-digital-design/ex1/mux_triple_2to1_tb.vhd @@ -1,69 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity mux_triple_2to1_tb is -end mux_triple_2to1_tb; - -architecture behav of mux_triple_2to1_tb is - -signal a1, b1: std_logic_vector(2 downto 0); -signal s1: std_logic; -signal d1: std_logic_vector(2 downto 0); - -component mux_triple_2to1 port ( - a, b: in std_logic_vector(2 downto 0); - s: in std_logic; - d: out std_logic_vector(2 downto 0) -); -end component; - -begin - uut: mux_triple_2to1 port map ( - a => a1, - b => b1, - s => s1, - d => d1 - ); - - process begin - a1 <= "001"; - b1 <= "010"; - s1 <= '0'; - wait for 20 ps; - - a1 <= "010"; - b1 <= "100"; - s1 <= '0'; - wait for 20 ps; - - a1 <= "111"; - b1 <= "011"; - s1 <= '0'; - wait for 20 ps; - - a1 <= "101"; - b1 <= "111"; - s1 <= '0'; - wait for 20 ps; - - a1 <= "010"; - b1 <= "001"; - s1 <= '1'; - wait for 20 ps; - - a1 <= "000"; - b1 <= "101"; - s1 <= '1'; - wait for 20 ps; - - a1 <= "101"; - b1 <= "010"; - s1 <= '1'; - wait for 20 ps; - - a1 <= "111"; - b1 <= "101"; - s1 <= '1'; - wait for 20 ps; - end process; -end behav; diff --git a/vhdl-digital-design/ex2/Makefile b/vhdl-digital-design/ex2/Makefile @@ -1 +0,0 @@ -include ../Makefile diff --git a/vhdl-digital-design/ex2/ff.vhd b/vhdl-digital-design/ex2/ff.vhd @@ -1,15 +0,0 @@ -entity ff is port ( - d: in bit; - clk: in bit; - q: out bit -); -end ff; - -architecture behav of ff is -begin - process (clk) begin - if (clk 'event and clk = '1') then - q <= d; - end if; - end process; -end behav; diff --git a/vhdl-digital-design/ex2/ff_tb.vhd b/vhdl-digital-design/ex2/ff_tb.vhd @@ -1,53 +0,0 @@ -entity ff_tb is -end ff_tb; - -architecture behav of ff_tb is - -signal d1: bit; -signal clk1: bit; -signal q1: bit; - -component ff is port ( - d: in bit; - clk: in bit; - q: out bit -); -end component; - -begin - uut: ff port map ( - d => d1, - clk => clk1, - q => q1 - ); - - process begin - clk1 <= '1'; - wait for 150 ns; - clk1 <= '0'; - wait for 250 ns; - clk1 <= '1'; - wait for 150 ns; - clk1 <= '0'; - wait for 250 ns; - clk1 <= '1'; - wait for 150 ns; - clk1 <= '0'; - wait for 250 ns; - end process; - - process begin - d1 <= '1'; - wait for 280 ns; - d1 <= '0'; - wait for 300 ns; - d1 <= '1'; - wait for 250 ns; - d1 <= '0'; - wait for 150 ns; - d1 <= '1'; - wait for 75 ns; - d1 <= '0'; - wait for 150 ns; - end process; -end behav; diff --git a/vhdl-digital-design/ex2/ffrst.vhd b/vhdl-digital-design/ex2/ffrst.vhd @@ -1,18 +0,0 @@ -entity ffrst is port ( - d: in bit; - clk: in bit; - rst: in bit; - q: out bit -); -end ffrst; - -architecture behav of ffrst is -begin - process (clk, rst) begin - if (rst = '0') then - q <= '0'; - elsif (clk 'event and clk = '1') then - q <= d; - end if; - end process; -end behav; diff --git a/vhdl-digital-design/ex2/ffrst_tb.vhd b/vhdl-digital-design/ex2/ffrst_tb.vhd @@ -1,59 +0,0 @@ -entity ffrst_tb is -end ffrst_tb; - -architecture behav of ffrst_tb is - -signal d1: bit; -signal clk1: bit; -signal rst1: bit; -signal q1: bit; - -component ffrst is port ( - d: in bit; - clk: in bit; - rst: in bit; - q: out bit -); -end component; - -begin - uut: ffrst port map ( - d => d1, - clk => clk1, - rst => rst1, - q => q1 - ); - - process begin - rst1 <= '1'; - clk1 <= '1'; - wait for 150 ns; - clk1 <= '0'; - wait for 250 ns; - rst1 <= '0'; -- reset now is 0 so q is always 0 now - clk1 <= '1'; - wait for 150 ns; - clk1 <= '0'; - wait for 250 ns; - rst1 <= '1'; - clk1 <= '1'; - wait for 150 ns; - clk1 <= '0'; - wait for 250 ns; - end process; - - process begin - d1 <= '1'; - wait for 280 ns; - d1 <= '0'; - wait for 300 ns; - d1 <= '1'; - wait for 250 ns; - d1 <= '0'; - wait for 150 ns; - d1 <= '1'; - wait for 75 ns; - d1 <= '0'; - wait for 150 ns; - end process; -end behav; diff --git a/vhdl-digital-design/ex2/latch.vhd b/vhdl-digital-design/ex2/latch.vhd @@ -1,15 +0,0 @@ -entity latch is port ( - d: in bit; - en: in bit; - q: out bit -); -end latch; - -architecture behav of latch is -begin - process (d, en) begin - if (en = '1') then - q <= d; - end if; - end process; -end behav; diff --git a/vhdl-digital-design/ex2/latch_tb.vhd b/vhdl-digital-design/ex2/latch_tb.vhd @@ -1,53 +0,0 @@ -entity latch_tb is -end latch_tb; - -architecture behav of latch_tb is - -signal d1: bit; -signal en1: bit; -signal q1: bit; - -component latch is port ( - d: in bit; - en: in bit; - q: out bit -); -end component; - -begin - uut: latch port map ( - d => d1, - en => en1, - q => q1 - ); - - process begin - en1 <= '1'; - wait for 150 ns; - en1 <= '0'; - wait for 250 ns; - en1 <= '1'; - wait for 150 ns; - en1 <= '0'; - wait for 250 ns; - en1 <= '1'; - wait for 150 ns; - en1 <= '0'; - wait for 250 ns; - end process; - - process begin - d1 <= '1'; - wait for 280 ns; - d1 <= '0'; - wait for 300 ns; - d1 <= '1'; - wait for 250 ns; - d1 <= '0'; - wait for 150 ns; - d1 <= '1'; - wait for 75 ns; - d1 <= '0'; - wait for 150 ns; - end process; -end behav; diff --git a/vhdl-digital-design/ex2/reg.vhd b/vhdl-digital-design/ex2/reg.vhd @@ -1,22 +0,0 @@ -entity reg is port ( - d: in bit_vector(3 downto 0); - clk: in bit; - clr: in bit; - q: out bit_vector(3 downto 0) -); -end reg; - -architecture struct of reg is -component ffrst is port ( - d: in bit; - clk: in bit; - rst: in bit; - q: out bit -); -end component; - -begin - u: for i in 0 to 3 generate - f: ffrst port map (d(i), clk, clr, q(i)); - end generate; -end struct; diff --git a/vhdl-digital-design/ex2/reg_tb.vhd b/vhdl-digital-design/ex2/reg_tb.vhd @@ -1,48 +0,0 @@ -entity reg_tb is -end reg_tb; - -architecture behav of reg_tb is - -signal d1: bit_vector(3 downto 0); -signal clk1: bit; -signal clr1: bit; -signal q1: bit_vector(3 downto 0); - -component reg is port ( - d: in bit_vector(3 downto 0); - clk: in bit; - clr: in bit; - q: out bit_vector(3 downto 0) -); -end component; - -begin - uut: reg port map ( - d => d1, - clk => clk1, - clr => clr1, - q => q1 - ); - - process begin - clr1 <= '0'; - clk1 <= '0'; - d1 <= "0001"; - wait for 250 ns; - - clr1 <= '1'; - clk1 <= '1'; - d1 <= "0001"; - wait for 250 ns; - - clr1 <= '1'; - clk1 <= '0'; - d1 <= "0011"; - wait for 250 ns; - - clr1 <= '1'; - clk1 <= '1'; - d1 <= "0101"; - wait for 250 ns; - end process; -end behav;- \ No newline at end of file diff --git a/vhdl-digital-design/ex2/shift4.vhd b/vhdl-digital-design/ex2/shift4.vhd @@ -1,32 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity shift4 is port ( - d: in std_logic_vector(3 downto 0); - en: in std_logic; - load: in std_logic; - sin: in std_logic; - clk: in std_logic; - q: out std_logic_vector(3 downto 0) -); -end shift4; - -architecture behav of shift4 is - -signal qq: std_logic_vector(3 downto 0); - -begin - process (clk) begin - if (rising_edge(clk)) then - if (load = '1') then - q <= d; - elsif (en = '1') then - qq(0) <= qq(1); - qq(1) <= qq(2); - qq(2) <= qq(3); - qq(3) <= sin; - end if; - end if; - end process; - q <= qq; -end behav; diff --git a/vhdl-digital-design/ex2/shiftn.vhd b/vhdl-digital-design/ex2/shiftn.vhd @@ -1,34 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity shiftn is - generic (n: integer := 8); - port ( - d: in std_logic_vector(n - 1 downto 0); - en: in std_logic; - load: in std_logic; - sin: in std_logic; - clk: in std_logic; - q: out std_logic_vector(n - 1 downto 0) -); -end shiftn; - -architecture behav of shiftn is - -signal qq: std_logic_vector(n - 1 downto 0); - -begin - process (clk) begin - if (rising_edge(clk)) then - if (load = '1') then - q <= d; - elsif (en = '1') then - u: for i in 0 to n - 2 loop - qq(i) <= qq(i + 1); - end loop; - qq(n - 1) <= sin; - end if; - end if; - end process; - q <= qq; -end behav;- \ No newline at end of file diff --git a/vhdl-digital-design/ex2/upcount.vhd b/vhdl-digital-design/ex2/upcount.vhd @@ -1,22 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; -use ieee.std_logic_arith.all; -use ieee.std_logic_unsigned.all; - -entity upcount is port ( - clk: in std_logic; - rst: in std_logic; - q: inout std_logic_vector(1 downto 0) -); -end upcount; - -architecture behav of upcount is -begin - process (clk, rst) begin - if (rst = '1') then - q <= "00"; - elsif (rising_edge(clk)) then - q <= q + 1; - end if; - end process; -end behav; diff --git a/vhdl-digital-design/ex2/upcount_tb.vhd b/vhdl-digital-design/ex2/upcount_tb.vhd @@ -1,35 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity upcount_tb is -end upcount_tb; - -architecture behav of upcount_tb is - -signal clk1: std_logic := '1'; -signal rst1: std_logic := '1'; -signal q1: std_logic_vector(1 downto 0); - -component upcount is port ( - clk: in std_logic; - rst: in std_logic; - q: inout std_logic_vector(1 downto 0) -); -end component; - -begin - uut: upcount port map ( - clk => clk1, - rst => rst1, - q => q1 - ); - - process begin - rst1 <= '0'; - clk1 <= '0'; - wait for 250 ns; - - clk1 <= '1'; - wait for 250 ns; - end process; -end behav; diff --git a/vhdl-digital-design/ex3/Makefile b/vhdl-digital-design/ex3/Makefile @@ -1 +0,0 @@ -include ../Makefile diff --git a/vhdl-digital-design/ex3/regfile.vhd b/vhdl-digital-design/ex3/regfile.vhd @@ -1,35 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; -use ieee.std_logic_unsigned.all; -use ieee.numeric_std.all; - -entity regfile is -generic ( - dw: natural := 4; - sz: natural := 4; - addrw: natural := 2 -); -port ( - a: in std_logic_vector(dw-1 downto 0); - addr: in std_logic_vector(addrw-1 downto 0); - we: in std_logic; - clk: in std_logic; - c: out std_logic_vector(dw-1 downto 0) -); -end regfile; - -architecture behav of regfile is - -type regarr is array(sz-1 downto 0) of std_logic_vector(dw-1 downto 0); -signal regf: regarr; - -begin - process (clk) begin - if (falling_edge(clk)) then - if (we = '1') then - regf(to_integer(unsigned(addr))) <= a; - end if; - end if; - end process; - c <= regf(to_integer(unsigned(addr))); -end behav; diff --git a/vhdl-digital-design/ex3/regfile_ext.vhd b/vhdl-digital-design/ex3/regfile_ext.vhd @@ -1,45 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; -use ieee.std_logic_unsigned.all; -use ieee.numeric_std.all; - -entity regfile_ext is -generic ( - dw: natural := 4; - sz: natural := 4; - addrw: natural := 2 -); -port ( - a: in std_logic_vector(dw-1 downto 0); - raddr1: in std_logic_vector(addrw-1 downto 0); - raddr2: in std_logic_vector(addrw-1 downto 0); - waddr: in std_logic_vector(addrw-1 downto 0); - we: in std_logic; - clk: in std_logic; - rst: in std_logic; - b: out std_logic_vector(dw-1 downto 0); - c: out std_logic_vector(dw-1 downto 0) -); -end regfile_ext; - -architecture behav of regfile_ext is - -type regarr is array(sz-1 downto 0) of std_logic_vector(dw-1 downto 0); -signal regf: regarr; - -begin - process (clk) begin - if (rst = '1') then - regf(0) <= "0000"; - regf(1) <= "0000"; - regf(2) <= "0000"; - regf(3) <= "0000"; - elsif (falling_edge(clk)) then - if (we = '1') then - regf(to_integer(unsigned(waddr))) <= a; - end if; - end if; - end process; - b <= regf(to_integer(unsigned(raddr1))); - c <= regf(to_integer(unsigned(raddr2))); -end behav; diff --git a/vhdl-digital-design/ex3/regfile_ext_tb.vhd b/vhdl-digital-design/ex3/regfile_ext_tb.vhd @@ -1,111 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity regfile_ext_tb is -end regfile_ext_tb; - -architecture behav of regfile_ext_tb is - -component regfile_ext is -generic ( - dw: natural := 4; - sz: natural := 4; - addrw: natural := 2 -); -port ( - a: in std_logic_vector(dw-1 downto 0); - raddr1: in std_logic_vector(addrw-1 downto 0); - raddr2: in std_logic_vector(addrw-1 downto 0); - waddr: in std_logic_vector(addrw-1 downto 0); - we: in std_logic; - clk: in std_logic; - rst: in std_logic; - b: out std_logic_vector(dw-1 downto 0); - c: out std_logic_vector(dw-1 downto 0) -); -end component; - -signal s_dw: natural := 4; -signal s_sz: natural := 4; -signal s_addrw: natural := 2; -signal s_a: std_logic_vector(s_dw-1 downto 0); -signal s_raddr1:std_logic_vector(s_addrw-1 downto 0); -signal s_raddr2:std_logic_vector(s_addrw-1 downto 0); -signal s_waddr: std_logic_vector(s_addrw-1 downto 0); -signal s_we: std_logic; -signal s_clk: std_logic; -signal s_rst: std_logic; -signal s_b: std_logic_vector(s_dw-1 downto 0); -signal s_c: std_logic_vector(s_dw-1 downto 0); - -begin - uut: regfile_ext port map ( - a => s_a, - raddr1 => s_raddr1, - raddr2 => s_raddr2, - waddr => s_waddr, - we => s_we, - clk => s_clk, - rst => s_rst, - b => s_b, - c => s_c - ); - - process begin - s_we <= '1'; - s_clk <= '1'; - s_rst <= '1'; - wait for 250 ns; - - s_we <= '1'; - s_clk <= '0'; - s_rst <= '0'; - s_raddr1 <= "00"; - s_raddr2 <= "00"; - s_waddr <= "00"; - s_a <= "0101"; - wait for 250 ns; - - s_we <= '1'; - s_clk <= '1'; - s_rst <= '1'; - wait for 250 ns; - - s_we <= '1'; - s_clk <= '0'; - s_rst <= '0'; - s_raddr1 <= "01"; - s_raddr2 <= "01"; - s_waddr <= "01"; - s_a <= "1010"; - wait for 250 ns; - - s_we <= '1'; - s_clk <= '1'; - s_rst <= '1'; - wait for 250 ns; - - s_we <= '1'; - s_clk <= '0'; - s_rst <= '0'; - s_raddr1 <= "10"; - s_raddr2 <= "10"; - s_waddr <= "10"; - s_a <= "0000"; - wait for 250 ns; - - s_we <= '1'; - s_clk <= '1'; - s_rst <= '1'; - wait for 250 ns; - - s_we <= '1'; - s_clk <= '0'; - s_rst <= '0'; - s_raddr1 <= "11"; - s_raddr2 <= "11"; - s_waddr <= "11"; - s_a <= "1111"; - wait for 250 ns; - end process; -end behav; diff --git a/vhdl-digital-design/ex3/regfile_tb.vhd b/vhdl-digital-design/ex3/regfile_tb.vhd @@ -1,83 +0,0 @@ -library ieee; -use ieee.std_logic_1164.all; - -entity regfile_tb is -end regfile_tb; - -architecture behav of regfile_tb is - -component regfile is -generic ( - dw: natural := 4; - sz: natural := 4; - addrw: natural := 2 -); -port ( - a: in std_logic_vector(dw-1 downto 0); - addr: in std_logic_vector(addrw-1 downto 0); - we: in std_logic; - clk: in std_logic; - c: out std_logic_vector(dw-1 downto 0) -); -end component; - -signal s_dw: natural := 4; -signal s_sz: natural := 4; -signal s_addrw: natural := 2; -signal s_a: std_logic_vector(s_dw-1 downto 0); -signal s_addr: std_logic_vector(s_addrw-1 downto 0); -signal s_we: std_logic; -signal s_clk: std_logic; -signal s_c: std_logic_vector(s_dw-1 downto 0); - -begin - uut: regfile port map ( - a => s_a, - addr => s_addr, - we => s_we, - clk => s_clk, - c => s_c - ); - - process begin - s_we <= '1'; - s_clk <= '1'; - wait for 250 ns; - - s_we <= '1'; - s_clk <= '0'; - s_addr <= "00"; - s_a <= "0101"; - wait for 250 ns; - - s_we <= '1'; - s_clk <= '1'; - wait for 250 ns; - - s_we <= '1'; - s_clk <= '0'; - s_addr <= "01"; - s_a <= "1101"; - wait for 250 ns; - - s_we <= '1'; - s_clk <= '1'; - wait for 250 ns; - - s_we <= '1'; - s_clk <= '0'; - s_addr <= "10"; - s_a <= "0010"; - wait for 250 ns; - - s_we <= '1'; - s_clk <= '1'; - wait for 250 ns; - - s_we <= '1'; - s_clk <= '0'; - s_addr <= "11"; - s_a <= "1001"; - wait for 250 ns; - end process; -end behav; diff --git a/vhdl_digital_design/Makefile b/vhdl_digital_design/Makefile @@ -0,0 +1,10 @@ +all: + ghdl -a ${IN}.vhd + ghdl -e ${IN} + ghdl -r ${IN} --vcd=${IN}.vcd + +sim: + gtkwave ${IN}.vcd + +clean: + rm -f *.o *.cf *.vcd ${IN} diff --git a/vhdl_digital_design/ex1/Makefile b/vhdl_digital_design/ex1/Makefile @@ -0,0 +1 @@ +include ../Makefile diff --git a/vhdl_digital_design/ex1/adder4.vhd b/vhdl_digital_design/ex1/adder4.vhd @@ -0,0 +1,23 @@ +library ieee; +use ieee.std_logic_1164.all; +use work.all; + +entity adder4 is port ( + a, b: in std_logic_vector(3 downto 0); + cin: in std_logic; + s: out std_logic_vector(3 downto 0); + cout: out std_logic +); +end adder4; + +architecture struct of adder4 is + +signal y: std_logic_vector(4 downto 0); + +begin + y(0) <= cin; + cout <= y(4); + u: for i in 0 to 3 generate + p: entity work.fa(dataflow) port map (a(i), b(i), cin, s(i), cout => y(i+1)); + end generate; +end struct; diff --git a/vhdl_digital_design/ex1/adder4_tb.vhd b/vhdl_digital_design/ex1/adder4_tb.vhd @@ -0,0 +1,67 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity adder4_tb is +end adder4_tb; + +architecture behav of adder4_tb is + +signal a1, b1: std_logic_vector(3 downto 0); +signal cin1: std_logic; +signal s1: std_logic_vector(3 downto 0); +signal cout1: std_logic; + +component adder4 is port ( + a, b: in std_logic_vector(3 downto 0); + cin: in std_logic; + s: out std_logic_vector(3 downto 0); + cout: out std_logic +); +end component; + +begin + uut: adder4 port map ( + a => a1, + b => b1, + cin => cin1, + s => s1, + cout => cout1 + ); + + process begin + a1 <= "0000"; + b1 <= "0000"; + cin1 <= '0'; + wait for 20 ps; + + a1 <= "1111"; + b1 <= "1111"; + cin1 <= '0'; + wait for 20 ps; + + a1 <= "1111"; + b1 <= "1111"; + cin1 <= '1'; + wait for 20 ps; + + -- 3 + 5 (overflow) + a1 <= "0011"; + b1 <= "0101"; + cin1 <= '0'; + wait for 20 ps; + + -- -2 + 3 + -- 2 -> 0010 -> (2's complement) -> ~0010 | 0001 -> + -- 1101 | 0001 -> 1101 (+ cin) + a1 <= not "0010" or "0001"; + b1 <= "0011"; + cin1 <= '1'; + wait for 20 ps; + + -- -8 + 7 (~1000 | 0001 + cin) + a1 <= not "1000" or "0001"; + b1 <= "0111"; + cin1 <= '1'; + wait for 20 ps; + end process; +end behav; diff --git a/vhdl_digital_design/ex1/dec2to4.vhd b/vhdl_digital_design/ex1/dec2to4.vhd @@ -0,0 +1,16 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity dec2to4 is port ( + a: in std_logic_vector(1 downto 0); + d: out std_logic_vector(3 downto 0) +); +end dec2to4; + +architecture dataflow of dec2to4 is +begin + d(0) <= not a(0) and not a(1); + d(1) <= not a(0) and a(1); + d(2) <= a(0) and not a(1); + d(3) <= a(0) and a(1); +end dataflow; diff --git a/vhdl_digital_design/ex1/dec2to4_tb.vhd b/vhdl_digital_design/ex1/dec2to4_tb.vhd @@ -0,0 +1,37 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity dec2to4_tb is +end dec2to4_tb; + +architecture behav of dec2to4_tb is + +signal a1: std_logic_vector(1 downto 0); +signal d1: std_logic_vector(3 downto 0); + +component dec2to4 is port ( + a: in std_logic_vector(1 downto 0); + d: out std_logic_vector(3 downto 0) +); +end component; + +begin + uut: dec2to4 port map ( + a => a1, + d => d1 + ); + + process begin + a1 <= "00"; + wait for 20 ps; + + a1 <= "01"; + wait for 20 ps; + + a1 <= "10"; + wait for 20 ps; + + a1 <= "11"; + wait for 20 ps; + end process; +end behav; diff --git a/vhdl_digital_design/ex1/dec2to4en.vhd b/vhdl_digital_design/ex1/dec2to4en.vhd @@ -0,0 +1,17 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity dec2to4en is port ( + a: in std_logic_vector(1 downto 0); + en: in std_logic; + d: out std_logic_vector(3 downto 0) +); +end dec2to4en; + +architecture dataflow of dec2to4en is +begin + d(0) <= not a(0) and not a(1) and en; + d(1) <= a(0) and not a(1) and en; + d(2) <= not a(0) and a(1) and en; + d(3) <= a(0) and a(1) and en; +end dataflow; diff --git a/vhdl_digital_design/ex1/dec2to4en_tb.vhd b/vhdl_digital_design/ex1/dec2to4en_tb.vhd @@ -0,0 +1,60 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity dec2to4en_tb is +end dec2to4en_tb; + +architecture behav of dec2to4en_tb is + +signal a1: std_logic_vector(1 downto 0); +signal en1: std_logic; +signal d1: std_logic_vector(3 downto 0); + +component dec2to4en is port ( + a: in std_logic_vector(1 downto 0); + en: in std_logic; + d: out std_logic_vector(3 downto 0) +); +end component; + +begin + uut: dec2to4en port map ( + a => a1, + en => en1, + d => d1 + ); + + process begin + a1 <= "00"; + en1 <= '0'; + wait for 20 ps; + + a1 <= "01"; + en1 <= '0'; + wait for 20 ps; + + a1 <= "10"; + en1 <= '0'; + wait for 20 ps; + + a1 <= "11"; + en1 <= '0'; + wait for 20 ps; + + a1 <= "00"; + en1 <= '1'; + wait for 20 ps; + + a1 <= "01"; + en1 <= '1'; + wait for 20 ps; + + a1 <= "10"; + en1 <= '1'; + wait for 20 ps; + + a1 <= "11"; + en1 <= '1'; + wait for 20 ps; + end process; +end behav; diff --git a/vhdl_digital_design/ex1/dec4to16.vhd b/vhdl_digital_design/ex1/dec4to16.vhd @@ -0,0 +1,28 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity dec4to16 is port ( + a: in std_logic_vector(3 downto 0); + d: out std_logic_vector(15 downto 0) +); +end dec4to16; + +architecture dataflow of dec4to16 is +begin + d(0) <= not a(3) and not a(2) and not a(1) and not a(0); + d(1) <= not a(3) and not a(2) and not a(1) and a(0); + d(2) <= not a(3) and not a(2) and a(1) and not a(0); + d(3) <= not a(3) and not a(2) and a(1) and a(0); + d(4) <= not a(3) and a(2) and not a(1) and not a(0); + d(5) <= not a(3) and a(2) and not a(1) and a(0); + d(6) <= not a(3) and a(2) and a(1) and not a(0); + d(7) <= not a(3) and a(2) and a(1) and a(0); + d(8) <= a(3) and not a(2) and not a(1) and not a(0); + d(9) <= a(3) and not a(2) and not a(1) and a(0); + d(10) <= a(3) and not a(2) and a(1) and not a(0); + d(11) <= a(3) and not a(2) and a(1) and a(0); + d(12) <= a(3) and a(2) and not a(1) and not a(0); + d(13) <= a(3) and a(2) and not a(1) and a(0); + d(14) <= a(3) and a(2) and a(1) and not a(0); + d(15) <= a(3) and a(2) and a(1) and a(0); +end dataflow; diff --git a/vhdl_digital_design/ex1/dec4to16_tb.vhd b/vhdl_digital_design/ex1/dec4to16_tb.vhd @@ -0,0 +1,73 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity dec4to16_tb is +end dec4to16_tb; + +architecture behav of dec4to16_tb is + +signal a1: std_logic_vector(3 downto 0); +signal d1: std_logic_vector(15 downto 0); + +component dec4to16 is port ( + a: in std_logic_vector(3 downto 0); + d: out std_logic_vector(15 downto 0) +); +end component; + +begin + uut: dec4to16 port map ( + a => a1, + d => d1 + ); + + process begin + a1 <= "0000"; + wait for 20 ps; + + a1 <= "0001"; + wait for 20 ps; + + a1 <= "0010"; + wait for 20 ps; + + a1 <= "0011"; + wait for 20 ps; + + a1 <= "0100"; + wait for 20 ps; + + a1 <= "0101"; + wait for 20 ps; + + a1 <= "0110"; + wait for 20 ps; + + a1 <= "0111"; + wait for 20 ps; + + a1 <= "1000"; + wait for 20 ps; + + a1 <= "1001"; + wait for 20 ps; + + a1 <= "1010"; + wait for 20 ps; + + a1 <= "1011"; + wait for 20 ps; + + a1 <= "1100"; + wait for 20 ps; + + a1 <= "1101"; + wait for 20 ps; + + a1 <= "1110"; + wait for 20 ps; + + a1 <= "1111"; + wait for 20 ps; + end process; +end behav; diff --git a/vhdl_digital_design/ex1/fa.vhd b/vhdl_digital_design/ex1/fa.vhd @@ -0,0 +1,14 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity fa is port ( + a, b, cin: in std_logic; + s, cout: out std_logic +); +end fa; + +architecture dataflow of fa is +begin + s <= a xor b xor cin; + cout <= (a and b) or (cin and (a xor b)); +end dataflow; diff --git a/vhdl_digital_design/ex1/fa_tb.vhd b/vhdl_digital_design/ex1/fa_tb.vhd @@ -0,0 +1,68 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity fa_tb is +end fa_tb; + +architecture behav of fa_tb is + +signal a1, b1, cin1: std_logic; +signal s1, cout1: std_logic; + +component fa is port ( + a, b, cin: in std_logic; + s, cout: out std_logic +); +end component; + +begin + uut: fa port map ( + a => a1, + b => b1, + cin => cin1, + s => s1, + cout => cout1 + ); + + process begin + a1 <= '0'; + b1 <= '0'; + cin1 <= '0'; + wait for 20 ps; + + a1 <= '0'; + b1 <= '0'; + cin1 <= '1'; + wait for 20 ps; + + a1 <= '0'; + b1 <= '1'; + cin1 <= '0'; + wait for 20 ps; + + a1 <= '0'; + b1 <= '1'; + cin1 <= '1'; + wait for 20 ps; + + a1 <= '1'; + b1 <= '0'; + cin1 <= '0'; + wait for 20 ps; + + a1 <= '1'; + b1 <= '0'; + cin1 <= '1'; + wait for 20 ps; + + a1 <= '1'; + b1 <= '1'; + cin1 <= '0'; + wait for 20 ps; + + a1 <= '1'; + b1 <= '1'; + cin1 <= '1'; + wait for 20 ps; + end process; +end behav; diff --git a/vhdl_digital_design/ex1/ha.vhd b/vhdl_digital_design/ex1/ha.vhd @@ -0,0 +1,14 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity ha is port ( + a, b: in bit; + s, c: out bit +); +end ha; + +architecture dataflow of ha is +begin + s <= a xor b; + c <= a and b; +end dataflow; diff --git a/vhdl_digital_design/ex1/ha_tb.vhd b/vhdl_digital_design/ex1/ha_tb.vhd @@ -0,0 +1,43 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity ha_tb is +end ha_tb; + +architecture behav of ha_tb is + +signal a1, b1: bit; +signal s1, c1: bit; + +component ha is port ( + a, b: in bit; + s, c: out bit +); +end component; + +begin + uut: ha port map ( + a => a1, + b => b1, + s => s1, + c => c1 + ); + + process begin + a1 <= '0'; + b1 <= '0'; + wait for 20 ps; + + a1 <= '0'; + b1 <= '1'; + wait for 20 ps; + + a1 <= '1'; + b1 <= '0'; + wait for 20 ps; + + a1 <= '1'; + b1 <= '1'; + wait for 20 ps; + end process; +end behav; diff --git a/vhdl_digital_design/ex1/mux2to1.vhd b/vhdl_digital_design/ex1/mux2to1.vhd @@ -0,0 +1,15 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity mux2to1 is +port ( + a, b, s: in bit; + c: out bit +); +end mux2to1; + +architecture dataflow of mux2to1 is +begin + c <= a when s = '1' else b; + --c <= (a and s) or (b and (not s)); -- logic form +end dataflow; diff --git a/vhdl_digital_design/ex1/mux2to1_tb.vhd b/vhdl_digital_design/ex1/mux2to1_tb.vhd @@ -0,0 +1,33 @@ +entity mux2to1_tb is +end mux2to1_tb; + +architecture tb of mux2to1_tb is + +signal a1, b1, s1, c1: bit; + +component mux2to1 +port ( + a, b, s: in bit; + c: out bit +); +end component; + +begin + m1: mux2to1 port map ( + a => a1, + b => b1, + s => s1, + c => c1 + ); + process begin + a1 <= '1'; + b1 <= '0'; + s1 <= '1'; + wait for 20 ps; + + a1 <= '1'; + b1 <= '0'; + s1 <= '0'; + wait for 20 ps; + end process; +end tb; diff --git a/vhdl_digital_design/ex1/mux4to1.vhd b/vhdl_digital_design/ex1/mux4to1.vhd @@ -0,0 +1,22 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity mux4to1 is port ( + a: in std_logic_vector(3 downto 0); + s: in std_logic_vector(1 downto 0); + d: out std_logic +); +end mux4to1; + +architecture behav of mux4to1 is +begin + process (a, s) begin + case s is + when "00" => d <= a(0); + when "01" => d <= a(1); + when "10" => d <= a(2); + when "11" => d <= a(3); + when others => d <= 'X'; + end case; + end process; +end behav; diff --git a/vhdl_digital_design/ex1/mux4to1_tb.vhd b/vhdl_digital_design/ex1/mux4to1_tb.vhd @@ -0,0 +1,44 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity mux4to1_tb is +end mux4to1_tb; + +architecture behav of mux4to1_tb is + +signal a1: std_logic_vector(3 downto 0); +signal s1: std_logic_vector(1 downto 0); +signal d1: std_logic; + +component mux4to1 port ( + a: in std_logic_vector(3 downto 0); + s: in std_logic_vector(1 downto 0); + d: out std_logic +); +end component; + +begin + uut: mux4to1 port map ( + a => a1, + s => s1, + d => d1 + ); + + process begin + a1 <= "0000"; + s1 <= "00"; + wait for 20 ps; + + a1 <= "0101"; + s1 <= "01"; + wait for 20 ps; + + a1 <= "1010"; + s1 <= "10"; + wait for 20 ps; + + a1 <= "1100"; + s1 <= "11"; + wait for 20 ps; + end process; +end behav; diff --git a/vhdl_digital_design/ex1/mux_triple_2to1.vhd b/vhdl_digital_design/ex1/mux_triple_2to1.vhd @@ -0,0 +1,14 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity mux_triple_2to1 is port ( + a, b: in std_logic_vector(2 downto 0); + s: in std_logic; + d: out std_logic_vector(2 downto 0) +); +end mux_triple_2to1; + +architecture dataflow of mux_triple_2to1 is +begin + d <= a when s = '1' else b; +end dataflow; diff --git a/vhdl_digital_design/ex1/mux_triple_2to1_tb.vhd b/vhdl_digital_design/ex1/mux_triple_2to1_tb.vhd @@ -0,0 +1,69 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity mux_triple_2to1_tb is +end mux_triple_2to1_tb; + +architecture behav of mux_triple_2to1_tb is + +signal a1, b1: std_logic_vector(2 downto 0); +signal s1: std_logic; +signal d1: std_logic_vector(2 downto 0); + +component mux_triple_2to1 port ( + a, b: in std_logic_vector(2 downto 0); + s: in std_logic; + d: out std_logic_vector(2 downto 0) +); +end component; + +begin + uut: mux_triple_2to1 port map ( + a => a1, + b => b1, + s => s1, + d => d1 + ); + + process begin + a1 <= "001"; + b1 <= "010"; + s1 <= '0'; + wait for 20 ps; + + a1 <= "010"; + b1 <= "100"; + s1 <= '0'; + wait for 20 ps; + + a1 <= "111"; + b1 <= "011"; + s1 <= '0'; + wait for 20 ps; + + a1 <= "101"; + b1 <= "111"; + s1 <= '0'; + wait for 20 ps; + + a1 <= "010"; + b1 <= "001"; + s1 <= '1'; + wait for 20 ps; + + a1 <= "000"; + b1 <= "101"; + s1 <= '1'; + wait for 20 ps; + + a1 <= "101"; + b1 <= "010"; + s1 <= '1'; + wait for 20 ps; + + a1 <= "111"; + b1 <= "101"; + s1 <= '1'; + wait for 20 ps; + end process; +end behav; diff --git a/vhdl_digital_design/ex2/Makefile b/vhdl_digital_design/ex2/Makefile @@ -0,0 +1 @@ +include ../Makefile diff --git a/vhdl_digital_design/ex2/ff.vhd b/vhdl_digital_design/ex2/ff.vhd @@ -0,0 +1,15 @@ +entity ff is port ( + d: in bit; + clk: in bit; + q: out bit +); +end ff; + +architecture behav of ff is +begin + process (clk) begin + if (clk 'event and clk = '1') then + q <= d; + end if; + end process; +end behav; diff --git a/vhdl_digital_design/ex2/ff_tb.vhd b/vhdl_digital_design/ex2/ff_tb.vhd @@ -0,0 +1,53 @@ +entity ff_tb is +end ff_tb; + +architecture behav of ff_tb is + +signal d1: bit; +signal clk1: bit; +signal q1: bit; + +component ff is port ( + d: in bit; + clk: in bit; + q: out bit +); +end component; + +begin + uut: ff port map ( + d => d1, + clk => clk1, + q => q1 + ); + + process begin + clk1 <= '1'; + wait for 150 ns; + clk1 <= '0'; + wait for 250 ns; + clk1 <= '1'; + wait for 150 ns; + clk1 <= '0'; + wait for 250 ns; + clk1 <= '1'; + wait for 150 ns; + clk1 <= '0'; + wait for 250 ns; + end process; + + process begin + d1 <= '1'; + wait for 280 ns; + d1 <= '0'; + wait for 300 ns; + d1 <= '1'; + wait for 250 ns; + d1 <= '0'; + wait for 150 ns; + d1 <= '1'; + wait for 75 ns; + d1 <= '0'; + wait for 150 ns; + end process; +end behav; diff --git a/vhdl_digital_design/ex2/ffrst.vhd b/vhdl_digital_design/ex2/ffrst.vhd @@ -0,0 +1,18 @@ +entity ffrst is port ( + d: in bit; + clk: in bit; + rst: in bit; + q: out bit +); +end ffrst; + +architecture behav of ffrst is +begin + process (clk, rst) begin + if (rst = '0') then + q <= '0'; + elsif (clk 'event and clk = '1') then + q <= d; + end if; + end process; +end behav; diff --git a/vhdl_digital_design/ex2/ffrst_tb.vhd b/vhdl_digital_design/ex2/ffrst_tb.vhd @@ -0,0 +1,59 @@ +entity ffrst_tb is +end ffrst_tb; + +architecture behav of ffrst_tb is + +signal d1: bit; +signal clk1: bit; +signal rst1: bit; +signal q1: bit; + +component ffrst is port ( + d: in bit; + clk: in bit; + rst: in bit; + q: out bit +); +end component; + +begin + uut: ffrst port map ( + d => d1, + clk => clk1, + rst => rst1, + q => q1 + ); + + process begin + rst1 <= '1'; + clk1 <= '1'; + wait for 150 ns; + clk1 <= '0'; + wait for 250 ns; + rst1 <= '0'; -- reset now is 0 so q is always 0 now + clk1 <= '1'; + wait for 150 ns; + clk1 <= '0'; + wait for 250 ns; + rst1 <= '1'; + clk1 <= '1'; + wait for 150 ns; + clk1 <= '0'; + wait for 250 ns; + end process; + + process begin + d1 <= '1'; + wait for 280 ns; + d1 <= '0'; + wait for 300 ns; + d1 <= '1'; + wait for 250 ns; + d1 <= '0'; + wait for 150 ns; + d1 <= '1'; + wait for 75 ns; + d1 <= '0'; + wait for 150 ns; + end process; +end behav; diff --git a/vhdl_digital_design/ex2/latch.vhd b/vhdl_digital_design/ex2/latch.vhd @@ -0,0 +1,15 @@ +entity latch is port ( + d: in bit; + en: in bit; + q: out bit +); +end latch; + +architecture behav of latch is +begin + process (d, en) begin + if (en = '1') then + q <= d; + end if; + end process; +end behav; diff --git a/vhdl_digital_design/ex2/latch_tb.vhd b/vhdl_digital_design/ex2/latch_tb.vhd @@ -0,0 +1,53 @@ +entity latch_tb is +end latch_tb; + +architecture behav of latch_tb is + +signal d1: bit; +signal en1: bit; +signal q1: bit; + +component latch is port ( + d: in bit; + en: in bit; + q: out bit +); +end component; + +begin + uut: latch port map ( + d => d1, + en => en1, + q => q1 + ); + + process begin + en1 <= '1'; + wait for 150 ns; + en1 <= '0'; + wait for 250 ns; + en1 <= '1'; + wait for 150 ns; + en1 <= '0'; + wait for 250 ns; + en1 <= '1'; + wait for 150 ns; + en1 <= '0'; + wait for 250 ns; + end process; + + process begin + d1 <= '1'; + wait for 280 ns; + d1 <= '0'; + wait for 300 ns; + d1 <= '1'; + wait for 250 ns; + d1 <= '0'; + wait for 150 ns; + d1 <= '1'; + wait for 75 ns; + d1 <= '0'; + wait for 150 ns; + end process; +end behav; diff --git a/vhdl_digital_design/ex2/reg.vhd b/vhdl_digital_design/ex2/reg.vhd @@ -0,0 +1,22 @@ +entity reg is port ( + d: in bit_vector(3 downto 0); + clk: in bit; + clr: in bit; + q: out bit_vector(3 downto 0) +); +end reg; + +architecture struct of reg is +component ffrst is port ( + d: in bit; + clk: in bit; + rst: in bit; + q: out bit +); +end component; + +begin + u: for i in 0 to 3 generate + f: ffrst port map (d(i), clk, clr, q(i)); + end generate; +end struct; diff --git a/vhdl_digital_design/ex2/reg_tb.vhd b/vhdl_digital_design/ex2/reg_tb.vhd @@ -0,0 +1,48 @@ +entity reg_tb is +end reg_tb; + +architecture behav of reg_tb is + +signal d1: bit_vector(3 downto 0); +signal clk1: bit; +signal clr1: bit; +signal q1: bit_vector(3 downto 0); + +component reg is port ( + d: in bit_vector(3 downto 0); + clk: in bit; + clr: in bit; + q: out bit_vector(3 downto 0) +); +end component; + +begin + uut: reg port map ( + d => d1, + clk => clk1, + clr => clr1, + q => q1 + ); + + process begin + clr1 <= '0'; + clk1 <= '0'; + d1 <= "0001"; + wait for 250 ns; + + clr1 <= '1'; + clk1 <= '1'; + d1 <= "0001"; + wait for 250 ns; + + clr1 <= '1'; + clk1 <= '0'; + d1 <= "0011"; + wait for 250 ns; + + clr1 <= '1'; + clk1 <= '1'; + d1 <= "0101"; + wait for 250 ns; + end process; +end behav;+ \ No newline at end of file diff --git a/vhdl_digital_design/ex2/shift4.vhd b/vhdl_digital_design/ex2/shift4.vhd @@ -0,0 +1,32 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity shift4 is port ( + d: in std_logic_vector(3 downto 0); + en: in std_logic; + load: in std_logic; + sin: in std_logic; + clk: in std_logic; + q: out std_logic_vector(3 downto 0) +); +end shift4; + +architecture behav of shift4 is + +signal qq: std_logic_vector(3 downto 0); + +begin + process (clk) begin + if (rising_edge(clk)) then + if (load = '1') then + q <= d; + elsif (en = '1') then + qq(0) <= qq(1); + qq(1) <= qq(2); + qq(2) <= qq(3); + qq(3) <= sin; + end if; + end if; + end process; + q <= qq; +end behav; diff --git a/vhdl_digital_design/ex2/shiftn.vhd b/vhdl_digital_design/ex2/shiftn.vhd @@ -0,0 +1,34 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity shiftn is + generic (n: integer := 8); + port ( + d: in std_logic_vector(n - 1 downto 0); + en: in std_logic; + load: in std_logic; + sin: in std_logic; + clk: in std_logic; + q: out std_logic_vector(n - 1 downto 0) +); +end shiftn; + +architecture behav of shiftn is + +signal qq: std_logic_vector(n - 1 downto 0); + +begin + process (clk) begin + if (rising_edge(clk)) then + if (load = '1') then + q <= d; + elsif (en = '1') then + u: for i in 0 to n - 2 loop + qq(i) <= qq(i + 1); + end loop; + qq(n - 1) <= sin; + end if; + end if; + end process; + q <= qq; +end behav;+ \ No newline at end of file diff --git a/vhdl_digital_design/ex2/upcount.vhd b/vhdl_digital_design/ex2/upcount.vhd @@ -0,0 +1,22 @@ +library ieee; +use ieee.std_logic_1164.all; +use ieee.std_logic_arith.all; +use ieee.std_logic_unsigned.all; + +entity upcount is port ( + clk: in std_logic; + rst: in std_logic; + q: inout std_logic_vector(1 downto 0) +); +end upcount; + +architecture behav of upcount is +begin + process (clk, rst) begin + if (rst = '1') then + q <= "00"; + elsif (rising_edge(clk)) then + q <= q + 1; + end if; + end process; +end behav; diff --git a/vhdl_digital_design/ex2/upcount_tb.vhd b/vhdl_digital_design/ex2/upcount_tb.vhd @@ -0,0 +1,35 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity upcount_tb is +end upcount_tb; + +architecture behav of upcount_tb is + +signal clk1: std_logic := '1'; +signal rst1: std_logic := '1'; +signal q1: std_logic_vector(1 downto 0); + +component upcount is port ( + clk: in std_logic; + rst: in std_logic; + q: inout std_logic_vector(1 downto 0) +); +end component; + +begin + uut: upcount port map ( + clk => clk1, + rst => rst1, + q => q1 + ); + + process begin + rst1 <= '0'; + clk1 <= '0'; + wait for 250 ns; + + clk1 <= '1'; + wait for 250 ns; + end process; +end behav; diff --git a/vhdl_digital_design/ex3/Makefile b/vhdl_digital_design/ex3/Makefile @@ -0,0 +1 @@ +include ../Makefile diff --git a/vhdl_digital_design/ex3/regfile.vhd b/vhdl_digital_design/ex3/regfile.vhd @@ -0,0 +1,35 @@ +library ieee; +use ieee.std_logic_1164.all; +use ieee.std_logic_unsigned.all; +use ieee.numeric_std.all; + +entity regfile is +generic ( + dw: natural := 4; + sz: natural := 4; + addrw: natural := 2 +); +port ( + a: in std_logic_vector(dw-1 downto 0); + addr: in std_logic_vector(addrw-1 downto 0); + we: in std_logic; + clk: in std_logic; + c: out std_logic_vector(dw-1 downto 0) +); +end regfile; + +architecture behav of regfile is + +type regarr is array(sz-1 downto 0) of std_logic_vector(dw-1 downto 0); +signal regf: regarr; + +begin + process (clk) begin + if (falling_edge(clk)) then + if (we = '1') then + regf(to_integer(unsigned(addr))) <= a; + end if; + end if; + end process; + c <= regf(to_integer(unsigned(addr))); +end behav; diff --git a/vhdl_digital_design/ex3/regfile_ext.vhd b/vhdl_digital_design/ex3/regfile_ext.vhd @@ -0,0 +1,45 @@ +library ieee; +use ieee.std_logic_1164.all; +use ieee.std_logic_unsigned.all; +use ieee.numeric_std.all; + +entity regfile_ext is +generic ( + dw: natural := 4; + sz: natural := 4; + addrw: natural := 2 +); +port ( + a: in std_logic_vector(dw-1 downto 0); + raddr1: in std_logic_vector(addrw-1 downto 0); + raddr2: in std_logic_vector(addrw-1 downto 0); + waddr: in std_logic_vector(addrw-1 downto 0); + we: in std_logic; + clk: in std_logic; + rst: in std_logic; + b: out std_logic_vector(dw-1 downto 0); + c: out std_logic_vector(dw-1 downto 0) +); +end regfile_ext; + +architecture behav of regfile_ext is + +type regarr is array(sz-1 downto 0) of std_logic_vector(dw-1 downto 0); +signal regf: regarr; + +begin + process (clk) begin + if (rst = '1') then + regf(0) <= "0000"; + regf(1) <= "0000"; + regf(2) <= "0000"; + regf(3) <= "0000"; + elsif (falling_edge(clk)) then + if (we = '1') then + regf(to_integer(unsigned(waddr))) <= a; + end if; + end if; + end process; + b <= regf(to_integer(unsigned(raddr1))); + c <= regf(to_integer(unsigned(raddr2))); +end behav; diff --git a/vhdl_digital_design/ex3/regfile_ext_tb.vhd b/vhdl_digital_design/ex3/regfile_ext_tb.vhd @@ -0,0 +1,111 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity regfile_ext_tb is +end regfile_ext_tb; + +architecture behav of regfile_ext_tb is + +component regfile_ext is +generic ( + dw: natural := 4; + sz: natural := 4; + addrw: natural := 2 +); +port ( + a: in std_logic_vector(dw-1 downto 0); + raddr1: in std_logic_vector(addrw-1 downto 0); + raddr2: in std_logic_vector(addrw-1 downto 0); + waddr: in std_logic_vector(addrw-1 downto 0); + we: in std_logic; + clk: in std_logic; + rst: in std_logic; + b: out std_logic_vector(dw-1 downto 0); + c: out std_logic_vector(dw-1 downto 0) +); +end component; + +signal s_dw: natural := 4; +signal s_sz: natural := 4; +signal s_addrw: natural := 2; +signal s_a: std_logic_vector(s_dw-1 downto 0); +signal s_raddr1:std_logic_vector(s_addrw-1 downto 0); +signal s_raddr2:std_logic_vector(s_addrw-1 downto 0); +signal s_waddr: std_logic_vector(s_addrw-1 downto 0); +signal s_we: std_logic; +signal s_clk: std_logic; +signal s_rst: std_logic; +signal s_b: std_logic_vector(s_dw-1 downto 0); +signal s_c: std_logic_vector(s_dw-1 downto 0); + +begin + uut: regfile_ext port map ( + a => s_a, + raddr1 => s_raddr1, + raddr2 => s_raddr2, + waddr => s_waddr, + we => s_we, + clk => s_clk, + rst => s_rst, + b => s_b, + c => s_c + ); + + process begin + s_we <= '1'; + s_clk <= '1'; + s_rst <= '1'; + wait for 250 ns; + + s_we <= '1'; + s_clk <= '0'; + s_rst <= '0'; + s_raddr1 <= "00"; + s_raddr2 <= "00"; + s_waddr <= "00"; + s_a <= "0101"; + wait for 250 ns; + + s_we <= '1'; + s_clk <= '1'; + s_rst <= '1'; + wait for 250 ns; + + s_we <= '1'; + s_clk <= '0'; + s_rst <= '0'; + s_raddr1 <= "01"; + s_raddr2 <= "01"; + s_waddr <= "01"; + s_a <= "1010"; + wait for 250 ns; + + s_we <= '1'; + s_clk <= '1'; + s_rst <= '1'; + wait for 250 ns; + + s_we <= '1'; + s_clk <= '0'; + s_rst <= '0'; + s_raddr1 <= "10"; + s_raddr2 <= "10"; + s_waddr <= "10"; + s_a <= "0000"; + wait for 250 ns; + + s_we <= '1'; + s_clk <= '1'; + s_rst <= '1'; + wait for 250 ns; + + s_we <= '1'; + s_clk <= '0'; + s_rst <= '0'; + s_raddr1 <= "11"; + s_raddr2 <= "11"; + s_waddr <= "11"; + s_a <= "1111"; + wait for 250 ns; + end process; +end behav; diff --git a/vhdl_digital_design/ex3/regfile_tb.vhd b/vhdl_digital_design/ex3/regfile_tb.vhd @@ -0,0 +1,83 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity regfile_tb is +end regfile_tb; + +architecture behav of regfile_tb is + +component regfile is +generic ( + dw: natural := 4; + sz: natural := 4; + addrw: natural := 2 +); +port ( + a: in std_logic_vector(dw-1 downto 0); + addr: in std_logic_vector(addrw-1 downto 0); + we: in std_logic; + clk: in std_logic; + c: out std_logic_vector(dw-1 downto 0) +); +end component; + +signal s_dw: natural := 4; +signal s_sz: natural := 4; +signal s_addrw: natural := 2; +signal s_a: std_logic_vector(s_dw-1 downto 0); +signal s_addr: std_logic_vector(s_addrw-1 downto 0); +signal s_we: std_logic; +signal s_clk: std_logic; +signal s_c: std_logic_vector(s_dw-1 downto 0); + +begin + uut: regfile port map ( + a => s_a, + addr => s_addr, + we => s_we, + clk => s_clk, + c => s_c + ); + + process begin + s_we <= '1'; + s_clk <= '1'; + wait for 250 ns; + + s_we <= '1'; + s_clk <= '0'; + s_addr <= "00"; + s_a <= "0101"; + wait for 250 ns; + + s_we <= '1'; + s_clk <= '1'; + wait for 250 ns; + + s_we <= '1'; + s_clk <= '0'; + s_addr <= "01"; + s_a <= "1101"; + wait for 250 ns; + + s_we <= '1'; + s_clk <= '1'; + wait for 250 ns; + + s_we <= '1'; + s_clk <= '0'; + s_addr <= "10"; + s_a <= "0010"; + wait for 250 ns; + + s_we <= '1'; + s_clk <= '1'; + wait for 250 ns; + + s_we <= '1'; + s_clk <= '0'; + s_addr <= "11"; + s_a <= "1001"; + wait for 250 ns; + end process; +end behav; diff --git a/vhdl_digital_design/ex4/Makefile b/vhdl_digital_design/ex4/Makefile @@ -0,0 +1 @@ +include ../Makefile diff --git a/vhdl_digital_design/ex4/alu4.vhd b/vhdl_digital_design/ex4/alu4.vhd @@ -0,0 +1,37 @@ +library ieee; +use ieee.std_logic_1164.all; +use ieee.numeric_std.all; + +entity alu4 is port ( + alu_in1: in std_logic_vector(3 downto 0); + alu_in2: in std_logic_vector(3 downto 0); + alu_ctrl: in std_logic_vector(3 downto 0); + alu_out: out std_logic_vector(3 downto 0); + alu_zero: out std_logic +); +end alu4; + +architecture behav of alu4 is +signal sig: std_logic_vector(3 downto 0); + +begin + process (alu_ctrl) begin + case alu_ctrl is + when "0000" => sig <= alu_in1 and alu_in2; + when "0001" => sig <= alu_in1 or alu_in2; + when "0010" => + sig <= std_logic_vector(signed(alu_in1) + signed(alu_in2)); + when "0110" => + sig <= std_logic_vector(signed(alu_in1) - signed(alu_in2)); + when "0111" => + if (alu_in1 < alu_in2) then + sig <= "0001"; + else + sig <= "0000"; + end if; + when others => sig <= (others => 'X'); + end case; + end process; + alu_zero <= '1' when sig = "0000" else '0'; + alu_out <= sig; +end behav; diff --git a/vhdl_digital_design/ex4/alu4_tb.vhd b/vhdl_digital_design/ex4/alu4_tb.vhd @@ -0,0 +1,63 @@ +library ieee; +use ieee.std_logic_1164.all; + +entity alu4_tb is +end alu4_tb; + +architecture behav of alu4_tb is +component alu4 is port ( + alu_in1: in std_logic_vector(3 downto 0); + alu_in2: in std_logic_vector(3 downto 0); + alu_ctrl: in std_logic_vector(3 downto 0); + alu_out: out std_logic_vector(3 downto 0); + alu_zero: out std_logic +); +end component; + +signal s_alu_in1: std_logic_vector(3 downto 0); +signal s_alu_in2: std_logic_vector(3 downto 0); +signal s_alu_ctrl: std_logic_vector(3 downto 0); +signal s_alu_out: std_logic_vector(3 downto 0); +signal s_alu_zero: std_logic; + +begin + uut: alu4 port map ( + alu_in1 => s_alu_in1, + alu_in2 => s_alu_in2, + alu_ctrl => s_alu_ctrl, + alu_out => s_alu_out, + alu_zero => s_alu_zero + ); + + process begin + s_alu_in1 <= "0010"; + s_alu_in2 <= "0100"; + s_alu_ctrl <= "0010"; + wait for 250 ns; + + s_alu_in1 <= "0100"; + s_alu_in2 <= "1111"; + s_alu_ctrl <= "0000"; + wait for 250 ns; + + s_alu_in1 <= "0100"; + s_alu_in2 <= "1111"; + s_alu_ctrl <= "0001"; + wait for 250 ns; + + s_alu_in1 <= "0100"; + s_alu_in2 <= "0010"; + s_alu_ctrl <= "0110"; + wait for 250 ns; + + s_alu_in1 <= "0100"; + s_alu_in2 <= "0110"; + s_alu_ctrl <= "0110"; + wait for 250 ns; + + s_alu_in1 <= "0100"; + s_alu_in2 <= "0110"; + s_alu_ctrl <= "0111"; + wait for 250 ns; + end process; +end behav;+ \ No newline at end of file