Compare commits

...

15 Commits

Author SHA1 Message Date
Pradana Aumars 397cdf5293 Fix test_exception_init 2021-06-12 11:07:40 +02:00
Pradana Aumars f5230ae3d5 Exception strings include msg from type and custom msg 2021-06-12 11:04:02 +02:00
Pradana Aumars fce41edbe5 Add FILEPATH_HOME 2021-06-12 11:02:56 +02:00
Pradana Aumars fc0f657774 Fix conf_verify_key 2021-06-12 11:01:50 +02:00
Pradana Aumars d15c8a688e Add CPPFLAGS to testing suite 2021-06-12 11:01:11 +02:00
Pradana Aumars a72786a38f Remove install.c CPP file 2021-06-12 10:57:08 +02:00
Pradana Aumars 24ac0e4897 Add test for calibrate.replace_text 2021-06-03 00:34:12 +02:00
Pradana Aumars f9f8ce747a Add absolute paths to file_t 2021-06-03 00:33:26 +02:00
Pradana Aumars 0794691f5a Update check_file_t to correctly check exception 2021-06-02 12:05:00 +02:00
Pradana Aumars 72f71d4e2b Add exception_t.exception_null to check if no exception 2021-06-02 12:04:36 +02:00
Pradana Aumars 84cf1b0818 Compartmentisation of tests, add testing of exception_t 2021-06-02 11:50:58 +02:00
Pradana Aumars 208cb375e1 Add exception_init and exception_free 2021-06-01 00:58:30 +02:00
Pradana Aumars ea37ce1732 Fix hash and hash_str
* file_t.hash is now a buffer and not a pointer
* add exception checking to file_t_md5_gen
2021-06-01 00:08:30 +02:00
Pradana Aumars a6227b8481 Add exception flag MD5SUM_GEN_FAIL 2021-06-01 00:07:32 +02:00
Pradana Aumars 8f72eabf1f Fix test check_file_t.file_init
* Add filepath_t enum key
* file_init writes path according to filepath_t
* file_init does NOT correctly write path FILEPATH_ABSOLUTE
* file_init parameters changed to include filepath_t and no longer includes "ENV" string
* file_close only now frees hash_str when non null ptr
* calibrate verify function updated to use correct file_init parameters
2021-05-31 22:07:06 +02:00
14 changed files with 258 additions and 128 deletions

View File

@ -1,11 +1,22 @@
bin_PROGRAMS = modetw
lib_LTLIBRARIES = libfile_t.la
lib_LTLIBRARIES = libmodetw.la
modetw_SOURCES = main.c calibrate.c exception_t.c file_t.c conf.c
modetw_CPPFLAGS = $(XML_CPPFLAGS)
modetw_CFLAGS = $(GLIB_CFLAGS)
modetw_LDFLAGS= $(XML_LIBS) $(GLIB_LIBS)
CFILES = \
exception_t.c \
file_t.c \
calibrate.c \
conf.c
HFILES = \
exception_t.h \
file_t.h \
calibrate.h \
conf.h
libfile_t_la_SOURCES = file_t.c file_t.h
modetw_SOURCES = main.c
modetw_LDADD = libmodetw.la
libmodetw_la_SOURCES = $(CFILES) $(HFILES)
libmodetw_la_CPPFLAGS = $(XML_CPPFLAGS)
libmodetw_la_CFLAGS = $(GLIB_CFLAGS)
libmodetw_la_LDFLAGS= $(XML_LIBS) $(GLIB_LIBS)
modetw_LDADD = libfile_t.la

View File

@ -192,7 +192,7 @@ verify(exception_t *e)
file_t *f;
xmlNode *x_name = b_node->children;
xmlNode *x_sum = x_name->next;
f = file_init((char*) x_name->content, e, "HOME");
f = file_init((char*) x_name->content, FILEPATH_ABSOLUTE, e);
if (strcmp(f->hash_str, (char*) x_sum->content) != 0)
{
e->type = MD5SUM_VERIFY_FAIL;
@ -253,7 +253,7 @@ edit(exception_t *e)
strcat(fullpath, x_group_type);
strcat(fullpath, "/");
strcat(fullpath, x_path);
f = file_init(&fullpath, e, "HOME");
f = file_init(&fullpath, FILEPATH_ABSOLUTE, e);
replace_text(f, x_before, x_after, x_type, e);
file_close(f);
}

View File

