new: working on the gen command
This commit is contained in:
parent
0d00678c30
commit
e29c3ce419
@ -7,7 +7,7 @@ msgid ""
|
||||
msgstr ""
|
||||
"Project-Id-Version: PACKAGE VERSION\n"
|
||||
"Report-Msgid-Bugs-To: \n"
|
||||
"POT-Creation-Date: 2024-05-02 00:49+0300\n"
|
||||
"POT-Creation-Date: 2024-05-02 22:51+0300\n"
|
||||
"PO-Revision-Date: 2024-05-01 13:34+0300\n"
|
||||
"Last-Translator: <ngn@ngn.tf>\n"
|
||||
"Language-Team: Turkish <gnome-turk@gnome.org>\n"
|
||||
@ -17,45 +17,84 @@ msgstr ""
|
||||
"Content-Transfer-Encoding: 8bit\n"
|
||||
"Plural-Forms: nplurals=2; plural=(n != 1);\n"
|
||||
|
||||
#: src/config.c:13
|
||||
msgid "Configuration target is missing a name"
|
||||
msgstr ""
|
||||
|
||||
#: src/config.c:18
|
||||
#, c-format
|
||||
msgid "Configuration target \"%s\" does not have \"dst\" field"
|
||||
msgstr ""
|
||||
|
||||
#: src/config.c:23
|
||||
#, c-format
|
||||
msgid "Configuration target \"%s\" does not have \"src\" field"
|
||||
msgstr ""
|
||||
|
||||
#: src/config.c:32
|
||||
msgid "Configuration does not have a name field"
|
||||
msgstr ""
|
||||
|
||||
#: src/config.c:37
|
||||
#: src/config.c:28
|
||||
msgid "Configuration does not have an author field"
|
||||
msgstr ""
|
||||
|
||||
#: src/config.c:42
|
||||
#: src/config.c:33
|
||||
msgid "Configuration does not have any targets"
|
||||
msgstr ""
|
||||
|
||||
#: src/config.c:120
|
||||
#: src/config.c:91
|
||||
msgid "Configuration contains multiple targets with the same name"
|
||||
msgstr ""
|
||||
|
||||
#: src/config.c:113
|
||||
#, c-format
|
||||
msgid "Key %s is unknown"
|
||||
msgstr ""
|
||||
|
||||
#: src/config.c:156
|
||||
#: src/config.c:143
|
||||
msgid "Configuration file not found"
|
||||
msgstr ""
|
||||
|
||||
#: src/config.c:170
|
||||
#: src/config.c:158
|
||||
msgid "Failed to parse configuration file"
|
||||
msgstr ""
|
||||
|
||||
#: src/config.c:174
|
||||
msgid "Configuration details:\n"
|
||||
msgstr ""
|
||||
|
||||
#: src/config.c:175
|
||||
msgid "Name"
|
||||
msgstr ""
|
||||
|
||||
#: src/config.c:176
|
||||
msgid "Author"
|
||||
msgstr ""
|
||||
|
||||
#: src/config.c:178
|
||||
msgid "Keywords"
|
||||
msgstr ""
|
||||
|
||||
#: src/gen.c:15
|
||||
msgid "Please specify a directory for the repository"
|
||||
msgstr ""
|
||||
|
||||
#: src/gen.c:20
|
||||
msgid "Failed to access the directory"
|
||||
msgstr ""
|
||||
|
||||
#: src/gen.c:25
|
||||
msgid "Failed to change directory to the specified directory"
|
||||
msgstr ""
|
||||
|
||||
#: src/gen.c:29 src/gen.c:36 src/pull.c:82
|
||||
msgid "Loaded repository configuration"
|
||||
msgstr ""
|
||||
|
||||
#: src/gen.c:31 src/pull.c:77
|
||||
msgid "Failed to load the configuration file (mc.cfg):"
|
||||
msgstr ""
|
||||
|
||||
#: src/gen.c:42
|
||||
msgid "Copying all the targets"
|
||||
msgstr ""
|
||||
|
||||
#: src/gen.c:47
|
||||
msgid "Failed to copy the target:"
|
||||
msgstr ""
|
||||
|
||||
#: src/gen.c:53
|
||||
#, c-format
|
||||
msgid "%s: copy success"
|
||||
msgstr ""
|
||||
|
||||
#: src/log.c:145
|
||||
msgid "y"
|
||||
msgstr ""
|
||||
@ -146,43 +185,58 @@ msgstr ""
|
||||
msgid "Failed to chdir to %s"
|
||||
msgstr ""
|
||||
|
||||
#: src/pull.c:77
|
||||
msgid "Failed to load the configuration file (mc.cfg):"
|
||||
msgstr ""
|
||||
|
||||
#: src/pull.c:82
|
||||
msgid "Loaded repository configuration"
|
||||
msgstr ""
|
||||
|
||||
#: src/pull.c:83
|
||||
msgid "Configuration details:\n"
|
||||
msgstr ""
|
||||
|
||||
#: src/pull.c:84
|
||||
msgid "Name"
|
||||
msgstr ""
|
||||
|
||||
#: src/pull.c:85
|
||||
msgid "Author"
|
||||
msgstr ""
|
||||
|
||||
#: src/pull.c:87
|
||||
msgid "Keywords"
|
||||
msgstr ""
|
||||
|
||||
#: src/pull.c:92
|
||||
msgid "Do you want to continue?"
|
||||
msgstr ""
|
||||
|
||||
#: src/pull.c:95
|
||||
#: src/pull.c:88
|
||||
msgid "Checking all the targets"
|
||||
msgstr ""
|
||||
|
||||
#: src/pull.c:99
|
||||
#: src/pull.c:92
|
||||
#, c-format
|
||||
msgid "Failed to access the source for the target \"%s\""
|
||||
msgstr ""
|
||||
|
||||
#: src/pull.c:105
|
||||
#: src/pull.c:98
|
||||
msgid "All the targets are OK"
|
||||
msgstr ""
|
||||
|
||||
#: src/target.c:13
|
||||
msgid "Configuration target is missing a name"
|
||||
msgstr ""
|
||||
|
||||
#: src/target.c:18
|
||||
#, c-format
|
||||
msgid "Configuration target \"%s\" does not have \"dst\" field"
|
||||
msgstr ""
|
||||
|
||||
#: src/target.c:23
|
||||
#, c-format
|
||||
msgid "Configuration target \"%s\" does not have \"src\" field"
|
||||
msgstr ""
|
||||
|
||||
#: src/target.c:38
|
||||
#, c-format
|
||||
msgid "Failed to open the directory: %s"
|
||||
msgstr ""
|
||||
|
||||
#: src/target.c:76
|
||||
#, c-format
|
||||
msgid "Source directory \"%s\" does not exist"
|
||||
msgstr ""
|
||||
|
||||
#: src/util.c:115 src/util.c:126
|
||||
#, c-format
|
||||
msgid "Failed to create directory: %s"
|
||||
msgstr ""
|
||||
|
||||
#: src/util.c:205
|
||||
#, c-format
|
||||
msgid "Failed to open \"%s\" for reading"
|
||||
msgstr ""
|
||||
|
||||
#: src/util.c:207
|
||||
#, c-format
|
||||
msgid "Failed to open \"%s\" for writing"
|
||||
msgstr ""
|
||||
|
63
src/config.c
63
src/config.c
@ -8,23 +8,14 @@
|
||||
#include "log.h"
|
||||
#include "util.h"
|
||||
|
||||
bool target_is_valid(target_t *target) {
|
||||
if (NULL == target->name) {
|
||||
error_set(_("Configuration target is missing a name"));
|
||||
return false;
|
||||
}
|
||||
|
||||
if (NULL == target->dst) {
|
||||
error_set(_("Configuration target \"%s\" does not have \"dst\" field"), target->name);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (NULL == target->src) {
|
||||
error_set(_("Configuration target \"%s\" does not have \"src\" field"), target->name);
|
||||
return false;
|
||||
}
|
||||
|
||||
bool config_contains_target(config_t *config, char *name) {
|
||||
target_t *cur = config->t_last;
|
||||
while (cur) {
|
||||
if (eq(cur->name, name))
|
||||
return true;
|
||||
cur = cur->next;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool config_is_valid(config_t *config) {
|
||||
@ -55,13 +46,10 @@ bool config_is_valid(config_t *config) {
|
||||
|
||||
bool config_add_target(config_t *config, char *name) {
|
||||
target_t *new = malloc(sizeof(target_t));
|
||||
clist_init(&new->requires);
|
||||
|
||||
new->next = NULL;
|
||||
target_init(new);
|
||||
new->name = name;
|
||||
new->desc = NULL;
|
||||
new->dst = NULL;
|
||||
new->src = NULL;
|
||||
|
||||
config->t_len++;
|
||||
|
||||
if (NULL == config->t_first || NULL == config->t_last) {
|
||||
config->t_first = new;
|
||||
@ -99,6 +87,11 @@ int config_handler(void *data, const char *section, const char *key, const char
|
||||
|
||||
if (NULL == config->t_last || (NULL != config->t_last->name && !eq(config->t_last->name, (char *)section))) {
|
||||
debug("adding new target => %s", section);
|
||||
if (config_contains_target(config, (char *)section)) {
|
||||
error_set(_("Configuration contains multiple targets with the same name"));
|
||||
errno = ConfigMultiple;
|
||||
return 0;
|
||||
}
|
||||
config_add_target(config, strdup(section));
|
||||
}
|
||||
|
||||
@ -122,15 +115,6 @@ UNKNOWN:
|
||||
return 0;
|
||||
}
|
||||
|
||||
void target_free(target_t *target) {
|
||||
free(target->name);
|
||||
free(target->desc);
|
||||
free(target->dst);
|
||||
free(target->src);
|
||||
clist_free(&target->requires);
|
||||
free(target);
|
||||
}
|
||||
|
||||
void config_free(config_t *config) {
|
||||
free(config->name);
|
||||
free(config->author);
|
||||
@ -139,7 +123,9 @@ void config_free(config_t *config) {
|
||||
while (cur != NULL) {
|
||||
prev = cur;
|
||||
cur = cur->next;
|
||||
|
||||
target_free(prev);
|
||||
free(prev);
|
||||
}
|
||||
|
||||
clist_free(&config->keywords);
|
||||
@ -148,6 +134,7 @@ void config_free(config_t *config) {
|
||||
config->author = NULL;
|
||||
config->t_first = NULL;
|
||||
config->t_last = NULL;
|
||||
config->t_len = 0;
|
||||
clist_init(&config->keywords);
|
||||
}
|
||||
|
||||
@ -162,11 +149,12 @@ bool config_load(config_t *config, char *path) {
|
||||
config->author = NULL;
|
||||
config->t_first = NULL;
|
||||
config->t_last = NULL;
|
||||
config->t_len = 0;
|
||||
clist_init(&config->keywords);
|
||||
|
||||
if (ini_parse(path, config_handler, config) < 0) {
|
||||
config_free(config);
|
||||
if (errno != ConfigUnknown) {
|
||||
if (errno != ConfigUnknown || errno != ConfigMultiple) {
|
||||
error_set(_("Failed to parse configuration file"));
|
||||
errno = ConfigParseFail;
|
||||
}
|
||||
@ -181,3 +169,14 @@ bool config_load(config_t *config, char *path) {
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
void config_print(config_t *config) {
|
||||
info(_("Configuration details:\n"));
|
||||
printf(COLOR_BOLD " %s " COLOR_RESET "=> %s\n", _("Name"), config->name);
|
||||
printf(COLOR_BOLD " %s " COLOR_RESET "=> %s\n", _("Author"), config->author);
|
||||
|
||||
printf(COLOR_BOLD " %s " COLOR_RESET "=> ", _("Keywords"));
|
||||
for (int i = 0; i < config->keywords.s; i++)
|
||||
printf("%s ", config->keywords.c[i]);
|
||||
printf("\n\n");
|
||||
}
|
||||
|
13
src/config.h
13
src/config.h
@ -1,21 +1,13 @@
|
||||
#pragma once
|
||||
#include "target.h"
|
||||
#include "util.h"
|
||||
#include <stdbool.h>
|
||||
#include <stddef.h>
|
||||
|
||||
typedef struct target {
|
||||
struct target *next;
|
||||
clist_t
|
||||
requires;
|
||||
char *name;
|
||||
char *desc;
|
||||
char *src;
|
||||
char *dst;
|
||||
} target_t;
|
||||
|
||||
typedef struct config {
|
||||
target_t *t_first;
|
||||
target_t *t_last;
|
||||
size_t t_len;
|
||||
|
||||
char *name;
|
||||
char *author;
|
||||
@ -24,3 +16,4 @@ typedef struct config {
|
||||
|
||||
bool config_load(config_t *, char *);
|
||||
void config_free(config_t *);
|
||||
void config_print(config_t *);
|
||||
|
@ -5,6 +5,13 @@ enum ErrorCodes {
|
||||
ConfigNotFound = 954,
|
||||
ConfigInvalid = 953,
|
||||
ConfigParseFail = 952,
|
||||
ConfigMultiple = 951,
|
||||
|
||||
TargetSrcFail = 950,
|
||||
|
||||
OpendirFail = 948,
|
||||
MkdirFail = 945,
|
||||
OpenFail = 944,
|
||||
};
|
||||
|
||||
extern int errno;
|
||||
|
61
src/gen.c
61
src/gen.c
@ -1,5 +1,64 @@
|
||||
#include "gen.h"
|
||||
#include "args.h"
|
||||
#include "config.h"
|
||||
#include "error.h"
|
||||
#include "intl.h"
|
||||
#include "log.h"
|
||||
#include "util.h"
|
||||
#include <unistd.h>
|
||||
|
||||
bool gen_cmd() {
|
||||
return true;
|
||||
bool ret = false;
|
||||
config_t cfg;
|
||||
|
||||
if (args.count != 2) {
|
||||
error(_("Please specify a directory for the repository"));
|
||||
return ret;
|
||||
}
|
||||
|
||||
if (!exists(args.list[1]) || !is_dir(args.list[1])) {
|
||||
error(_("Failed to access the directory"));
|
||||
return ret;
|
||||
}
|
||||
|
||||
if (chdir(args.list[1]) < 0) {
|
||||
error(_("Failed to change directory to the specified directory"));
|
||||
return ret;
|
||||
}
|
||||
|
||||
success(_("Loaded repository configuration"));
|
||||
if (!config_load(&cfg, "mc.cfg")) {
|
||||
error(_("Failed to load the configuration file (mc.cfg):"));
|
||||
details(errch);
|
||||
return ret;
|
||||
}
|
||||
|
||||
success(_("Loaded repository configuration"));
|
||||
config_print(&cfg);
|
||||
|
||||
target_t *cur = cfg.t_first;
|
||||
int counter = 0;
|
||||
|
||||
info(_("Copying all the targets"));
|
||||
bar_init();
|
||||
|
||||
while (cur && counter++) {
|
||||
if(!target_copy(cur, true)){
|
||||
error(_("Failed to copy the target:"));
|
||||
details(errch);
|
||||
bar_free();
|
||||
goto END;
|
||||
}
|
||||
|
||||
success(_("%s: copy success"));
|
||||
bar(counter, cfg.t_len);
|
||||
cur = cur->next;
|
||||
}
|
||||
|
||||
bar_free();
|
||||
ret = true;
|
||||
|
||||
END:
|
||||
config_free(&cfg);
|
||||
return ret;
|
||||
}
|
||||
|
18
src/log.c
18
src/log.c
@ -138,31 +138,31 @@ void input(const char *msg, ...) {
|
||||
va_end(args);
|
||||
}
|
||||
|
||||
bool yesno(const char *msg){
|
||||
if(env_mc_yes())
|
||||
bool yesno(const char *msg) {
|
||||
if (env_mc_yes())
|
||||
return true;
|
||||
|
||||
char *yes[] = {_("y"), _("Y")};
|
||||
char *no[] = {_("n"), _("N")};
|
||||
|
||||
char question[strlen(msg)+12], c;
|
||||
char question[strlen(msg) + 12], c;
|
||||
sprintf(question, _("%s [y/N] "), msg);
|
||||
|
||||
while(true){
|
||||
while (true) {
|
||||
input(question);
|
||||
|
||||
int c = getchar();
|
||||
if(c == '\n')
|
||||
if (c == '\n')
|
||||
return false;
|
||||
getchar();
|
||||
|
||||
for(int i = 0; i < sizeof(yes)/sizeof(char*); i++){
|
||||
if(yes[i][0] == c)
|
||||
for (int i = 0; i < sizeof(yes) / sizeof(char *); i++) {
|
||||
if (yes[i][0] == c)
|
||||
return true;
|
||||
}
|
||||
|
||||
for(int i = 0; i < sizeof(no)/sizeof(char*); i++){
|
||||
if(no[i][0] == c)
|
||||
for (int i = 0; i < sizeof(no) / sizeof(char *); i++) {
|
||||
if (no[i][0] == c)
|
||||
return false;
|
||||
}
|
||||
|
||||
|
@ -80,14 +80,7 @@ COPY:
|
||||
}
|
||||
|
||||
success(_("Loaded repository configuration"));
|
||||
info(_("Configuration details:\n"));
|
||||
printf(COLOR_BOLD " %s " COLOR_RESET "=> %s\n", _("Name"), repo_cfg.name);
|
||||
printf(COLOR_BOLD " %s " COLOR_RESET "=> %s\n", _("Author"), repo_cfg.author);
|
||||
|
||||
printf(COLOR_BOLD " %s " COLOR_RESET "=> ", _("Keywords"));
|
||||
for (int i = 0; i < repo_cfg.keywords.s; i++)
|
||||
printf("%s ", repo_cfg.keywords.c[i]);
|
||||
printf("\n\n");
|
||||
config_print(&repo_cfg);
|
||||
|
||||
if (!yesno(_("Do you want to continue?")))
|
||||
goto END;
|
||||
|
110
src/target.c
Normal file
110
src/target.c
Normal file
@ -0,0 +1,110 @@
|
||||
#include "target.h"
|
||||
#include "error.h"
|
||||
#include "intl.h"
|
||||
#include "util.h"
|
||||
|
||||
#include <libgen.h>
|
||||
#include <dirent.h>
|
||||
#include <stdlib.h>
|
||||
#include <string.h>
|
||||
|
||||
bool target_is_valid(target_t *t) {
|
||||
if (NULL == t->name) {
|
||||
error_set(_("Configuration target is missing a name"));
|
||||
return false;
|
||||
}
|
||||
|
||||
if (NULL == t->dst) {
|
||||
error_set(_("Configuration target \"%s\" does not have \"dst\" field"), t->name);
|
||||
return false;
|
||||
}
|
||||
|
||||
if (NULL == t->src) {
|
||||
error_set(_("Configuration target \"%s\" does not have \"src\" field"), t->name);
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool target_copy_dir(char *src, char *dst) {
|
||||
if (!mksubdirsp(dst, 755))
|
||||
return false;
|
||||
|
||||
DIR *dir = opendir(src);
|
||||
struct dirent *ent = NULL;
|
||||
|
||||
if (NULL == dir) {
|
||||
error_set(_("Failed to open the directory: %s"), src);
|
||||
errno = OpendirFail;
|
||||
return false;
|
||||
}
|
||||
|
||||
size_t src_len = strlen(src);
|
||||
size_t dst_len = strlen(dst);
|
||||
|
||||
while ((ent = readdir(dir)) != NULL) {
|
||||
size_t len = strlen(ent->d_name);
|
||||
char src_fp[src_len + len + 2], dst_fp[dst_len + len + 2];
|
||||
|
||||
join(src_fp, src, ent->d_name);
|
||||
join(dst_fp, dst, ent->d_name);
|
||||
|
||||
if (is_dir(src_fp)) {
|
||||
if (!target_copy_dir(src_fp, dst_fp))
|
||||
return false;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (!copyfile(src_fp, dst_fp))
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
bool target_copy(target_t *t, bool fromdst) {
|
||||
char *src = t->src, *dst = t->dst;
|
||||
bool ret = false;
|
||||
|
||||
if (fromdst) {
|
||||
src = t->dst;
|
||||
dst = t->src;
|
||||
}
|
||||
|
||||
if (!exists(t->src)) {
|
||||
error_set(_("Source directory \"%s\" does not exist"), src);
|
||||
errno = TargetSrcFail;
|
||||
return ret;
|
||||
}
|
||||
|
||||
if (is_dir(src))
|
||||
return target_copy_dir(src, dst);
|
||||
|
||||
char *dstcp = strdup(dst);
|
||||
char *dstdir = dirname(dst);
|
||||
|
||||
if(!mksubdirsp(dstdir, 0755))
|
||||
return ret;
|
||||
|
||||
ret = copyfile(src, dstcp);
|
||||
free(dstcp);
|
||||
return ret;
|
||||
}
|
||||
|
||||
void target_init(target_t *t) {
|
||||
clist_init(&t->requires);
|
||||
t->next = NULL;
|
||||
t->name = NULL;
|
||||
t->desc = NULL;
|
||||
t->dst = NULL;
|
||||
t->src = NULL;
|
||||
}
|
||||
|
||||
void target_free(target_t *t) {
|
||||
free(t->name);
|
||||
free(t->desc);
|
||||
free(t->dst);
|
||||
free(t->src);
|
||||
clist_free(&t->requires);
|
||||
}
|
17
src/target.h
Normal file
17
src/target.h
Normal file
@ -0,0 +1,17 @@
|
||||
#include "util.h"
|
||||
#include <stdbool.h>
|
||||
|
||||
typedef struct target {
|
||||
struct target *next;
|
||||
clist_t
|
||||
requires;
|
||||
char *name;
|
||||
char *desc;
|
||||
char *src;
|
||||
char *dst;
|
||||
} target_t;
|
||||
|
||||
bool target_is_valid(target_t *);
|
||||
void target_init(target_t *);
|
||||
void target_free(target_t *);
|
||||
bool target_copy(target_t *, bool);
|
38
src/util.c
38
src/util.c
@ -8,6 +8,8 @@
|
||||
#include <time.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#include "error.h"
|
||||
#include "intl.h"
|
||||
#include "util.h"
|
||||
|
||||
bool eq(char *s1, char *s2) {
|
||||
@ -109,16 +111,22 @@ bool mksubdirsp(char *path, int perms) {
|
||||
for (char *c = path; *c != '\0'; c++) {
|
||||
if (*c == '/' && indx != 0) {
|
||||
cur[indx] = '\0';
|
||||
if (!exists(cur) && mkdir(cur, perms) < 0)
|
||||
if (!exists(cur) && mkdir(cur, perms) < 0){
|
||||
error_set(_("Failed to create directory: %s"), cur);
|
||||
errno = MkdirFail;
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
cur[indx] = *c;
|
||||
indx++;
|
||||
}
|
||||
|
||||
if (!exists(cur) && mkdir(cur, perms) < 0)
|
||||
if (!exists(cur) && mkdir(cur, perms) < 0){
|
||||
error_set(_("Failed to create directory: %s"), cur);
|
||||
errno = MkdirFail;
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
@ -187,3 +195,29 @@ void clist_add(clist_t *l, char *en) {
|
||||
l->c[l->s] = en;
|
||||
l->s++;
|
||||
}
|
||||
|
||||
bool copyfile(char *src, char *dst){
|
||||
FILE *srcf = fopen(src, "r");
|
||||
FILE *dstf = fopen(dst, "w");
|
||||
|
||||
if(NULL == srcf || NULL == dstf){
|
||||
if(NULL == srcf)
|
||||
error_set(_("Failed to open \"%s\" for reading"), srcf);
|
||||
else
|
||||
error_set(_("Failed to open \"%s\" for writing"), dstf);
|
||||
errno = OpenFail;
|
||||
return false;
|
||||
}
|
||||
|
||||
char buffer[32];
|
||||
int read = -1;
|
||||
|
||||
bzero(buffer, 32);
|
||||
|
||||
while((read = fread(buffer, 1, 32, srcf)) > 0)
|
||||
fwrite(buffer, 1, read, dstf);
|
||||
|
||||
fclose(srcf);
|
||||
fclose(dstf);
|
||||
return true;
|
||||
}
|
||||
|
@ -18,6 +18,7 @@ int randint(int, int);
|
||||
bool is_dir(char *);
|
||||
bool mksubdirsp(char *, int);
|
||||
bool rmrf(char *);
|
||||
bool copyfile(char *, char *);
|
||||
|
||||
void clist_init(clist_t *);
|
||||
void clist_from_str(clist_t *, char *);
|
||||
|
Loading…
Reference in New Issue
Block a user