Compare commits

...

5 Commits

8 changed files with 172 additions and 27 deletions

View File

@ -5,8 +5,8 @@
# `make clean all` nicht mit -j verwenden! -> race condition im make file
# statdessen: `make clean; make all -j` verwenden
NAME = libmrbesen.so
NAMEINC = mrbesen
NAMESHORT = mrbesen
NAME = lib$(NAMESHORT).so
NAMETEST = test
CFLAGS = -fpic -std=c++17 -O2 -g -pipe -Wall -Wextra -Wno-unused-parameter -Wpedantic
CXX = g++
@ -15,6 +15,7 @@ BUILDDIR = build/
INCF = inc/
TESTF = tests/
DEPF = $(BUILDDIR)deps/
OUTF = ./
INCLUDES = -I$(INCF)
LDFLAGS =
@ -28,11 +29,11 @@ BUILDDIRS = $(patsubst $(SRCF)%, $(BUILDDIR)%, $(SOURCEDIRS))
INCLUDES += $(addprefix -I, $(SOURCEDIRS))
all: $(NAME) runtest
all: $(OUTF)$(NAME) runtest
$(NAME): $(BUILDDIRS) $(DEPF) $(OBJFILES)
$(OUTF)$(NAME): $(BUILDDIRS) $(DEPF) $(OBJFILES)
@echo "Linking $@"
@$(LD) -shared -o $@ $(filter %.o, $^)
@$(CXX) -shared -o $@ $(filter %.o, $^)
$(BUILDDIR)%.o: $(SRCF)%.cpp
@echo "Compiling: $@"
@ -46,24 +47,24 @@ clean-depends:
$(RM) -r $(DEPF)
clean:
$(RM) -r $(NAME) $(BUILDDIR) $(NAMETEST)
$(RM) -r $(OUTF)$(NAME) $(BUILDDIR) $(NAMETEST)
$(NAMETEST): $(NAME) $(TESTF)*.cpp
@echo "Compiling tests"
@$(CXX) -o $@ $(filter-out %.so, $^) $(CFLAGS) $(INCLUDES) $(LDFLAGS) -L./ -lmrbesen
@$(CXX) -o $@ $(filter-out %.so, $^) $(CFLAGS) $(INCLUDES) $(LDFLAGS) -L$(OUTF) -l$(NAMESHORT)
runtest: $(NAMETEST)
@echo "Running tests"
LD_LIBRARY_PATH=./:$(LD_LIBRARY_PATH) ./$<
LD_LIBRARY_PATH=$(OUTF):$(LD_LIBRARY_PATH) ./$<
install: $(NAME)
cp -f ./$(NAME) /usr/lib/
mkdir -p /usr/include/$(NAMEINC)/
cp -rf $(INCF)* /usr/include/$(NAMEINC)/
cp -rf $(INCF)* /usr/include/$(NAMESHORT)/
uninstall:
$(RM) -r /usr/lib/$(NAME) /usr/include/$(NAMEINC)/
$(RM) -r /usr/lib/$(NAME) /usr/include/$(NAMESHORT)/
.PHONY: clean all $(NAMETEST) clean-depends runtest install
.PHONY: clean all clean-depends runtest install uninstall
include $(DEPFILES)

View File

@ -1,5 +1,7 @@
#pragma once
#include <functional>
#include <iterator>
#include <string>
namespace mrbesen::Files {
@ -8,4 +10,22 @@ void parent(const std::string& child, std::string& out); //get the parent direct
void file(const std::string& path, std::string& out); //get the filename without the path
void extention(const std::string& path, std::string& ext); //get the files extenetion
enum class FileType : unsigned char {
UNKNOWN = 0,
FIFO = 1,
CHARACTER = 2,
DIRECTORY = 4,
BLOCK = 6,
REGULAR = 8,
LINK = 10,
SOCKET = 12,
WHT = 14 ///????
//copied from dirent.h -> see man readdir
};
typedef std::function<bool(const std::string&, FileType type)> fileNameFilter;
template<class Container>
bool scan(const std::string& path, std::insert_iterator<Container> it, bool prefixdir = false, fileNameFilter fnf = fileNameFilter(nullptr));
}