@ -13,22 +13,22 @@ conf_verify_key(const char *f, const char *key, char *value)
if (!g_key_file_load_from_file (key_file, f, G_KEY_FILE_NONE, &error))
{
if (!g_error_matches (error, G_FILE_ERROR, G_FILE_ERROR_NOENT))
if (g_error_matches (error, G_FILE_ERROR, G_FILE_ERROR_NOENT))
g_warning ("Error loading key file: %s\n", error->message);
return 1;
}
value = g_key_file_get_string (key_file, "Global", key, &error);
if (value == NULL &&
!g_error_matches (error, G_KEY_FILE_ERROR, G_KEY_FILE_ERROR_KEY_NOT_FOUND))
g_error_matches (error, G_KEY_FILE_ERROR, G_KEY_FILE_ERROR_KEY_NOT_FOUND))
{
g_warning ("Error finding key in key file: %s\n", error->message);
return 1;
}
else if (value == NULL)
{
g_warning ("Error finding game directory.\n");
g_warning ("Error: %s.\n", error->message);
return 1;
}
return 1;
return 0;
}

View File

@ -1 +1,44 @@
#include <stdlib.h>
#include <string.h>
#include <limits.h>
#include <stdio.h>
#include "exception_t.h"
exception_t*
exception_init() {
exception_t *e = (exception_t*) malloc(sizeof(exception_t));
e->type = NO_ERROR;
e->msg = malloc(CHAR_MAX);
return e;
}
void
exception_free(exception_t *e) {
free(e->msg);
free(e);
}
int
exception_null(const exception_t *e) {
return e->type == NO_ERROR;
}
char*
exception_prestr(const exception_t *e) {
switch(e->type) {
case NO_ERROR: return "No error\n";
case NO_FILE: return "No file found";
case XML_FILE_MISSING: return "XML file missing";
case XML_READ_FILE_FAIL: return "XML file reading failed";
case MD5SUM_GEN_FAIL: return "MD5sum generation failed";
case MD5SUM_VERIFY_FAIL: return "MD5sum verification failed";
}
}
char*
exception_str(const exception_t *e, char* msg) {
if (e->type != NO_ERROR) sprintf(msg, "%s: %s\n", exception_prestr(e), e->msg);
else sprintf(msg, "%s\n", exception_prestr(e));
return msg;
}

View File

@ -6,6 +6,7 @@ typedef enum exception_type {
NO_FILE,
XML_FILE_MISSING,
XML_READ_FILE_FAIL,
MD5SUM_GEN_FAIL,
MD5SUM_VERIFY_FAIL
} exception_type;
@ -14,7 +15,16 @@ typedef struct exception_t {
char *msg;
} exception_t;
exception_t*
exception_init();
void
exception_free(exception_t *e);
int
exception_null(const exception_t *e);
char*
exception_str(exception_t *e);
exception_str(const exception_t *e, char* msg);
#endif

View File

