/* convert.c: */

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

#include "mkisofs.h"

static char g_conversion_table[256] = {
  'X',  /*  0  */
  'X',  /*  1  */
  'X',  /*  2  */
  'X',  /*  3  */
  'X',  /*  4  */
  'X',  /*  5  */
  'X',  /*  6  */
  'X',  /*  7  */
  'X',  /*  8  */
  'X',  /*  9  */
  'X',  /*  10  */
  'X',  /*  11  */
  'X',  /*  12  */
  'X',  /*  13  */
  'X',  /*  14  */
  'X',  /*  15  */
  'X',  /*  16  */
  'X',  /*  17  */
  'X',  /*  18  */
  'X',  /*  19  */
  'X',  /*  20  */
  'X',  /*  21  */
  'X',  /*  22  */
  'X',  /*  23  */
  'X',  /*  24  */
  'X',  /*  25  */
  'X',  /*  26  */
  'X',  /*  27  */
  'X',  /*  28  */
  'X',  /*  29  */
  'X',  /*  30  */
  'X',  /*  31  */
  'S',  /*  space */
  'E',  /*  !  */
  'Q',  /*  "  */
  'H',  /*  #  */
  'D',  /*  $  */
  'P',  /*  %  */
  'A',  /*  &  */
  'A',  /*  '  */
  'P',  /*  (  */
  'P',  /*  )  */
  'A',  /*  *  */
  'P',  /*  +  */
  'C',  /*  ,  */
  'M',  /*  -  */
  'D',  /*  .  */
  'S',  /*  /  */
  '0',  /*  0  */
  '1',  /*  1  */
  '2',  /*  2  */
  '3',  /*  3  */
  '4',  /*  4  */
  '5',  /*  5  */
  '6',  /*  6  */
  '7',  /*  7  */
  '8',  /*  8  */
  '9',  /*  9  */
  'C',  /*  :  */
  'S',  /*  ;  */
  'L',  /*  <  */
  'E',  /*  =  */
  'G',  /*  >  */
  'Q',  /*  ?  */
  'A',  /*  @  */
  'A',  /*  A  */
  'B',  /*  B  */
  'C',  /*  C  */
  'D',  /*  D  */
  'E',  /*  E  */
  'F',  /*  F  */
  'G',  /*  G  */
  'H',  /*  H  */
  'I',  /*  I  */
  'J',  /*  J  */
  'K',  /*  K  */
  'L',  /*  L  */
  'M',  /*  M  */
  'N',  /*  N  */
  'O',  /*  O  */
  'P',  /*  P  */
  'Q',  /*  Q  */
  'R',  /*  R  */
  'S',  /*  S  */
  'T',  /*  T  */
  'U',  /*  U  */
  'V',  /*  V  */
  'W',  /*  W  */
  'X',  /*  X  */
  'Y',  /*  Y  */
  'Z',  /*  Z  */
  'B',  /*  [  */
  'B',  /*  \  */
  'B',  /*  ]  */
  'C',  /*  ^  */
  '_',  /*  _  */
  'A',  /*  `  */
  'A',  /*  a  */
  'B',  /*  b  */
  'C',  /*  c  */
  'D',  /*  d  */
  'E',  /*  e  */
  'F',  /*  f  */
  'G',  /*  g  */
  'H',  /*  h  */
  'I',  /*  i  */
  'J',  /*  j  */
  'K',  /*  k  */
  'L',  /*  l  */
  'M',  /*  m  */
  'N',  /*  n  */
  'O',  /*  o  */
  'P',  /*  p  */
  'Q',  /*  q  */
  'R',  /*  r  */
  'S',  /*  s  */
  'T',  /*  t  */
  'U',  /*  u  */
  'V',  /*  v  */
  'W',  /*  w  */
  'X',  /*  x  */
  'Y',  /*  y  */
  'Z',  /*  z  */
  'B',  /*  {  */
  'B',  /*  |  */
  'B',  /*  }  */
  'T',  /*  ~  */
  'D',  /*  delete */
  'X',  /*  128  */
  'X',  /*  129  */
  'X',  /*  130  */
  'X',  /*  131  */
  'X',  /*  132  */
  'X',  /*  133  */
  'X',  /*  134  */
  'X',  /*  135  */
  'X',  /*  136  */
  'X',  /*  137  */
  'X',  /*  138  */
  'X',  /*  139  */
  'X',  /*  140  */
  'X',  /*  141  */
  'X',  /*  142  */
  'X',  /*  143  */
  'X',  /*  144  */
  'X',  /*  145  */
  'X',  /*  146  */
  'X',  /*  147  */
  'X',  /*  148  */
  'X',  /*  149  */
  'X',  /*  150  */
  'X',  /*  151  */
  'X',  /*  152  */
  'X',  /*  153  */
  'X',  /*  154  */
  'X',  /*  155  */
  'X',  /*  156  */
  'X',  /*  157  */
  'X',  /*  158  */
  'X',  /*  159  */
  'X',  /*  160  */
  'E',  /*  ¡  */
  'C',  /*  ¢  */
  'L',  /*  £  */
  'C',  /*  ¤  */
  'Y',  /*  ¥  */
  'S',  /*  ¦  */
  'P',  /*  §  */
  'D',  /*  ¨  */
  'C',  /*  ©  */
  'A',  /*  ª  */
  'G',  /*  «  */
  'N',  /*  ¬  */
  'M',  /*  ­  */
  'R',  /*  ®  */
  'B',  /*  ¯  */
  'C',  /*  °  */
  'P',  /*  ±  */
  '2',  /*  ²  */
  '3',  /*  ³  */
  'A',  /*  ´  */
  'M',  /*  µ  */
  'P',  /*  ¶  */
  'D',  /*  ·  */
  'C',  /*  ¸  */
  '1',  /*  ¹  */
  'O',  /*  º  */
  'G',  /*  »  */
  '4',  /*  ¼  */
  '2',  /*  ½  */
  '3',  /*  ¾  */
  'Q',  /*  ¿  */
  'A',  /*  À  */
  'A',  /*  Á  */
  'A',  /*  Â  */
  'A',  /*  Ã  */
  'A',  /*  Ä  */
  'A',  /*  Å  */
  'A',  /*  Æ  */
  'C',  /*  Ç  */
  'E',  /*  È  */
  'E',  /*  É  */
  'E',  /*  Ê  */
  'E',  /*  Ë  */
  'I',  /*  Ì  */
  'I',  /*  Í  */
  'I',  /*  Î  */
  'I',  /*  Ï  */
  'D',  /*  Ð  */
  'N',  /*  Ñ  */
  'O',  /*  Ò  */
  'O',  /*  Ó  */
  'O',  /*  Ô  */
  'O',  /*  Õ  */
  'O',  /*  Ö  */
  'X',  /*  ×  */
  'O',  /*  Ø  */
  'U',  /*  Ù  */
  'U',  /*  Ú  */
  'U',  /*  Û  */
  'U',  /*  Ü  */
  'Y',  /*  Ý  */
  'D',  /*  Þ  */
  'S',  /*  ß  */
  'A',  /*  à  */
  'A',  /*  á  */
  'A',  /*  â  */
  'A',  /*  ã  */
  'A',  /*  ä  */
  'A',  /*  å  */
  'A',  /*  æ  */
  'C',  /*  ç  */
  'E',  /*  è  */
  'E',  /*  é  */
  'E',  /*  ê  */
  'E',  /*  ë  */
  'I',  /*  ì  */
  'I',  /*  í  */
  'I',  /*  î  */
  'I',  /*  ï  */
  'D',  /*  ð  */
  'N',  /*  ñ  */
  'O',  /*  ò  */
  'O',  /*  ó  */
  'O',  /*  ô  */
  'O',  /*  õ  */
  'O',  /*  ö  */
  'D',  /*  ÷  */
  'O',  /*  ø  */
  'U',  /*  ù  */
  'U',  /*  ú  */
  'U',  /*  û  */
  'U',  /*  ü  */
  'Y',  /*  ý  */
  'D',  /*  þ  */
  'Y'   /*  ÿ  */
};