View File

@ -14,7 +14,12 @@ void toLower(std::string& in); //inplace toLower
bool endsWith(const std::string& str, const std::string& ending);
bool startsWith(const std::string& str, const std::string& start);
void removeEnd(std::string& str, const std::string& ending);
void removeStart(std::string& str, const std::string& start);
//makes sure a string does NOT ends or starts with a specific sub string
bool removeEnd(std::string& str, const std::string& ending); //returns true on change (ending = "" -> returns false)
bool removeStart(std::string& str, const std::string& start);
//makes sure a string DOES ends or starts with a specific sub string
bool insertEnd(std::string& str, const std::string& ending);
bool insertStart(std::string& str, const std::string& start);
}

View File

@ -1,5 +1,10 @@
#include "files.h"
#include <dirent.h>
#include <list>
#include <set>
#include "util.h"
void mrbesen::Files::parent(const std::string& child, std::string& out) {
//letzten path trenner finden
size_t pos = child.rfind('/', child.length() -2); //das erste Zeichen überspringen (könnte ein / sein)
@ -35,3 +40,40 @@ void mrbesen::Files::extention(const std::string& path, std::string& ext) {
ext = filestr.substr(pos+1);
}
template<class Container>
bool mrbesen::Files::scan(const std::string& path, std::insert_iterator<Container> it, bool prefixdir, fileNameFilter fnf) {
std::string path_ = path;
mrbesen::Util::insertEnd(path_, "/");
::DIR* dir = opendir(path_.c_str());
if(!dir) {
return false;
}
//read dir
struct ::dirent* entr;
while((entr = readdir(dir))) {
std::string fname = entr->d_name;
FileType type = (FileType) entr->d_type; //DT_BLK DT_CHR DT_DIR DT_FIFO DT_LNK DT_REG DT_SOCK DT_UNKNOWN (dirent.h, man readdir)
if(fnf) {
if(!fnf(fname, type)) {
continue;
}
}
if(prefixdir)
fname = path_ + fname;
it = fname;
}
closedir(dir);
return true;
}
//curently only these are supported, because iterators may break on others upon insertion
template bool mrbesen::Files::scan<std::list<std::string>>(const std::string&, std::insert_iterator<std::list<std::string>>, bool, fileNameFilter);
template bool mrbesen::Files::scan<std::set<std::string>>(const std::string&, std::insert_iterator<std::set<std::string>>, bool, fileNameFilter);
template bool mrbesen::Files::scan<std::multiset<std::string>>(const std::string&, std::insert_iterator<std::multiset<std::string>>, bool, fileNameFilter);

View File

@ -71,18 +71,41 @@ bool mrbesen::Util::startsWith(const std::string& str, const std::string& start)
return str.find(start) == 0;
}
void mrbesen::Util::removeEnd(std::string& str, const std::string& ending) {
if(ending.empty()) return;
bool mrbesen::Util::removeEnd(std::string& str, const std::string& ending) {
if(ending.empty()) return false;
if(endsWith(str, ending)) {
str.resize(str.size() - ending.length());
return true;
}
return false;
}
void mrbesen::Util::removeStart(std::string& str, const std::string& start) {
if(start.empty()) return;
bool mrbesen::Util::removeStart(std::string& str, const std::string& start) {
if(start.empty()) return false;
if(startsWith(str, start)) {
str = str.substr(start.length());
return true;
}
return false;
}
bool mrbesen::Util::insertEnd(std::string& str, const std::string& ending) {
if(ending.empty()) return false;
if(endsWith(str, ending)) return false;
str.append(ending);
return true;
}
bool mrbesen::Util::insertStart(std::string& str, const std::string& start) {
if(start.empty()) return false;
if(startsWith(str, start)) return false;
str = start + str;
return true;
}

View File

@ -1,6 +1,9 @@
#include "test.h"
#include "files.h"
#include "util.h"
#include <list>
#include <set>
#include <string>
using namespace mrbesen;
@ -99,3 +102,22 @@ int testFiles_extention() {
return TESTGOOD;
}
int testFiles_scan() {
std::string path = "./tests";
std::list<std::string> out, out2;
ASSERT(Files::scan(path, std::inserter(out, out.begin()), false), "");
ASSERT(Files::scan(path, std::inserter(out2, out2.begin()), true), "");
ASSERT(out.size() == out2.size(), out.size() << " " << out2.size());
std::set<std::string> out3;
ASSERT(Files::scan(path, std::inserter(out3, out3.begin()), false, [](const std::string& str, Files::FileType t){ return mrbesen::Util::startsWith(str, "."); }), "");
ASSERT(out3.size() == 2, out3.size());
ASSERT(out3.find(".") != out3.end(), "");
ASSERT(out3.find("..") != out3.end(), "");
return TESTGOOD;
}

View File

@ -5,14 +5,16 @@
int testFiles_parent();
int testFiles_file();
int testFiles_extention();
int testFiles_scan();
int testUtil_Count();
int testUtil_equalsIgnoreCase();
int testUtil_toLower();
int testUtil_start_endWith();
int testUtil_removeStart_End();
int testUtil_insertStart_End();
test_t tests[] = {testFiles_parent, testFiles_file, testFiles_extention, testUtil_Count, testUtil_equalsIgnoreCase, testUtil_toLower, testUtil_start_endWith, testUtil_removeStart_End, NULL};
test_t tests[] = {testFiles_parent, testFiles_file, testFiles_extention, testFiles_scan, testUtil_Count, testUtil_equalsIgnoreCase, testUtil_toLower, testUtil_start_endWith, testUtil_removeStart_End, testUtil_insertStart_End, NULL};
int main(int argc, char** argv) {
@ -21,7 +23,7 @@ int main(int argc, char** argv) {
int testcount = 0;
for(; *current; current++) {
testcount++;
printf("\033[1mRunning test number: %d ", testcount);
printf("\033[1mRunning test number: %02d ", testcount);
if((*current)()) {
printf("\033[1;92msucceeded\033[0;1m!\n");
} else {

View File

@ -92,29 +92,59 @@ int testUtil_start_endWith() {
int testUtil_removeStart_End() {
std::string a = "abcdefg";
removeStart(a, "");
ASSERT(!removeStart(a, ""), "");
ASSERT(a == "abcdefg", "");
removeStart(a, "b");
ASSERT(!removeStart(a, "b"), "");
ASSERT(a == "abcdefg", "");
removeStart(a, "a");
ASSERT(removeStart(a, "a"), "");
ASSERT(a == "bcdefg", "");
removeStart(a, "bcd");
ASSERT(removeStart(a, "bcd"), "");
ASSERT(a == "efg", "");
removeEnd(a, "xyz");
ASSERT(!removeEnd(a, "xyz"), "");
ASSERT(a == "efg", "");
removeEnd(a, "");
ASSERT(!removeEnd(a, ""), "");
ASSERT(a == "efg", "");
removeEnd(a, "fg");
ASSERT(removeEnd(a, "fg"), "");
ASSERT(a == "e", "");
removeEnd(a, "e");
ASSERT(removeEnd(a, "e"), "");
ASSERT(a == "", "");
return TESTGOOD;
}
int testUtil_insertStart_End() {
std::string a = "";
ASSERT(!insertStart(a, ""), "");
ASSERT(a == "", a);
ASSERT(insertStart(a, "abc"), "");
ASSERT(a == "abc", a);
ASSERT(!insertStart(a, "a"), "");
ASSERT(a == "abc", a);
ASSERT(insertStart(a, "bc"), "");
ASSERT(a == "bcabc", a);
ASSERT(!insertStart(a, ""), "");
ASSERT(a == "bcabc", a);
ASSERT(!insertEnd(a, ""), "");
ASSERT(a == "bcabc", a);
ASSERT(!insertEnd(a, "bc"), "");
ASSERT(a == "bcabc", a);
ASSERT(insertEnd(a, "def"), "");
ASSERT(a == "bcabcdef", a);
return TESTGOOD;
}