/*
 * mkdtlogin.c
 * A simple utility for generating dtlogin session menu entries.
 * Written by Stefan Teleman (stefan.teleman@gmail.com) on 12/15/2005.
 * Copyright (C) 2005 Stefan Teleman.
 *
 * This simple program is released under the terms of the GNU General
 * Public License (GPL) Version 2.
 * 
 */

#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include <sys/types.h>
#include <dirent.h>
#include <sys/stat.h>
#include <sys/param.h>
#include <errno.h>

static const char* xsession = "Xsession.KDE-3.4.3-32";
static const char* xsession2 = "Xsession2.KDE-3.4.3-32";
static const char* xinitrc = "Xinitrc.KDE-3.4.3-32";
static const char* xresources = "Xresources.KDE-3.4.3-32";

static int printXsessionFile(const char* path, const char* language);
static int printXsession2File(const char* path, const char* language);
static int printXinitrcFile(const char* path, const char* language);
static int printXresourcesFile(const char* path, const char* language);
static void printFileCreationError(const char* path, const char* fileName);
static void checkForRoot(const char* progName);
static void checkDirectories(const char* base, const char* lang);
static void usage(const char* progName);

extern char *optarg;
extern int optind, opterr, optopt;
extern int errno;

int
main(int argc, char* argv[])
{
  int c;
  char* base;
  char* lang;
  char baseInstallPath[MAXPATHLEN +1];
  char resourceInstallPath[MAXPATHLEN +1];
  char language[64];

  if (argc != 5)
    usage(argv[0]);

  while ((c = getopt(argc, argv, "b:l:")) != -1)
  {
    switch(c)
    {
      case 'b':
        base = optarg;
        break;
      case 'l':
        lang = optarg;
        break;
      default:
        usage(argv[0]);
        break;
    }
  }

  checkDirectories(base, lang);

  (void) memset(baseInstallPath, '\0', MAXPATHLEN + 1);
  (void) memset(resourceInstallPath, '\0', MAXPATHLEN + 1);
  (void) memset(language, '\0', 64);

  (void) sprintf(baseInstallPath, "%s/dt/config", base);
  (void) sprintf(language, "%s", lang);
  (void) sprintf(resourceInstallPath, "%s/%s/Xresources.d",
                 baseInstallPath, language);

  if (-1 == printXsessionFile(baseInstallPath, language))
  {
    printFileCreationError(baseInstallPath, xsession);
    return -1;
  }
  if (-1 == printXsession2File(baseInstallPath, language))
  {
    printFileCreationError(baseInstallPath, xsession2);
    return -1;
  }
  if (-1 == printXinitrcFile(baseInstallPath, language))
  {
    printFileCreationError(baseInstallPath, xinitrc);
    return -1;
  }
  if (-1 == printXresourcesFile(resourceInstallPath, language))
  {
    printFileCreationError(resourceInstallPath, xresources);
    return -1;
  }
  return 0;
}