@ -1,13 +1,11 @@
#include <stdlib.h>
#include <string.h>
#include <sys/stat.h>
#include <openssl/md5.h> /* md5sum */
#include <fcntl.h>
#include <sys/mman.h>
#include <errno.h>
#include <unistd.h>
#include <limits.h>
#include <glib.h>
#include "file_t.h"
@ -28,49 +26,50 @@ get_size_by_fd(int fd)
}
file_t*
file_init(const char *filename, exception_t *e, const char *env)
file_init(const char *filename, filepath_t FILEPATH, exception_t *e)
{
GString *abspath = g_string_new (NULL);
if (env != NULL)
{
char *envpath;
size_t sizehome, sizepath;
envpath = getenv (env);
sizehome = strlen(envpath);
sizepath = strlen(filename);
abspath = malloc(sizehome + sizepath + 2);
strcpy (abspath, envpath);
strcat (abspath, "/");
strcat (abspath, filename);
abspath[sizehome + sizepath + 2] = '\0';
}
else
{
abspath = filename;
}
char *path = NULL;
switch (FILEPATH) {
case FILEPATH_ABSOLUTE: {
realpath(filename, path);
break;
}
case FILEPATH_HOME: {
char* home = getenv("HOME");
size_t pathlen = strlen(home) + strlen(filename);
path = malloc(pathlen + 1);
strcpy(home, path);
strcat(path, filename);
path[pathlen] = '\0';
}
case FILEPATH_RELATIVE: path = (char*) filename; break;
}
/* Checks if the file path can be opened. */
if (open(abspath, O_RDONLY) < 0)
if (open(path, O_RDONLY) < 0)
{
e->type = NO_FILE;
e->msg = abspath;
e->msg = path;
return NULL;
}
file_t *f;
f = malloc(sizeof(file_t*));
f->name = (char*) abspath;
f->hash = NULL;
f = malloc(sizeof(file_t));
f->name = path;
f->hash_str = NULL;
f->fp = FILEPATH;
return f;
}
void
file_close(file_t *f)
{
free(f->name);
free(f->hash);
free(f->hash_str);
switch (f->fp) {
case FILEPATH_ABSOLUTE:
case FILEPATH_HOME: free(f->name);
default: break;
}
if (f->hash_str != NULL) free(f->hash_str);
free(f);
}
@ -90,11 +89,14 @@ file_md5_gen(file_t *f, exception_t *e)
file_buffer = (unsigned char*) mmap(0, file_size, PROT_READ, MAP_SHARED, file_descript, 0);
/* Computes the MD5 checksum to result */
MD5(file_buffer, file_size, f->hash);
if (MD5(file_buffer, file_size, f->hash) == NULL) {
e->type = MD5SUM_GEN_FAIL;
e->msg = "No hash!";
}
/* Removes fime_buffer and file_size */
munmap(file_buffer, file_size);
return f->hash;
}
@ -102,14 +104,27 @@ char*
file_md5_str(file_t *f, exception_t *e)
{
static const char digits[] = "0123456789abcdef";
f->hash_str = malloc (MD5_DIGEST_LENGTH+1);
for (size_t i = 0; i < MD5_DIGEST_LENGTH; i+=2)
f->hash_str = malloc (2*MD5_DIGEST_LENGTH+1);
size_t si = 0;
for (size_t i = si; i < MD5_DIGEST_LENGTH; i++)
{
f->hash_str[i] += digits[f->hash[i] / MD5_DIGEST_LENGTH];
f->hash_str[i+1] += digits[f->hash[i+1] % MD5_DIGEST_LENGTH];
f->hash_str[si++] = digits[f->hash[i] / MD5_DIGEST_LENGTH];
f->hash_str[si++] = digits[f->hash[i] % MD5_DIGEST_LENGTH];
}
f->hash_str[MD5_DIGEST_LENGTH] = '\0';
f->hash_str[2*MD5_DIGEST_LENGTH] = '\0';
return f->hash_str;
}
char*
file_abs(const file_t *f) {
char *path = NULL;
switch (f->fp) {
case FILEPATH_ABSOLUTE: return f->name;
case FILEPATH_RELATIVE: {
realpath(f->name, path);
break;
}
}
return path;
}

View File

@ -1,15 +1,24 @@
#ifndef FILE_T_H
#define FILE_T_H
#include <openssl/md5.h> /* md5sum */
#include "exception_t.h"
typedef enum filepath_t {
FILEPATH_ABSOLUTE,
FILEPATH_RELATIVE,
FILEPATH_HOME
} filepath_t;
/**
* Wrapper to file
*/
typedef struct file_t {
char *name; /**< Absolute path to file */
unsigned char *hash; /**< MD5sum hash */
unsigned char hash[MD5_DIGEST_LENGTH]; /**< MD5sum hash */
char *hash_str; /**< MD5sum hash as char* */
filepath_t fp;
} file_t;
/**
@ -20,7 +29,7 @@ typedef struct file_t {
* @return Pointer to file_t
*/
file_t*
file_init(const char *filename, exception_t *e, const char *env);
file_init(const char *filename, filepath_t FILEPATH, exception_t *e);
/**
* Destroy file_t
@ -44,4 +53,7 @@ file_md5_gen(file_t *f, exception_t *e);
char*
file_md5_str(file_t *f, exception_t *e);
char*
file_abs(const file_t *f);
#endif

View File

@ -1,39 +0,0 @@
#include "install.h"
int
backup()
{
struct stat sb;
const std::string bkp = hd + _prefix + "_backup/";
struct stat stat_dir;
if (stat(bkp.c_str(), &stat_dir) != 0)
{
mkdir(bkp.c_str(), 0700);
}
for (auto &i : _vec)
{
const std::string source_file = hd + _prefix + "/" + i;
const std::string dest_file = bkp + i;
std::cout << "Backing up " << _prefix << "/" << i << "\n";
int source = open(source_file.c_str(), O_RDONLY, 0);
int dest = open(dest_file.c_str(), O_WRONLY | O_CREAT /*| O_TRUNC/**/, 0644);
// struct required, rationale: function stat() exists also
struct stat stat_source;
fstat(source, &stat_source);
sendfile(dest, source, 0, stat_source.st_size);
close(source);
close(dest);
if (access(dest_file.c_str(), F_OK) != 0)
{
throw ExceptionHandler(CUSTOM_ERROR, "Backing up " + dest_file + " failed!");
}
}
}

View File

