/* ---------------------------------------------------------------------
   (c) ED 2005
   Project      : CLIB/DIR
   Function     : Unit Test for DIR
   Module       : MAIN
   File         : main.c
   Created      : 05-09-2005
   Modified     : 05-09-2005
   --------------------------------------------------------------------- */

/* ---------------------------------------------------------------------
   Log

   0.0 05-09-2005 Created

   --------------------------------------------------------------------- */
#ifdef __cplusplus
#error This is not C++. Please use a C compiler.
#endif

#ifdef DBG_SYSALLOC
#include "ed/inc/sysalloc.h"
#endif

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#include "ed/inc/dir.h"
#include "ed/inc/str.h"
#include "ed/inc/fic.h"

/* macros ============================================================== */

#define VER "0.0"

#define PRJ "DIR2"
#define MOD "MAIN"
#define CPY "(c) ED 2005"

#define DBG 0

/* constants =========================================================== */

/* types =============================================================== */

/* structures ========================================================== */
struct user
{
   int count;
   char const *s_opt;
};


/* private functions =================================================== */

/* ---------------------------------------------------------------------
   banner ()
   ---------------------------------------------------------------------

   ---------------------------------------------------------------------
   I:
   O:
   --------------------------------------------------------------------- */
static void banner (void)
{
   printf ("\n" PRJ " " CPY " " VER "\n\n");
}

/* ---------------------------------------------------------------------
   usage ()
   ---------------------------------------------------------------------

   ---------------------------------------------------------------------
   I:
   O:
   --------------------------------------------------------------------- */
static void usage (void)
{
   fprintf (stdout, "usage " PRJ
            " directory[ \"files[ files[*]]\""
            " [/u | /l | d2u | u2d]] \n");
}

/* ---------------------------------------------------------------------
   dos2unix ()
   ---------------------------------------------------------------------
   \r\n -> \n
   ---------------------------------------------------------------------
   I:
   O:
   --------------------------------------------------------------------- */
static void dos2unix (char const *s_file)
{
#define TMP "$$$"

   FILE *fp_in = fopen (s_file, "rb");

   if (fp_in != NULL)
   {
#if DBG
      FILE *fp_out = stdout;
#else
      FILE *fp_out = fopen (TMP, "wb");
#endif
      if (fp_out != NULL)
      {
         int sts = 0;
         int c;

         while ((c = fgetc (fp_in)) != EOF)
         {
            switch (c)
            {

            case '\r':

               if (sts == 0)
               {
                  sts = 1;
#if DBG
                  printf ("\\r");
#endif
               }
               break;

            case '\n':

#if DBG
               printf ("\\n");
#endif
               fputc ('\n', fp_out);
               sts = 0;
               break;

            default:
#if DBG
               if (sts == 1)
               {
                  printf ("\\n");
                  printf ("\n");
                  sts = 0;
               }
#else
               if (sts == 1)
               {
                  fputc ('\n', fp_out);
                  sts = 0;
               }
               fputc (c, fp_out);
#endif
            }
         }

#if DBG
#else
         fclose (fp_out), fp_out = NULL;
#endif
      }
      fclose (fp_in), fp_in = NULL;
   }

#if DBG
#else
   if (FIC_exist (TMP))
   {
      FIC_backup (s_file, TMP, "d2u");
   }
#endif
#undef TMP
}

/* ---------------------------------------------------------------------
   unix2dos ()
   ---------------------------------------------------------------------
   \n -> \r\n
   ---------------------------------------------------------------------
   I:
   O:
   --------------------------------------------------------------------- */
static void unix2dos (char const *s_file)
{
#define TMP "$$$"

   FILE *fp_in = fopen (s_file, "rb");

   if (fp_in != NULL)
   {
#if DBG
      FILE *fp_out = stdout;
#else
      FILE *fp_out = fopen (TMP, "wb");
#endif
      if (fp_out != NULL)
      {
         int c;

         while ((c = fgetc (fp_in)) != EOF)
         {
            switch (c)
            {

            case '\r':
               break;

            case '\n':

#if DBG
               printf ("\\r\\n");
#endif
               fputc ('\r', fp_out);
               fputc ('\n', fp_out);
               break;

            default:
               fputc (c, fp_out);
            }
         }

#if DBG
#else
         fclose (fp_out), fp_out = NULL;
#endif
      }
      fclose (fp_in), fp_in = NULL;
   }

#if DBG
#else
   if (FIC_exist (TMP))
   {
      FIC_backup (s_file, TMP, "u2d");
   }
#endif
#undef TMP

}

/* ---------------------------------------------------------------------
   cb_out ()
   ---------------------------------------------------------------------

   ---------------------------------------------------------------------
   I:
   O:
   --------------------------------------------------------------------- */
static int cb_out (void *p_user, char const *s_path, char const *s_file)
{
   int stop = 0;

   struct user *p_data = p_user;

   p_data->count++;
   printf ("%3d %s\\%s\n", p_data->count, s_path, s_file);

   if (strcmp (p_data->s_opt, "/u") == 0)
   {
      /* to uppercase */
      char *s_new = STR_dup (s_file);

      if (s_new != NULL)
      {
         STR_toupper (s_new);
         rename (s_file, s_new);

         FREE (s_new);
      }
   }
   else if (strcmp (p_data->s_opt, "/l") == 0)
   {
      /* to lowercase */
      char *s_new = STR_dup (s_file);

      if (s_new != NULL)
      {
         STR_tolower (s_new);
         rename (s_file, s_new);

         FREE (s_new);
      }
   }
   else if (strcmp (p_data->s_opt, "/d2u") == 0)
   {
      /* DOS to Unix */
      dos2unix (s_file);
   }
   else if (strcmp (p_data->s_opt, "/u2d") == 0)
   {
      /* DOS to Unix */
      unix2dos (s_file);
   }
   else
   {
      /* nothing */
   }
   return stop;
}

/* ---------------------------------------------------------------------
   appli ()
   ---------------------------------------------------------------------

   ---------------------------------------------------------------------
   I:
   O:
   --------------------------------------------------------------------- */
static int appli (int argc, char **argv)
{
   int ret = EXIT_SUCCESS;

   if (argc > 1)
   {
      struct user user =
      {
         0,
         "",
      };

      char *s_dir = argv[1];
      char const *s_files = "";


      if (argc > 2)
      {
         s_files = argv[2];
      }

      if (argc > 3)
      {
         user.s_opt = argv[3];
      }

      dir (s_dir, s_files, cb_out, &user);

   }
   return ret;
}

/* ---------------------------------------------------------------------
   onexit ()
   ---------------------------------------------------------------------

   ---------------------------------------------------------------------
   I:
   O:
   --------------------------------------------------------------------- */
static void onexit (void)
{

#ifdef DBG_SYSALLOC
   sys_mem_trace ();
#endif

   system ("pause");

}

/* public functions ==================================================== */

/* ---------------------------------------------------------------------
   main ()
   ---------------------------------------------------------------------

   ---------------------------------------------------------------------
   I:
   O:
   --------------------------------------------------------------------- */
int main (int argc, char **argv)
{
   int ret;

#ifdef DBG_SYSALLOC
   static char Trace[1 << 8];

   SYS_INIT (Trace, OFF);
#endif

   atexit (onexit);

   if (argc > 1)
   {
      banner ();
      ret = appli (argc, argv);

      printf ("\n");
   }
   else
   {
      usage ();
      ret = EXIT_FAILURE;
   }
   return ret;
}

/* ---------------------------------------------------------------------
   Generated by NEW (c) ED 2.8
   Powered by C-code generator library  1.2
   --------------------------------------------------------------------- */