int printXsessionFile(const char* path, const char* language)
{
  FILE* fp;
  char fileName[MAXPATHLEN + 1];

  (void) memset(fileName, '\0', MAXPATHLEN + 1);
  (void) sprintf(fileName, "%s/%s.%s", path, xsession, language);

  if ((fp = fopen(fileName, "w")) == (FILE *) NULL)
  {
    perror("fopen");
    (void) fprintf(stderr, "%s: %s\n", fileName, strerror(errno));
    return -1;
  }
  (void) fprintf(fp, "#!/bin/ksh\n");
  (void) fprintf(fp, "#####################################################################\n");
  (void) fprintf(fp, "###  File:              Xsession.KDE-3.4.3-32\n");
  (void) fprintf(fp, "###\n");
  (void) fprintf(fp, "###  Default Location:  %s\n", fileName);
  (void) fprintf(fp, "###\n");
  (void) fprintf(fp, "###  Purpose:           KDE 3.4.3 session start script\n");
  (void) fprintf(fp, "###\n");
  (void) fprintf(fp, "###  Invoked by:        Solaris Desktop Login Manager (dtlogin)\n");
  (void) fprintf(fp, "###\n");
  (void) fprintf(fp, "#####################################################################\n\n");
  (void) fprintf(fp, "DTDSPMSG=/usr/dt/bin/dtdspmsg\n\n");
  (void) fprintf(fp, "export SESSIONTYPE=\"altDt\"\n");
  (void) fprintf(fp, "export SDT_ALT_SESSION=\"/usr/dt/config/Xsession2.KDE-3.4.3-32.%s\"\n", language);
  (void) fprintf(fp, "export SDT_ALT_HELLO=\"/bin/true\"\n");
  (void) fprintf(fp, "export SDT_NO_TOOLTALK=\"1\"\n");
  (void) fprintf(fp, "export SDT_NO_DTDBCACHE=\"1\"\n");
  (void) fprintf(fp, "export START_SPECKEYSD=\"Yes\"\n\n");
  (void) fprintf(fp, "exec /usr/dt/bin/Xsession\n");
  fclose(fp);
  chmod(fileName, S_IRWXU|S_IRGRP|S_IXGRP|S_IROTH|S_IXOTH);
  chown(fileName, 0, 2);
  return 0;
}

int printXsession2File(const char* path, const char* language)
{
  FILE* fp;
  char fileName[MAXPATHLEN + 1];

  (void) memset(fileName, '\0', MAXPATHLEN + 1);
  (void) sprintf(fileName, "%s/%s.%s", path, xsession2, language);

  if ((fp = fopen(fileName, "w")) == (FILE *) NULL)
  {
    perror("fopen");
    (void) fprintf(stderr, "%s: %s\n", fileName, strerror(errno));
    return -1;
  }
  (void) fprintf(fp, "#!/bin/ksh\n");
  (void) fprintf(fp, "#####################################################################\n");
  (void) fprintf(fp, "###  File:              Xsession2.KDE-3.4.3-32.%s\n", language);
  (void) fprintf(fp, "###\n");
  (void) fprintf(fp, "###  Default Location:  %s.%s\n", fileName, language);
  (void) fprintf(fp, "###\n");
  (void) fprintf(fp, "###  Purpose:           KDE 3.4.3 Desktop start script\n");
  (void) fprintf(fp, "###\n");
  (void) fprintf(fp, "###  Invoked by:        /usr/dt/bin/Xsession\n");
  (void) fprintf(fp, "###\n");
  (void) fprintf(fp, "#####################################################################\n\n");
  (void) fprintf(fp, "# First a little namespace cleanup of vars associated with this\n# (and /usr/dt/bin/Xsession.ow) scripts.\n\n");
  (void) fprintf(fp, "unset SDT_ALT_SESSION\n");
  (void) fprintf(fp, "unset SDT_ALT_HELLO\n");
  (void) fprintf(fp, "unset SDT_NO_DSDM\n\n");
  (void) fprintf(fp, "#\n# Find \"xinitrc\" file by standard precedence rules and start\n# the user\'s Desktop.\n#\n\n");
  (void) fprintf(fp, "DEFAULT_XINITRC=\"/usr/dt/config/Xinitrc.KDE-3.4.3-32.%s\"\n", language);
  (void) fprintf(fp, "HOME_XINITRC=\"$HOME/.xinitrc\"\n\n");
  (void) fprintf(fp, "if [ -f $HOME_XINITRC ] ; then\n");
  (void) fprintf(fp, "\tXINITRC=$HOME_XINITRC\n");
  (void) fprintf(fp, "else\n");
  (void) fprintf(fp, "\tXINITRC=$DEFAULT_XINITRC\nfi\n\n");
  (void) fprintf(fp, "echo \'Welcome to KDE 3.4.3 \'\n\n");
  (void) fprintf(fp, "if [ -x /usr/dt/bin/xmbind ] ; then\n");
  (void) fprintf(fp, "\t/usr/dt/bin/xmbind\nfi\n\n");
  (void) fprintf(fp, "if [ -f $XINITRC ] ; then\n");
  (void) fprintf(fp, "\techo \"using xinitrc file: $XINITRC\"\n");
  (void) fprintf(fp, "/bin/ksh $XINITRC\nfi\n");
  (void) fclose(fp);
  chmod(fileName, S_IRWXU|S_IRGRP|S_IXGRP|S_IROTH|S_IXOTH);
  chown(fileName, 0, 2);
  return 0;
}