@ -1,5 +1,15 @@
TESTS = check_file_t
check_PROGRAMS = check_file_t
check_file_t_SOURCES = check_file_t.c $(top_builddir)/src/file_t.h
check_file_t_CFLAGS= $(CFLAGS) $(CHECK_CFLAGS)
check_file_t_LDADD = $(top_builddir)/src/libfile_t.la $(LDFLAGS) $(CHECK_LIBS)
TESTS = \
check_check
noinst_PROGRAMS = \
check_check
check_check_SOURCES = \
check_check.c \
check_file_t.c \
check_exception_t.c \
check_calibrate.c
check_check_CPPFLAGS= $(CPPFLAGS)
check_check_CFLAGS= $(CFLAGS) $(CHECK_CFLAGS)
check_check_LDFLAGS= $(LDFLAGS) $(CHECK_LIBS)
check_check_LDADD = $(top_builddir)/src/libmodetw.la

View File

@ -1,8 +1,36 @@
#include <stdlib.h>
#include <check.h>
#include "check_check.h"
#include "../src/calibrate.h"
#include "../src/file_t.h"
START_TEST(test_calibrate)
START_TEST(test_replace_text)
{
exception_t *e;
file_t *f;
e = exception_init();
f = file_init("samples/1.txt", FILEPATH_RELATIVE, e);
char *path = file_abs(f);
ck_assert(replace_text(path, "ABC", "123", "ASCII", e));
ck_assert(exception_null(e));
ck_assert(replace_text(path, "123", "ABC", "ASCII", e));
ck_assert(exception_null(e));
file_close(f);
exception_free(e);
free(path);
}
Suite*
calibrate_suite(void)
{
Suite *s;
TCase *tc_core;
s = suite_create ("calibrate");
tc_core = tcase_create ("core");
tcase_add_test(tc_core, test_replace_text);
suite_add_tcase(s, tc_core);
return s;
}

18
tests/check_check.c Normal file
View File

@ -0,0 +1,18 @@
#include <check.h>
#include "check_check.h"
int
main(void)
{
int number_failed;
SRunner *sr;
sr = srunner_create(file_t_suite());
srunner_add_suite(sr, exception_t_suite());
srunner_add_suite(sr, calibrate_suite());
srunner_run_all(sr, CK_VERBOSE);
number_failed = srunner_ntests_failed(sr);
srunner_free(sr);
return number_failed;
}

10
tests/check_check.h Normal file
View File

@ -0,0 +1,10 @@
#ifndef CHECK_CHECK_H
#define CHECK_CHECK_H
#include <check.h>
Suite* file_t_suite(void);
Suite* exception_t_suite(void);
Suite* calibrate_suite(void);
#endif

27
tests/check_exception_t.c Normal file
View File

@ -0,0 +1,27 @@
#include "check_check.h"
#include "../src/exception_t.h"
START_TEST(test_exception_init)
{
exception_t *e = NULL;
e = exception_init();
ck_assert_ptr_nonnull(e);
ck_assert_int_eq(e->type, NO_ERROR);
exception_free(e);
}
END_TEST
Suite*
exception_t_suite(void)
{
Suite *s;
TCase *tc_core;
s = suite_create ("exception_t");
tc_core = tcase_create ("core");
tcase_add_test(tc_core, test_exception_init);
suite_add_tcase(s, tc_core);
return s;
}

View File

@ -1,29 +1,30 @@
#include <check.h>
#include "check_check.h"
#include "../src/file_t.h"
START_TEST(test_file_init)
{
file_t *f;
exception_t *e = NULL;
f = file_init ("samples/1.txt", e, NULL);
ck_assert_ptr_ne (f, NULL);
ck_assert_ptr_eq (e, NULL);
exception_t *e = exception_init();
f = file_init ("samples/1.txt", FILEPATH_RELATIVE, e);
ck_assert_ptr_nonnull (f);
ck_assert (exception_null(e));
file_close (f);
exception_free(e);
}
END_TEST
START_TEST(test_file_md5)
{
file_t *f;
exception_t *e = NULL;
f = file_init("samples/1.txt", e, NULL);
exception_t *e = exception_init();
f = file_init("samples/1.txt", FILEPATH_RELATIVE, e);
file_md5_gen (f, e);
ck_assert_ptr_eq (e, NULL);
ck_assert (exception_null(e));
file_md5_str (f, e);
ck_assert_ptr_eq (e, NULL);
ck_assert (exception_null(e));
ck_assert_str_eq (f->hash_str, "492ff087b26577237c576e7ad409064e");
file_close (f);
exception_free(e);
}
Suite*
@ -41,19 +42,3 @@ file_t_suite(void)
return s;
}
int
main(void)
{
int number_failed;
Suite *s;
SRunner *sr;
s = file_t_suite();
sr = srunner_create(s);
srunner_run_all(sr, CK_VERBOSE);
number_failed = srunner_ntests_failed(sr);
srunner_free(sr);
return number_failed;
}