136 lines
3.4 KiB
C
136 lines
3.4 KiB
C
#include "common.h"
|
|
#include "compress.h"
|
|
#include <argp.h>
|
|
#include <locale.h>
|
|
#include <string.h>
|
|
|
|
/**
|
|
* Définition de la configuration de Argp, qui affichera
|
|
* ces informations dans la page d'aide entre autres
|
|
*/
|
|
static char doc[] = "Compresse ou décompresse des fichiers en "
|
|
"utilisant l'algorithme de Huffman";
|
|
static char args_doc[] = "FICHIER...";
|
|
static struct argp_option options[] = {
|
|
{
|
|
"verbose", 'V', 0, 0,
|
|
"Afficher des informations de débogage sur la compression"
|
|
},
|
|
{0}
|
|
};
|
|
|
|
/**
|
|
* Contient les valeurs des arguments (options et opérandes)
|
|
* passées au programme et interprétées via Argp
|
|
*/
|
|
typedef struct Args {
|
|
int verbose;
|
|
char** files;
|
|
} Args;
|
|
|
|
/**
|
|
* Fonction de rappel pour interpréter les arguments
|
|
* passés au programme
|
|
*/
|
|
static error_t parse_opt(int key, char* arg, struct argp_state* state) {
|
|
Args* args = state->input;
|
|
|
|
switch (key) {
|
|
case 'V':
|
|
args->verbose = TRUE;
|
|
break;
|
|
|
|
case ARGP_KEY_ARG:
|
|
// Consommation de tous les fichiers en argument
|
|
// et arrêt du parsage
|
|
args->files = &state->argv[state->next - 1];
|
|
state->next = state->argc;
|
|
break;
|
|
|
|
case ARGP_KEY_NO_ARGS:
|
|
argp_usage(state);
|
|
break;
|
|
|
|
default:
|
|
return ARGP_ERR_UNKNOWN;
|
|
}
|
|
|
|
return 0;
|
|
}
|
|
|
|
static struct argp argp = {options, parse_opt, args_doc, doc};
|
|
|
|
int main(int argc, char** argv) {
|
|
// Pour pouvoir afficher des caractères larges dans le terminal
|
|
setlocale(LC_CTYPE, "");
|
|
|
|
// Interprétation des arguments passés au programme par Argv,
|
|
// suivant la configuration définie au dessus
|
|
Args args;
|
|
|
|
args.verbose = FALSE;
|
|
args.files = NULL;
|
|
|
|
argp_parse(&argp, argc, argv, 0, 0, &args);
|
|
|
|
// Passage en mode verbeux si demandé
|
|
setVerbose(args.verbose);
|
|
|
|
// Compression des fichiers en argument
|
|
char** files = args.files;
|
|
|
|
while (*files != NULL) {
|
|
char* input = *files;
|
|
|
|
// Compression du fichier xx en xx.huf
|
|
// TODO: rendre le nom du fichier de sortie configurable
|
|
char* output = malloc((strlen(input) + 5) * sizeof(*output));
|
|
strcpy(output, input);
|
|
strcat(output, ".huf");
|
|
|
|
switch (compress(input, output)) {
|
|
case COMPRESS_READ_ERROR:
|
|
fprintf(
|
|
stderr,
|
|
"Erreur : impossible de lire le fichier '%s' - %s\n",
|
|
input, strerror(errno)
|
|
);
|
|
return COMPRESS_READ_ERROR;
|
|
|
|
case COMPRESS_WRITE_ERROR:
|
|
fprintf(
|
|
stderr,
|
|
"Erreur : impossible d'écrire dans le fichier '%s' - %s\n",
|
|
output, strerror(errno)
|
|
);
|
|
return COMPRESS_WRITE_ERROR;
|
|
|
|
case COMPRESS_OPEN_INPUT_ERROR:
|
|
fprintf(
|
|
stderr,
|
|
"Erreur : impossible d'ouvrir le fichier '%s' - %s\n",
|
|
input, strerror(errno)
|
|
);
|
|
return COMPRESS_OPEN_INPUT_ERROR;
|
|
|
|
case COMPRESS_OPEN_OUTPUT_ERROR:
|
|
fprintf(
|
|
stderr,
|
|
"Erreur : impossible d'ouvrir le fichier '%s' - %s\n",
|
|
output, strerror(errno)
|
|
);
|
|
return COMPRESS_OPEN_OUTPUT_ERROR;
|
|
}
|
|
|
|
free(output);
|
|
files++;
|
|
|
|
// Ligne de séparation entre les différents fichiers
|
|
if (*files != NULL) {
|
|
printVerbose("\n");
|
|
}
|
|
}
|
|
|
|
return EXIT_SUCCESS;
|
|
}
|