#include <stdio.h>
#include <string.h>
#include <platon/str/charsets.h>
#include <platon/str/strconv.h>
#include <platon/str/strplus.h>
#include <platon/str/strctype.h>
/* Compilation against libplaton library:
gcc -pedantic -L ../../platon/ -I ../../ -o strconv strconv.c -lplaton
*/
#define BUFSIZE 512
#if 0
# define ARGV0 (strrchr(argv[0], '/') != NULL \
? strrchr(argv[0], '/') + 1 : argv[0])
#endif
struct charset_struct
{
char name[20];
char *charset;
};
const struct charset_struct charsets[] = {
{"ascii", charset_ascii },
{"plain", charset_ascii },
{"iso88592", charset_iso88592 },
{"iso8859-2", charset_iso88592 },
{"iso-8859-2", charset_iso88592 },
{"cp1250", charset_cp1250 },
{"cp-1250", charset_cp1250 },
{"windows1250", charset_cp1250 },
{"windows-1250", charset_cp1250 },
{"keybcs2", charset_keybcs2 },
{"universum", charset_universum },
{"koi8cz", charset_koi8cz },
{"pclatin1a", charset_pclatin1a },
{"pclatin2", charset_pclatin2 },
{"*", NULL }
};
int main(int argc, char **argv)
{
FILE *f;
char buf[BUFSIZE], *src_charset, *dest_charset;
register int i, idx, count, errors;
#ifndef ARGV0
char *ARGV0 = strrchr(argv[0], '/') != NULL
? strrchr(argv[0], '/') + 1 : argv[0];
#endif
if (argc > 1 && ! strcmp(argv[1], "-l")) {
char *tmp_charset = NULL;
printf("List of available charsets and its aliases:\n");
for (i = 0; charsets[i].charset != NULL; i++) {
if (charsets[i].charset != tmp_charset) {
printf("\n ");
tmp_charset = charsets[i].charset;
} else {
printf(", ");
}
printf("%s", charsets[i].name);
}
printf("\n\n");
return 0;
}
if (argc < 4) {
fprintf(stderr, "Usage: %s [ -l ] <src_charset> <dest_charset> <filename> ...\n",
ARGV0);
return 1;
}
/* Source charset initialization */
src_charset = NULL;
while (strchr(argv[1], '_') != NULL)
*(strchr(argv[1], '_')) = '-';
argv[1] = strtolower(argv[1]);
argv[1] = str_trim(argv[1]);
for (i = 0; charsets[i].charset != NULL; i++) {
if (! strcmp(charsets[i].name, argv[1])) {
src_charset = charsets[i].charset;
break;
}
}
if (src_charset == NULL) {
fprintf(stderr, "%s: unknown source charset: %s\n", ARGV0, argv[1]);
return 4;
}
/* Destination charset initialization */
dest_charset = NULL;
while (strchr(argv[2], '_') != NULL)
*(strchr(argv[2], '_')) = '-';
argv[2] = strtolower(argv[2]);
argv[2] = str_trim(argv[2]);
for (i = 0; charsets[i].charset != NULL; i++) {
if (! strcmp(charsets[i].name, argv[2])) {
dest_charset = charsets[i].charset;
break;
}
}
if (dest_charset == NULL) {
fprintf(stderr, "%s: unknown destination charset: %s\n", ARGV0, argv[2]);
return 4;
}
if (src_charset == dest_charset) {
fprintf(stderr, "%s: source and destination charsets are the same\n", ARGV0);
return 8;
}
/*
* Main loop
*/
for (errors = 0, idx = 3; idx < argc; idx++) {
if ((f = fopen(argv[idx], "r+")) == NULL) {
fprintf(stderr, "%s: can't open file '%s'\n", ARGV0, argv[3]);
errors++;
continue;
}
i = -1;
count = 0;
do {
count = fread(buf, sizeof(char), BUFSIZE - 1, f);
buf[count] = '\0';
strconv(buf, src_charset, dest_charset);
fseek(f, -count, SEEK_CUR);
if (count != fwrite(buf, sizeof(char), count, f)) {
fclose(f);
fprintf(stderr, "%s: file '%s' write error\n", ARGV0, argv[idx]);
i = -1;
break;
}
i++;
} while (count == BUFSIZE - 1);
fclose(f);
if (i < 0) {
errors++;
continue;
}
printf("%s: file '%s' with size %ld successfully converted\n",
ARGV0, argv[idx],
(long) (i * (BUFSIZE - 1)) + (long) count);
}
return errors ? 2 : 0;
}
Platon Group <platon@platon.org> http://platon.org/
|