int printXinitrcFile(const char* path, const char* language)
{
  FILE* fp;
  char fileName[MAXPATHLEN + 1];

  (void) memset(fileName, '\0', MAXPATHLEN + 1);
  (void) sprintf(fileName, "%s/%s.%s", path, xinitrc, language);

  if ((fp = fopen(fileName, "w")) == (FILE *) NULL)
  {
    perror("fopen");
    (void) fprintf(stderr, "%s: %s\n", fileName, strerror(errno));
    return -1;
  }
  (void) fprintf(fp, "#!/bin/ksh\n");
  (void) fprintf(fp, "#####################################################################\n");
  (void) fprintf(fp, "###  File:              Xinitrc.KDE-3.4.3-32.%s\n", language);
  (void) fprintf(fp, "###\n");
  (void) fprintf(fp, "###  Default Location:  %s.%s\n", fileName, language);
  (void) fprintf(fp, "###\n");
  (void) fprintf(fp, "###  Purpose:           Xsession startup script\n");
  (void) fprintf(fp, "###\n");
  (void) fprintf(fp, "###  Invoked by:        /usr/dt/bin/Xsession\n");
  (void) fprintf(fp, "###\n");
  (void) fprintf(fp, "#####################################################################\n\n");
  (void) fprintf(fp, "export MLIBHOME=\"/usr\"\n");
  (void) fprintf(fp, "export QTDIR=\"/opt/qt-3.3.4-32\"\n");
  (void) fprintf(fp, "export I18NPATH=\"/opt/fsw4sun/share/locale:/usr/lib/locale:/usr/openwin/locale:/opt/kde-3.4.3/share/locale\"\n");
  (void) fprintf(fp, "export LANG=\"%s\"\n", language);
  (void) fprintf(fp, "export LC_ALL=\"%s\"\n", language);
  (void) fprintf(fp, "export KDE_RELEASE=\"KDE-3.4.3\"\n");
  (void) fprintf(fp, "export KDE_MULTIHEAD=\"false\"\n");
  (void) fprintf(fp, "export KDEDIR=\"/opt/kde-3.4.3\"\n");
  (void) fprintf(fp, "export KDEDIRS=\"/opt/kde-3.4.3\"\n");
  (void) fprintf(fp, "export KDEROOT=\"/opt/kde-3.4.3\"\n");
  (void) fprintf(fp, "export LD_LIBRARY_PATH=\"${QTDIR}/lib:${KDEROOT}/lib:${KDEROOT}/lib/kde3\"\n");
  (void) fprintf(fp, "export PATH=\"/opt/fsw4sun/bin:/usr/bin:/usr/sbin:${QTDIR}/bin:${KDEROOT}/bin:.:/usr/dt/bin:/usr/X11/bin:/usr/openwin/bin:/usr/ccs/bin\"\n\n");
  (void) fprintf(fp, "if [ \"x$LC_ALL\" = x -a \"x$LANG\" = x -o \"x$LANG\" = xC ] ; then\n");
  (void) fprintf(fp, "\texport LANG=\"%s\"\n", language);
  (void) fprintf(fp, "\texport LC_ALL=\"%s\"\nfi\n\n", language);
  (void) fprintf(fp, "if [ -f ${HOME}/.Xdefaults ] ; then\n");
  (void) fprintf(fp, "\txrdb -load ${HOME}/.Xdefaults    # Load Users X11 resource database\nfi\n\n");
  (void) fprintf(fp, "if [ -f ${HOME}/.Xauthority ] ; then\n");
  (void) fprintf(fp, "\txauth merge ${HOME}/.Xauthority\nfi\n\n");
  (void) fprintf(fp, "## export KDE_TRACE_FILE=\"/dev/null\"\n");
  (void) fprintf(fp, "export KDE_TRACE_FILE=\"/tmp/${USER}-startkde.out\"\n");
  (void) fprintf(fp, "echo \"Starting KDE 3.4.3\"\n");
  (void) fprintf(fp, "cat /dev/null > ${KDE_TRACE_FILE}\n");
  (void) fprintf(fp, "exec ${KDEROOT}/bin/startkde.%s > ${KDE_TRACE_FILE} 2>&1\n", language);
  (void) fclose(fp);
  chmod(fileName, S_IRWXU|S_IRGRP|S_IXGRP|S_IROTH|S_IXOTH);
  chown(fileName, 0, 2);
  return 0;
}

