/* proc.c
 * Copyright (C) 2004, 2005 Sylvain Cresto <scresto@gmail.com>
 *
 * This file is part of graveman!
 *
 * graveman! is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2, or
 * (at your option) any later version.
 * 
 * graveman! is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
 * General Public License for more details.
 * 
 * You should have received a copy of the GNU General Public License
 * along with program; see the file COPYING. If not, write to the
 * Free Software Foundation, Inc., 59 Temple Place - Suite 330, Boston,
 * MA 02111-1307, USA. 
 * 
 * URL: http://www.nongnu.org/graveman/
 *
 */

#include "graveman.h"

#define DRIVE_NAME "drive name:"
#define DRIVE_SPEED "drive speed:"
#define DRIVE_WRITE_CDR "Can write CD-R:"
#define DRIVE_WRITE_CDRW "Can write CD-RW:"
#define DRIVE_READ_DVD "Can read DVD:"
#define DRIVE_WRITE_DVDR "Can write DVD-R:"
#define DRIVE_MAX_CDREAD_SPEED "drive speed:"

GHashTable *Gproccdrominfo = NULL;

void proc_free_cdrominfo()
{
  if (Gproccdrominfo) {    
    g_hash_table_destroy(Gproccdrominfo);
    Gproccdrominfo = NULL;
  }
}

gboolean proc_init_cdrominfo (GError **Aerror)
{
  gchar *Lcontent;
  gchar **Larrbuf;
  gint i = 0, Lpos = 0;
  gchar *s, *p, *Lcurdev;
  gboolean Llast = FALSE;
  gchar Lcommand[_BUF_SIZE];

  if (!g_file_get_contents("/proc/sys/dev/cdrom/info", &Lcontent, NULL, Aerror)) {
    return FALSE;
  }

  proc_free_cdrominfo();
  Gproccdrominfo = g_hash_table_new_full(g_str_hash, g_str_equal, g_free, NULL);

  Larrbuf = g_strsplit(Lcontent, "\n", 0);

  for (i=0; Larrbuf[i]; i++) {
    if (!strncmp(Larrbuf[i], DRIVE_NAME, strlen(DRIVE_NAME))) {
      s=Larrbuf[i] + strlen(DRIVE_NAME);

      while (Llast == FALSE) {
        while (*s==' ' || *s==9) s++;

        if (*s<65) break;

        p=s;
        while (*s>32) s++;
        if (!*s) Llast = TRUE;
        *(s++)=0;

        Lcurdev = g_strdup_printf("/dev/%s", p);
        g_hash_table_insert(Gproccdrominfo, Lcurdev, g_strdup_printf("%d", Lpos++));

        g_snprintf(Lcommand, sizeof(Lcommand)-1, "/bin/umount %s", Lcurdev);
        _DEB("try to umount [%s]", Lcommand);

        g_spawn_command_line_async(Lcommand, NULL);
      }

    }

  }

  g_strfreev(Larrbuf);
  g_free(Lcontent);

  return TRUE;
}

/* actually only for DVD detection */
gboolean proc_maj_drive_info (Tdriveinfo *Adevice, GError **Aerror)
{
  gchar *Lcontent;
  gchar **Larrbuf;
  gint i = 0, j;
  gchar *s;
  GSList *Lcur;
  gchar *Lval;
  gint Lpos = -1;

  if (!Gproccdrominfo) return FALSE;

  for (Lcur = Adevice->dev; Lcur; Lcur = g_slist_next(Lcur)) {
    if ((Lval=g_hash_table_lookup(Gproccdrominfo, (gchar *)Lcur->data))) {
      Lpos = atoi(Lval);
      break;
    }
  }

  if (Lpos == -1) return FALSE;

  if (!g_file_get_contents("/proc/sys/dev/cdrom/info", &Lcontent, NULL, Aerror)) {
    return FALSE;
  }

  Larrbuf = g_strsplit(Lcontent, "\n", 0);

  for (i=0; Larrbuf[i]; i++) {
    s=Larrbuf[i];
    if (!*s) continue;
    if (!strncmp(s, DRIVE_READ_DVD, strlen(DRIVE_READ_DVD))) {
      s+=strlen(DRIVE_READ_DVD);
      for (j=0; j <= Lpos; j++) { 
        s++;
        while (*s==' ' || *s==9) s++;
      }

      if (*s=='1') {
        Adevice->type |= _READ_DVD;
        _DEB("proc : READ_DVD!");
      }
    } else if (!strncmp(s, DRIVE_WRITE_DVDR, strlen(DRIVE_WRITE_DVDR))) {
      s+=strlen(DRIVE_WRITE_DVDR);
      for (j=0; j <= Lpos; j++) { 
        s++;
        while (*s==' ' || *s==9) s++;
      }

      if (*s=='1') {
        Adevice->type |= _WRITE_DVD;
        _DEB("proc : WRITE_DVD!");
      }
    }
  }

  g_strfreev(Larrbuf);
  g_free(Lcontent);

  return TRUE;
}

/*
 * vim:et:ts=8:sts=2:sw=2
 */