static void map_special_characters (char *str)
{
  for (; *str; str++)
    *str = g_conversion_table[*(unsigned char*)str];
}

static void shorten_name (char *name, int max_length)
{
  int len = strlen (name);

  if (len <= max_length)
    return;

  while (len > max_length) {
    int i;
    for (i=len-1; i>=0; i--)
      if (strchr ("AEIOUaeiou", name[i]))
        break;
    if (i<0)
      break;
    memmove (name + i, name + i + 1, len-i);
    len--;
  }
  name[max_length] = 0;
}

char *convert_filename (const char *filename)
{
  char *name, *extension;
  char *dotptr;
  static char result[40];

  if (dotptr = strrchr (filename, '.')) {
    int len = dotptr - filename;
    name = malloc (len + 1);
    memcpy (name, filename, len);
    name[len] = 0;
    extension = strdup (dotptr + 1);
  } else {
    name = strdup ((char*) filename);
    extension = strdup ("");
  }

  if (map_filenames) {
    map_special_characters (name);
    map_special_characters (extension);
  }

  shorten_name (name, short_filenames ? 8 : 30);
  shorten_name (extension, short_filenames ? 3 : (30 - strlen (name)));

  strcpy (result, name);
  strcat (result, ".");
  strcat (result, extension);
  strcat (result, ";1");

  free (name);
  free (extension);

  return result;
}

char *convert_dirname (const char *dirname)
{
  static char result[40];
  
  strcpy (result, dirname);
  if (map_filenames)
    map_special_characters (result);

  shorten_name (result, short_filenames ? 8 : 31);

  return result;
}
