source: trunk/dll/uudecode.c@ 1395

Last change on this file since 1395 was 1395, checked in by Gregg Young, 17 years ago

Allow user to turn off alert and/or error beeps in settings notebook. Ticket 341 Move repeated strings to PCSZs. Ticket 6 Add *DateFormat functions to format dates based on locale Ticket 28 Eliminate Win_Error2 by moving function names to PCSZs used in Win_Error Ticket 6

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 11.2 KB
RevLine 
[195]1
2/***********************************************************************
3
4 $Id: uudecode.c 1395 2009-02-08 01:48:16Z gyoung $
5
6 uudecode
7
8 Copyright (c) 1993-98 M. Kimes
[907]9 Copyright (c) 2005, 2008 Steven H. Levine
[195]10
11 06 Jun 05 SHL Indent -i2
[204]12 06 Jun 05 SHL Drop unused code
[328]13 17 Jul 06 SHL Use Runtime_Error
[404]14 29 Jul 06 SHL Use xfgets
[486]15 01 Sep 06 SHL Back to fgets for now - avoid excess error messages
[574]16 22 Mar 07 GKY Use QWL_USER
[793]17 20 Aug 07 GKY Move #pragma alloc_text to end for OpenWatcom compat
[1395]18 07 Feb 09 GKY Allow user to turn off alert and/or error beeps in settings notebook.
[195]19
20***********************************************************************/
21
[2]22#include <stdlib.h>
23#include <string.h>
24#include <share.h>
[328]25
[907]26#define INCL_DOS
27#define INCL_WIN
[1160]28#define INCL_LONGLONG // dircnrs.h
[907]29
[1183]30#include "fm3dll.h"
[1228]31#include "fm3dll2.h" // #define's for UM_*, control id's, etc.
32#include "worker.h" // typedef WORKER
[1214]33#include "notebook.h" // Data declaration(s)
[2]34#include "fm3dlg.h"
35#include "fm3str.h"
[1160]36#include "makelist.h" // AddToList
37#include "errutil.h" // Dos_Error...
38#include "strutil.h" // GetPString
39#include "defview.h"
40#include "uudecode.h"
[1183]41#include "getnames.h" // export_filename
42#include "valid.h" // IsFile
43#include "misc.h" // PaintRecessedWindow
44#include "wrappers.h" // xfgets
[2]45
[328]46static PSZ pszSrcFile = __FILE__;
47
[2]48/* prototypes */
[195]49static BOOL decode(FILE * in, FILE * out);
50static void outdec(char *p, FILE * f, int n);
[2]51
52/* single character decode */
[1160]53#define DEC(c) (((c) - ' ') & 077)
[2]54
[195]55int UUD(char *filename, CHAR * dest)
56{
57 FILE *in, *out;
58 int mode, ret = 0;
59 char buf[80];
60 char fakedest[CCHMAXPATH];
[2]61
[195]62 if (!dest)
[2]63 dest = fakedest;
[195]64 in = _fsopen(filename, "r", SH_DENYWR);
[486]65 if (!in) {
[2]66 saymsg(MB_CANCEL,
[1160]67 HWND_DESKTOP,
68 GetPString(IDS_ERRORTEXT),
69 GetPString(IDS_COMPCANTOPENTEXT), filename);
[2]70 return ret;
71 }
72
[195]73 /* search for header line */
[486]74 for (;;) {
75 if (!fgets(buf, sizeof(buf), in)) {
[2]76 fclose(in);
77 saymsg(MB_CANCEL,
[1160]78 HWND_DESKTOP,
79 GetPString(IDS_ERRORTEXT),
80 GetPString(IDS_UUDNOBEGINTEXT), filename);
[2]81 return ret;
[195]82 }
83 if (!strncmp(buf, "begin ", 6))
84 break;
[1160]85 } // for
[2]86 *dest = 0;
[195]87 sscanf(buf, "begin %o %259s", &mode, dest);
[2]88 dest[CCHMAXPATH - 1] = 0;
[486]89 {
90 /* place dest in same directory as filename by default... */
[195]91 char build[CCHMAXPATH], *p;
[2]92
[195]93 strcpy(build, filename);
94 p = strrchr(build, '\\');
[486]95 if (p) {
[2]96 p++;
97 *p = 0;
98 }
99 else
[195]100 strcat(build, "\\");
101 strncat(build, dest, CCHMAXPATH - strlen(dest));
102 strcpy(dest, build);
[2]103 }
104
[486]105 if (!export_filename(HWND_DESKTOP, dest, FALSE)) {
[2]106 fclose(in);
107 return ret;
108 }
109
[195]110 /* create output file */
111 out = _fsopen(dest, "ab+", SH_DENYWR);
[486]112 if (!out) {
[2]113 fclose(in);
114 saymsg(MB_CANCEL,
[1160]115 HWND_DESKTOP,
116 GetPString(IDS_ERRORTEXT),
117 GetPString(IDS_UUDCANTOPENFORTEXT), dest, filename);
[2]118 return ret;
[195]119 }
[2]120
[204]121 ret = 1;
122 decode(in, out);
[2]123
[551]124 xfgets(buf, sizeof(buf), in, pszSrcFile, __LINE__);
[204]125
[2]126 fclose(in);
127 fclose(out);
128 return ret;
129}
130
131/*
132 * copy from in to out, decoding as you go along.
133 */
[195]134static BOOL decode(FILE * in, FILE * out)
135{
136 char buf[80];
137 char *bp;
138 int n;
[2]139
[486]140 for (;;) {
[195]141 /* for each input line */
[551]142 if (!xfgets(buf, sizeof(buf), in, pszSrcFile, __LINE__))
[2]143 return FALSE;
144 n = DEC(buf[0]);
[195]145 if (n <= 0)
146 break;
147 bp = &buf[1];
[486]148 while (n > 0) {
[195]149 outdec(bp, out, n);
150 bp += 4;
151 n -= 3;
152 }
153 }
[2]154 return TRUE;
155}
156
157/*
158 * output a group of 3 bytes (4 input characters).
159 * the input chars are pointed to by p, they are to
160 * be output to file f. n is used to tell us not to
161 * output all of them at the end of the file.
162 */
[195]163static void outdec(char *p, FILE * f, int n)
164{
[204]165 INT c1, c2, c3;
[2]166
[551]167 c1 = DEC(*p) << 2 | (UINT) DEC(p[1]) >> 4;
168 c2 = DEC(p[1]) << 4 | (UINT) DEC(p[2]) >> 2;
[195]169 c3 = DEC(p[2]) << 6 | DEC(p[3]);
170 if (n >= 1)
171 putc(c1, f);
172 if (n >= 2)
173 putc(c2, f);
174 if (n >= 3)
175 putc(c3, f);
[2]176}
177
[195]178MRESULT EXPENTRY MergeDlgProc(HWND hwnd, ULONG msg, MPARAM mp1, MPARAM mp2)
179{
[2]180 WORKER *wk;
181
[551]182 switch (msg) {
[195]183 case WM_INITDLG:
[486]184 if (mp2) {
[574]185 WinSetWindowPtr(hwnd, QWL_USER, mp2);
[195]186 wk = (WORKER *) mp2;
[551]187 if (wk->li && wk->li->list && wk->li->list[0]) {
[1160]188 WinSendDlgItemMsg(hwnd, MRG_TARGETNAME, EM_SETTEXTLIMIT,
189 MPFROM2SHORT(CCHMAXPATH, 0), MPVOID);
190 PostMsg(hwnd, UM_UNDO, MPVOID, MPVOID);
[2]191 }
192 else
[1160]193 WinDismissDlg(hwnd, 0);
[195]194 }
195 else
196 WinDismissDlg(hwnd, 0);
197 break;
[2]198
[195]199 case UM_UNDO:
200 WinSendDlgItemMsg(hwnd, MRG_LISTBOX, LM_DELETEALL, MPVOID, MPVOID);
[574]201 wk = WinQueryWindowPtr(hwnd, QWL_USER);
[486]202 if (wk) {
[195]203 INT x, numfiles = 0;
204 SHORT start;
205 CHAR *p;
[2]206
[551]207 WinSetDlgItemText(hwnd, MRG_TARGETNAME, wk->li->targetpath);
[195]208 start = 0;
[551]209 p = strrchr(wk->li->targetpath, '\\');
[195]210 if (p)
[1160]211 start = (p + 1) - wk->li->targetpath;
[195]212 WinSendDlgItemMsg(hwnd, MRG_TARGETNAME, EM_SETSEL,
[1160]213 MPFROM2SHORT(start, CCHMAXPATH), MPVOID);
[551]214 for (x = 0; wk->li->list[x]; x++) {
[1160]215 if (IsFile(wk->li->list[x]) == 1) {
216 numfiles++;
217 WinSendDlgItemMsg(hwnd, MRG_LISTBOX, LM_INSERTITEM,
218 MPFROM2SHORT(LIT_END, 0),
219 MPFROMP(wk->li->list[x]));
220 }
[2]221 }
[551]222 WinCheckButton(hwnd, MRG_BINARY, (wk->li->type == IDM_MERGEBINARY));
[486]223 if (!numfiles) {
[1160]224 saymsg(MB_CANCEL | MB_ICONEXCLAMATION,
225 hwnd,
226 GetPString(IDS_SILLYERRORTEXT),
227 GetPString(IDS_MERGEWASTETEXT));
228 WinDismissDlg(hwnd, 0);
[195]229 }
230 }
231 return 0;
[2]232
[195]233 case WM_CONTROL:
[551]234 switch (SHORT1FROMMP(mp1)) {
[195]235 case MRG_LISTBOX:
[551]236 switch (SHORT2FROMMP(mp1)) {
[195]237 case LN_ENTER:
[1160]238 {
239 SHORT x;
240 CHAR szBuffer[CCHMAXPATH];
[2]241
[1160]242 x = (SHORT) WinSendDlgItemMsg(hwnd, MRG_LISTBOX, LM_QUERYSELECTION,
243 MPFROMSHORT(LIT_FIRST), MPVOID);
244 if (x >= 0) {
245 *szBuffer = 0;
246 WinSendDlgItemMsg(hwnd, MRG_LISTBOX, LM_QUERYITEMTEXT,
247 MPFROM2SHORT(x, CCHMAXPATH), MPFROMP(szBuffer));
248 if (*szBuffer)
249 QuickEdit(hwnd, szBuffer);
250 }
251 }
252 break;
[2]253 }
254 break;
[195]255 }
256 break;
[2]257
[195]258 case WM_ADJUSTWINDOWPOS:
259 PostMsg(hwnd, UM_SETDIR, MPVOID, MPVOID);
260 break;
[2]261
[195]262 case UM_SETDIR:
[551]263 PaintRecessedWindow(WinWindowFromID(hwnd, MRG_HELP), (HPS) 0, FALSE,
[1160]264 TRUE);
[195]265 return 0;
[2]266
[195]267 case WM_COMMAND:
[551]268 switch (SHORT1FROMMP(mp1)) {
[195]269 case IDM_UNDO:
270 PostMsg(hwnd, UM_UNDO, MPVOID, MPVOID);
271 break;
[2]272
[195]273 case MRG_CHANGETARGET:
[574]274 wk = WinQueryWindowPtr(hwnd, QWL_USER);
[486]275 if (wk) {
[1160]276 CHAR filename[CCHMAXPATH];
[2]277
[1160]278 strcpy(filename, wk->li->targetpath);
279 if (export_filename(HWND_DESKTOP, filename, FALSE) && *filename) {
280 strcpy(wk->li->targetpath, filename);
281 WinSetDlgItemText(hwnd, MRG_TARGETNAME, wk->li->targetpath);
282 }
[195]283 }
284 break;
[2]285
[195]286 case MRG_REMOVE:
287 {
[1160]288 SHORT x;
[2]289
[1160]290 x = (SHORT) WinSendDlgItemMsg(hwnd, MRG_LISTBOX, LM_QUERYSELECTION,
291 MPFROMSHORT(LIT_FIRST), MPVOID);
292 if (x >= 0)
293 WinSendDlgItemMsg(hwnd, MRG_LISTBOX, LM_DELETEITEM,
294 MPFROMSHORT(x), MPVOID);
[195]295 }
296 break;
[2]297
[195]298 case MRG_BOTTOM:
299 case MRG_TOP:
300 {
[1160]301 SHORT x;
302 CHAR szBuffer[CCHMAXPATH];
[2]303
[1160]304 x = (SHORT) WinSendDlgItemMsg(hwnd, MRG_LISTBOX, LM_QUERYSELECTION,
305 MPFROMSHORT(LIT_FIRST), MPVOID);
306 if (x >= 0) {
307 *szBuffer = 0;
308 WinSendDlgItemMsg(hwnd, MRG_LISTBOX, LM_QUERYITEMTEXT,
309 MPFROM2SHORT(x, CCHMAXPATH), MPFROMP(szBuffer));
310 if (*szBuffer) {
311 WinSendDlgItemMsg(hwnd, MRG_LISTBOX, LM_DELETEITEM,
312 MPFROMSHORT(x), MPVOID);
313 if (SHORT1FROMMP(mp1) == MRG_TOP)
314 WinSendDlgItemMsg(hwnd, MRG_LISTBOX, LM_INSERTITEM,
315 MPFROM2SHORT(0, 0), MPFROMP(szBuffer));
316 else
317 WinSendDlgItemMsg(hwnd, MRG_LISTBOX, LM_INSERTITEM,
318 MPFROM2SHORT(LIT_END, 0), MPFROMP(szBuffer));
319 }
320 }
[195]321 }
322 break;
[2]323
[195]324 case DID_CANCEL:
325 WinDismissDlg(hwnd, 0);
326 break;
[2]327
[195]328 case IDM_HELP:
329 if (hwndHelp)
[1160]330 WinSendMsg(hwndHelp, HM_DISPLAY_HELP,
331 MPFROM2SHORT(HELP_MERGE, 0), MPFROMSHORT(HM_RESOURCEID));
[195]332 break;
[2]333
[195]334 case DID_OK:
[574]335 wk = WinQueryWindowPtr(hwnd, QWL_USER);
[486]336 if (wk) {
[1160]337 BOOL append, binary;
338 CHAR **list = NULL, **test, szBuffer[CCHMAXPATH];
339 UINT numfiles = 0, numalloc = 0;
340 INT error;
341 SHORT x, y;
[2]342
[1160]343 *szBuffer = 0;
344 WinQueryDlgItemText(hwnd, MRG_TARGETNAME, CCHMAXPATH, szBuffer);
345 if (!*szBuffer) {
[1395]346 if (!fAlertBeepOff)
347 DosBeep(50, 100);
[1160]348 WinSetFocus(HWND_DESKTOP, WinWindowFromID(hwnd, MRG_TARGETNAME));
349 break;
350 }
351 if (DosQueryPathInfo(szBuffer,
352 FIL_QUERYFULLNAME,
353 wk->li->targetpath, CCHMAXPATH)) {
[1395]354 if (!fAlertBeepOff)
355 DosBeep(50, 100);
[1160]356 WinSetFocus(HWND_DESKTOP, WinWindowFromID(hwnd, MRG_TARGETNAME));
357 break;
358 }
359 WinSetDlgItemText(hwnd, MRG_TARGETNAME, szBuffer);
360 append = WinQueryButtonCheckstate(hwnd, MRG_APPEND);
361 binary = WinQueryButtonCheckstate(hwnd, MRG_BINARY);
362 wk->li->type = (append && binary) ? IDM_MERGEBINARYAPPEND :
363 (append) ? IDM_MERGETEXTAPPEND :
364 (binary) ? IDM_MERGEBINARY : IDM_MERGETEXT;
365 x = (SHORT) WinSendDlgItemMsg(hwnd,
366 MRG_LISTBOX,
367 LM_QUERYITEMCOUNT, MPVOID, MPVOID);
368 for (y = 0; y < x; y++) {
369 *szBuffer = 0;
370 WinSendDlgItemMsg(hwnd,
371 MRG_LISTBOX,
372 LM_QUERYITEMTEXT,
373 MPFROM2SHORT(y, CCHMAXPATH), MPFROMP(szBuffer));
374 if (*szBuffer) {
375 error = AddToList(szBuffer, &list, &numfiles, &numalloc);
376 if (error) {
377 Runtime_Error(pszSrcFile, __LINE__, "AddToList");
378 break;
379 }
380 }
381 }
382 if (numfiles && list && numfiles + 1 < numalloc) {
383 test =
384 xrealloc(list, sizeof(CHAR *) * (numfiles + 1), pszSrcFile,
385 __LINE__);
386 if (test)
387 list = test;
388 }
389 if (!list || !list[0]) {
390 Runtime_Error2(pszSrcFile, __LINE__, IDS_NODATATEXT);
391 break;
392 }
393 else {
394 FreeList(wk->li->list);
395 wk->li->list = list;
396 }
[2]397 }
[195]398 WinDismissDlg(hwnd, 1);
399 break;
[1160]400 } // switch WM_COMMAND mp1
[195]401 return 0;
[1160]402 } // switch msg
[195]403 return WinDefDlgProc(hwnd, msg, mp1, mp2);
[2]404}
[793]405
406#pragma alloc_text(UUD,UUD,decode,outdec)
407#pragma alloc_text(MERGE,MergeDlgProc)
Note: See TracBrowser for help on using the repository browser.