int printXresourcesFile(const char* path, const char* language)
{
  FILE* fp;
  char fileName[MAXPATHLEN + 1];

  (void) memset(fileName, '\0', MAXPATHLEN + 1);
  (void) sprintf(fileName, "%s/%s.%s", path, xresources, language);

  if ((fp = fopen(fileName, "w")) == (FILE *) NULL)
  {
    perror("fopen");
    (void) fprintf(stderr, "%s: %s\n", fileName, strerror(errno));
    return -1;
  }
  (void) fprintf(fp, "Dtlogin*altDtsIncrement:  True\n");
  (void) fprintf(fp, "Dtlogin*altDtName:      KDE 3.4.3 [32-bit %s]\n", language);
  (void) fprintf(fp, "Dtlogin*altDtKey:       /opt/kde-3.4.3/bin/startkde.%s\n", language);
  (void) fprintf(fp, "Dtlogin*altDtStart:     /usr/dt/config/Xsession.KDE-3.4.3-32.%s\n", language);
  (void) fprintf(fp, "Dtlogin*altDtLogo:      /usr/dt/appconfig/icons/C/KDE341Login\n");
  (void) fprintf(fp, "Dtlogin*altDtXserverFlags: -defdepth 24\n");
  (void) fclose(fp);
  chmod(fileName, S_IRWXU|S_IRGRP|S_IXGRP|S_IROTH|S_IXOTH);
  chown(fileName, 0, 2);
  return 0;
}

void checkForRoot(const char* progName)
{
  if (getuid() != 0)
  {
    (void) fprintf(stderr, "%s: You must be root to do this.\n", progName);
    exit(1);
  }
}

void checkDirectories(const char* base, const char* lang)
{
  char dirPath[MAXPATHLEN +1];
  DIR* dirp = 0L;

  (void) memset(dirPath, '\0', MAXPATHLEN +1);
  (void) sprintf(dirPath, "%s/dt/config", base);

  dirp = opendir(dirPath);
  if (dirp == NULL)
  {
    (void) fprintf(stderr, "Error opening directory %s: %s\n", dirPath, strerror(errno));
    exit(1);
  }
  closedir(dirp);

  (void) strcat(dirPath, "/");
  (void) strcat(dirPath, lang);
  (void) strcat(dirPath, "/Xresources.d");
  dirp = opendir(dirPath);
  if (dirp == NULL)
  {
    (void) fprintf(stderr, "Error opening directory %s: %s\n", dirPath, strerror(errno));
    exit(1);
  }
  closedir(dirp);
}

void printFileCreationError(const char* path, const char* fileName)
{
  (void) fprintf(stderr, "creating file %s/%s failed!\n", path, fileName);
}

void usage(const char* progName)
{
  (void) fprintf(stderr, "Usage: %s -b <base-installation-dir> -l <language>\n", progName);
  exit(1);
}

// vim: ts=2 sw=2 et

