1 /* SPDX-License-Identifier: GPL-2.0-only OR GPL-3.0-only                     */
2 
3 #include "stdinc.h"
4 
5 #include <string.h>
6 #include "strutil.h"
7 
8 #define TMPNAME "tempfile"
9 
10 #ifdef CKMALLOC
11 #undef malloc
12 #undef realloc
13 
ckmalloc(size_t s)14 void *ckmalloc(size_t s)
15 {
16   void *tmp = malloc(s);
17 
18   if (!tmp)
19   {
20     fprintf(stderr, "allocation error(malloc): out of memory");
21     exit(255);
22   }
23   return tmp;
24 }
25 
ckrealloc(void * p,size_t s)26 void *ckrealloc(void *p, size_t s)
27 {
28   void *tmp = realloc(p, s);
29   if (!tmp)
30   {
31     fprintf(stderr, "allocation error(realloc): out of memory");
32     exit(255);
33   }
34   return tmp;
35 }
36 #endif
doexec(char * cmdline)37 void doexec(char *cmdline)
38 {
39  int res=system(cmdline);
40  if (res!=0)
41  {
42    fprintf(stderr, "command \"%s\" failed\n", cmdline); exit(2);
43  }
44 }
45 
main(int argc,char ** argv)46 int main(int argc, char **argv)
47 {
48   FILE *src,*dest;
49   int ch;
50   char cmdline[1024];
51   long charcnt,metacnt,crcnt;
52 
53   if (argc<2)
54   {
55     fprintf(stderr, "usage: %s <file> [destfile|destdir/]\n", argv[0]);
56     exit(1);
57   }
58 
59 #ifdef _WIN32
60   {
61     char *p;
62     int z;
63 
64     for (z = 1; z < argc; z++)
65     {
66       argv[z] = as_strdup(argv[z]);
67       for (p = argv[z]; *p; p++)
68         if (*p == '\\')
69           *p = '/';
70     }
71   }
72 #endif
73 
74   src = fopen(argv[1], OPENRDMODE);
75   if (src == NULL)
76   {
77     fprintf(stderr, "error opening %s for reading\n", argv[1]); exit(2);
78   }
79   if (argc < 3)
80     strcpy(cmdline, TMPNAME);
81   else
82   {
83     int l = strlen(argv[2]);
84 
85     if (strchr("/\\", argv[2][l - 1]))
86     {
87       const char *p = strrchr(argv[1], argv[2][l - 1]);
88       as_snprintf(cmdline, sizeof(cmdline), "%s%s", argv[2], p ? p + 1 : argv[1]);
89     }
90     else
91       strcpy(cmdline, argv[2]);
92   }
93   dest = fopen(cmdline, OPENWRMODE);
94   if (dest == NULL)
95   {
96     fprintf(stderr, "error opening %s for writing\n", cmdline); exit(2);
97   }
98   charcnt = metacnt = crcnt = 0;
99   while (!feof(src))
100   {
101     ch = fgetc(src); charcnt++;
102     switch (ch)
103     {
104       case EOF:
105         break;
106       case 10:
107         fputc(13, dest);
108         fputc(10, dest);
109         crcnt++;
110         break;
111       default:
112         if (ch & 0x80)
113         {
114           fprintf(stderr, "%s: non-ASCII character 0x%02x @ 0x%x\n",
115                   argv[1], ch, (unsigned)ftell(src));
116           metacnt++;
117         }
118         fputc(ch, dest);
119     }
120   }
121   fclose(src);
122   fclose(dest);
123   if (argc == 2)
124   {
125 #if defined (__MSDOS__) || defined(__EMX__)
126     as_snprintf(cmdline, sizeof(cmdline), "copy %s %s", TMPNAME, argv[1]);
127 #else
128     as_snprintf(cmdline, sizeof(cmdline), "cp %s %s", TMPNAME, argv[1]);
129 #endif
130     doexec(cmdline);
131     unlink(TMPNAME);
132   }
133   printf("%s: %ld char(s), %ld cr(s) added, %ld meta char(s) detected\n",
134          argv[1], charcnt, crcnt, metacnt);
135 
136   return metacnt ? 2 : 0;
137 }
138