Creazione automatica di un file di log per inviare quesiti al forum: differenze tra le versioni

Da Guide@Debianizzati.Org.
Vai alla navigazione Vai alla ricerca
mNessun oggetto della modifica
(→‎Script: nuova versione)
Riga 30: Riga 30:
== Script ==
== Script ==
<pre>
<pre>
#!/bin/bash
#! /bin/bash
 
# --------------------------------------------------------------------------
# Impostazioni
# --------------------------------------------------------------------------
 
# I file creati saranno leggibili e scrivibili da tutti
umask 0011
 
# --------------------------------------------------------------------------
# Funzioni che sovrascrivono comandi
# --------------------------------------------------------------------------
 
# Rimpiazza echo ed echo -n, impedendo echo -e e le possibili combinazioni
# Sintassi accettata:
#  echo -n "testo"  # stampa senza a capo finale
#  echo "testo"    # stampa con a capo finale
#  echo            # stampa una riga vuota
function echo {
  if [ $# -gt 1 ] && [ "$1" = "-n" ]; then
    shift
    printf %s "$*"
  else
    printf %s\\n "$*"
  fi
}
 
# --------------------------------------------------------------------------
# Costanti
# --------------------------------------------------------------------------


# Codename per stable e testing. Da modificare nei successivi rilasci di Debian
# Codename per stable e testing. Da modificare nei successivi rilasci di Debian
STABLE="wheezy"
readonly STABLE="wheezy"
TESTING="jessie"
readonly TESTING="jessie"


# Path dei comandi dello script
# Path dei comandi dello script
PATH=/bin:/sbin:/usr/bin:/usr/sbin
readonly PATH="/bin:/sbin:/usr/bin:/usr/sbin"


# Nome del file di log in base alla data corrente
# Nome del file di log in base alla data corrente
log="log_`date +%d%b_%H%M%S`"
readonly log="log_$(date '+%d%b_%H%M%S')"


# Nome del file compresso. Viene usata l'estensione .bz2 a meno
# Nome del file compresso. Viene usata l'estensione .bz2 a meno
# che non venga modificata da _compress
# che non venga modificata da _compress
complog="$log.bz2"
readonly complog="${log}.bz2"


# I file creati saranno leggibili e scrivibili da tutti
# nome utente
umask 0011
utente=$(logname) &&
[ "$utente" != "root" ] || {
  utente=
  tmputente=
  for tmputente in $(users); do
    if [ "$tmputente" = "root" ]; then
      continue
    elif [ -z "$utente" ]; then
      utente=$tmputente
    elif [ "$utente" != "$tmputente" ]; then
      utente=
      break
    fi
  done
  if [ -z "$utente" ]; then
    # NOTA: "root" è permesso (solo) se scelto esplicitamente dall'utente
    echo -n "Inserisci il tuo nome utente: "
    read tmputente &&
    # non può contenere: spazi, tabulazioni, nuove righe; né essere vuota
    [ -n "${tmputente##*[[:space:]]*}" ] &&
    # l'utente deve aver effettuato il login (anche in altre console)
    case " $(users) " in
      *" ${tmputente} "* ) true
                          ;;
      * ) false
          ;;
    esac || {
      echo "Nome utente invalido o non ha effettuato il login!" >&2
      exit 255
    }
    utente=$tmputente
  fi
  unset tmputente
}
readonly utente


# Nome utente e nome host
# nome host
utente=`logname`
readonly nomehost=$(hostname)
nomehost=`hostname`


# Codici stile carattere
# Codici stile carattere
ROSSO="\033[01;31m" # colore rosso e grassetto
readonly ROSSO="\033[01;31m" # colore rosso e grassetto
VERDE="\033[01;32m" # colore verde e grassetto
readonly VERDE="\033[01;32m" # colore verde e grassetto
BOLD="\033[01m"       # grassetto
readonly BOLD="\033[01m"       # grassetto
FINE="\033[0m"         # reset
readonly FINE="\033[0m"         # reset
 


# --------------------------------------------------------------------------
# --------------------------------------------------------------------------
Riga 71: Riga 132:
*                                                                              *
*                                                                              *
*  Script che crea un log utile alla risoluzione dei problemi più comuni        *
*  Script che crea un log utile alla risoluzione dei problemi più comuni        *
*  Versione 1.0.38                                                             *
*  Versione 1.0.39                                                             *
*                                                                              *
*                                                                              *
*********************************************************************************"
*********************************************************************************"
Riga 86: Riga 147:
-- Verrà creato un file in formato compresso da inviare al forum"
-- Verrà creato un file in formato compresso da inviare al forum"
   echo -n "Continuare [S/n]? "
   echo -n "Continuare [S/n]? "
   read risp
   read risp || risp="ERROR"
    
    
   # Se non viene premuto "s" o "S" o [Invio], lo script termina
   # Se non viene premuto "s" o "S" o [Invio], lo script termina
   ! [ "$risp" = "s" -o "$risp" = "S" -o "$risp" = "" ] && _exit
   [ -z "$risp" ] || [ "$risp" = "s" ] || [ "$risp" = "S" ] || _exit
}
}


Riga 101: Riga 162:
   # stesso nome di quelli che verranno creati, lo script chiede se cancellarli o meno
   # stesso nome di quelli che verranno creati, lo script chiede se cancellarli o meno
   local risp
   local risp
   if [ -f $log -o -f $log.zip -o -f $log.bz2 -o -f $log.tgz ]; then
   if [ -f "$log" ] || [ -f "${log}.zip" ] || [ -f "${log}.bz2" ] || [ -f "${log}.tgz" ]; then
     echo -en "\nEsiste già un file $log, $log.zip, $log.bz2 o $log.tgz nella directory corrente.\nSovrascivere [S/n]? "
     echo $'\n'"Esiste già un file ${log}, ${log}.zip, ${log}.bz2 o ${log}.tgz nella directory corrente."
    echo -n "Sovrascivere [S/n]? "
     read risp
     read risp
     case $risp in
     case "$risp" in
       ""|[Ss]) rm -f $log $log.zip $log.bz2 $log.tgz  ;;
       ""|[Ss]) rm -f -- "$log" "${log}.zip" "${log}.bz2" "${log}.tgz" ;;
       *)      _exit
       *)      _exit
     esac
     esac
   fi
   fi
}
}


# --------------------------------------------------------------------------
# --------------------------------------------------------------------------
Riga 128: Riga 189:


   # termina la funzione se il log è più grande di chunk_size x 4 (numero di parti impostate)
   # termina la funzione se il log è più grande di chunk_size x 4 (numero di parti impostate)
   if [ `du -k $log | cut -f1` -gt 240 ]; then
   if [ "$(du -k "$log" | cut -f1)" -gt 240 ]; then
     echo "Log troppo grande per essere inviato a paste.debian.net"
     echo "Log troppo grande per essere inviato a paste.debian.net"
     echo "Allegare il file compresso alla discussione sul forum."
     echo "Allegare il file compresso alla discussione sul forum."
Riga 136: Riga 197:
   # rinomina parti di log preesistenti (se ve ne sono)
   # rinomina parti di log preesistenti (se ve ne sono)
   # scarta i messaggi di errore (se presenti)
   # scarta i messaggi di errore (se presenti)
   rename "s/$chunk_prefix/old-$chunk_prefix-$(date +%s)/g" $chunk_prefix.* > /dev/null 2>&1
   rename "s/${chunk_prefix}/old-${chunk_prefix}-$(date '+%s')/" "$chunk_prefix".* > /dev/null 2>&1
   
   
   # dividi il file di log in parti di $chunk_size bytes senza spezzare le linee
   # dividi il file di log in parti di $chunk_size bytes senza spezzare le linee
   # scarta i messaggi di errore (se presenti) per log di dimensione superiore a 10 parti
   # scarta i messaggi di errore (se presenti) per log di dimensione superiore a 10 parti
   # (max 10 parti con l'opzione -a)
   # (max 10 parti con l'opzione -a)
   split -a 1 -d -C $chunk_size $log $chunk_prefix. > /dev/null 2>&1
   split -a 1 -d -C "$chunk_size" "$log" "${chunk_prefix}." > /dev/null 2>&1
   
   
   # comunica il numero di parti inviate
   # comunica il numero di parti inviate
   chunk_num=$( ls -1 $chunk_prefix.* | wc -l )
   chunk_num=$(find . -maxdepth 1 -type f -name "${chunk_prefix}.*" -printf x |
   if [ $chunk_num = 1 ]; then
              wc -c)
       echo -e "\nIl log sarà inviato in un singolo file."
   if [ "$chunk_num" = 1 ]; then
       echo $'\nIl log sarà inviato in un singolo file.'
   else
   else
       echo -e "\nIl log sarà inviato in $chunk_num parti."
       echo $'\n'"Il log sarà inviato in ${chunk_num} parti."
   fi
   fi
   
   
   # invia al massimo 4 parti
   # invia al massimo 4 parti
   echo -e "\nIl log è consultabile ai seguenti indirizzi:"
   echo $'\nIl log è consultabile ai seguenti indirizzi:'
   for chunkfile in $chunk_prefix.{0..3}; do
   for chunkfile in "${chunk_prefix}."[0-3]; do
   
   
     # verifica l'esistenza del file da inviare
     # verifica l'esistenza del file da inviare
     if [ -f $chunkfile ]; then
     if [ -f "$chunkfile" ]; then


     # invia dati tramite pastebinit, l'output d'errore viene soppresso
     # invia dati tramite pastebinit, l'output d'errore viene soppresso
     pastelink="$(pastebinit -a '' -b $paste_url -i $chunkfile 2>/dev/null)"
     pastelink=$(pastebinit -a '' -b "$paste_url" -i "$chunkfile" 2>/dev/null)
      
      
       if [ $? = 0 ]; then
       if [ $? = 0 ]; then
Riga 165: Riga 227:
        
        
  # controlla URL restituita da pastebinit
  # controlla URL restituita da pastebinit
  case $pastelink in
  case "$pastelink" in
  # verifica in caso di url corretta
  # verifica in caso di url corretta
  "$paste_url"/[0-9]*)
  "$paste_url"/[0-9]*)
      echo ".. inviato $chunkfile all'indirizzo $pastelink"
      echo ".. inviato ${chunkfile} all'indirizzo ${pastelink}"
      ;;
      ;;
  # verifica in caso di url non corretta
  # verifica in caso di url non corretta
  *)
  *)
      echo ".. $paste_url ha restituito una URL non valida ($pastelink) per $chunkfile!"
      echo ".. ${paste_url} ha restituito una URL non valida (${pastelink}) per ${chunkfile}!"
      paste_exit_status=1
      paste_exit_status=1
  esac
  esac
Riga 178: Riga 240:
       else
       else
  # Invio fallito (pastebinit exit status = 1)
  # Invio fallito (pastebinit exit status = 1)
  echo ".. non riuscito invio $chunkfile"
  echo ".. non riuscito invio ${chunkfile}"
  paste_exit_status=1
  paste_exit_status=1
       fi
       fi
Riga 187: Riga 249:
   
   
   # cancella le parti di log inviate
   # cancella le parti di log inviate
   rm -f $chunk_prefix.{0..9}
   for chunkfile in "./${chunk_prefix}."[0-9]*; do
    if [ -f "$chunkfile" ]; then
      rm -f -- "$chunkfile"
    fi
  done
   
   
   return $paste_exit_status
   return $paste_exit_status
Riga 197: Riga 263:
   # Pastebinit è installato?
   # Pastebinit è installato?
   if [ ! -f /usr/bin/pastebinit ]; then
   if [ ! -f /usr/bin/pastebinit ]; then
     echo -e "\nNon è possibile inviare il log a paste.debian.net\nIl pacchetto 'pastebinit' non è installato."
     echo $'\nNon è possibile inviare il log a paste.debian.net\nIl pacchetto "pastebinit" non è installato.'
     return 1
     return 1
   fi
   fi
   # Invia il file log.txt a paste.debian.net
   # Invia il file log.txt a paste.debian.net
   echo -en "\nInviare il log a http://paste.debian.net [S/n]? "
   echo -n $'\nInviare il log a http://paste.debian.net [S/n]? '
   read risp
   read risp
   case $risp in
   case "$risp" in
     ""|[Ss])
     ""|[Ss])
       _split_and_send
       _split_and_send
       if [ $? == 0 ]; then
       if [ $? = 0 ]; then
         echo -e "\nIl log è stato inviato"
         echo $'\nIl log è stato inviato'
       else
       else
         echo -e "\nSi sono verificati errori nell'invio del log!"
         echo $'\nSi sono verificati errori nell\'invio del log!'
       fi
       fi
       ;;
       ;;
Riga 223: Riga 289:
# Funzione richiamata in caso di corretta/scorretta creazione del file compresso
# Funzione richiamata in caso di corretta/scorretta creazione del file compresso
function _compress_ok {
function _compress_ok {
echo "File compresso creato correttamente nella directory corrente."
  echo "File compresso creato correttamente nella directory corrente."
}
}


function _compress_err {
function _compress_err {
echo "Errore nella creazione del file compresso."
  echo "Errore nella creazione del file compresso."
}
}


Riga 234: Riga 300:
function _compress {
function _compress {
   local risp
   local risp
   echo -en "\nCreare un file compresso [S/n]? "
   echo -n $'\nCreare un file compresso [S/n]? '
   read risp
   read risp
   case $risp in
   case "$risp" in
     ""|[Ss])
     ""|[Ss])
       echo "Sta per essere creato un file compresso..."
       echo "Sta per essere creato un file compresso..."
       sleep 1
       sleep 1
       if [ -f /bin/bzip2 ]; then
       if [ -f /bin/bzip2 ]; then
         bzip2 -k9 $log && _compress_ok || _compress_err
         bzip2 -k9 "$log" && _compress_ok || _compress_err
       elif [ -f /usr/bin/zip ]; then
       elif [ -f /usr/bin/zip ]; then
         zip $log.zip $log && _compress_ok || _compress_err
         zip "${log}.zip" "$log" && _compress_ok || _compress_err
         complog="$log.zip"  
         complog="${log}.zip"
       else
       else
         tar czf $log.tgz $log && _compress_ok || _compress_err
         tar czf "${log}.tgz" "$log" && _compress_ok || _compress_err
         complog="$log.tgz"
         complog="${log}.tgz"
       fi
       fi
       ;;
       ;;
Riga 278: Riga 344:
     echo -n "Scegliere il numero corrispondente: "
     echo -n "Scegliere il numero corrispondente: "
     read num
     read num
     case $num in
     case "$num" in
         [1-7]) _wait  ;;& # ;;& -> va alla successiva occorrenza del carattere immesso
         [1-7]) _wait  ;;& # ;;& -> va alla successiva occorrenza del carattere immesso
             1) echo -e "### Problemi di rete ###\n"           > $log && _rete  ;;&
             1) echo $'### Problemi di rete ###\n'           > "$log" && _rete  ;;&
             2) echo -e "### Problemi video ###\n"             > $log && _video  ;;&
             2) echo $'### Problemi video ###\n'             > "$log" && _video  ;;&
             3) echo -e "### Problemi audio ###\n"             > $log && _audio  ;;&
             3) echo $'### Problemi audio ###\n'             > "$log" && _audio  ;;&
             4) echo -e "### Problemi APT ###\n"               > $log && _apt    ;;&
             4) echo $'### Problemi APT ###\n'               > "$log" && _apt    ;;&
             5) echo -e "### Problemi mount-unmount ###\n"     > $log && _mount  ;;&
             5) echo $'### Problemi mount-unmount ###\n'     > "$log" && _mount  ;;&
             6) echo -e "### Problemi touchpad ###\n"           > $log && _tpad  ;;&
             6) echo $'### Problemi touchpad ###\n'           > "$log" && _tpad  ;;&
             7) echo -e "### Solo informazioni generiche ###\n" > $log && _common ;;&
             7) echo $'### Solo informazioni generiche ###\n' > "$log" && _common ;;&
         [1-7]) break  ;; # Termina il ciclo 'while'
         [1-7]) break  ;; # Termina il ciclo 'while'
       0) _exit  ;; # È stato inserito '0' . Uscita dallo script
       0) _exit  ;; # È stato inserito '0' . Uscita dallo script
Riga 299: Riga 365:
# Funzioni varie
# Funzioni varie
# --------------------------------------------------------------------------
# --------------------------------------------------------------------------
# Funzione che stampa solo lo spazio e il nome del comando, prima di eseguirlo
function _prompt {
  echo -n "[ ]  $*"
}


# Funzione che stampa un pallino di colore verde in caso di comando con output
# Funzione che stampa un pallino di colore verde in caso di comando con output
function _ok {
function _ok {
   echo -e "[$VERDE•$FINE]  $1"
   printf %b "\r[${VERDE}•${FINE}"
  echo -n "$*"
  # cancella fino a fine schermo e va a capo
  tput ed
  echo
}
}


# Funzione che stampa una pallino rosso in caso di comando privo di output
# Funzione che stampa una pallino rosso in caso di comando privo di output
function _error {
function _error {
   echo -e "[$ROSSO•$FINE]  $1"
   printf %b "\r[${ROSSO}•${FINE}"
  echo -n "$*"
  # cancella fino a fine schermo e va a capo
  tput ed
  echo
}
 
# Funzione che stampa in grassetto gli argomenti
function _bold {
  printf %b "$BOLD"
  echo -n "$*"
  printf %b\\n "$FINE"
}
}


Riga 316: Riga 402:
******************************************
******************************************
$1
$1
******************************************" >> $log
******************************************" >> "$log"
}
}


# Funzione che stampa un messaggio di attesa e aspetta 2 secondi
# Funzione che stampa un messaggio di attesa e aspetta 2 secondi
function _wait {
function _wait {
   echo -e "\nCreazione del log in corso. Attendere pochi secondi...\n"
   echo $'\nCreazione del log in corso...\n'
  sleep 2
}
}


# Stampa la data corrente nel file di log
# Stampa la data corrente nel file di log
function _data {
function _data {
   echo "Log creato il `date +%d\ %B\ %Y\ alle\ %H.%M`" >> $log
   echo "Log creato il $(date '+%d %B %Y alle %H.%M')" >> "$log"
}
}


Riga 334: Riga 419:


  # Sostituisce il nome utente e il nome host con 'nomeutente' e 'nomehost' se diversi da [dD]ebian
  # Sostituisce il nome utente e il nome host con 'nomeutente' e 'nomehost' se diversi da [dD]ebian
  [ "$nomehost" != "Debian" -a "$nomehost" != "debian" ] && sed -i -e "s/$nomehost/nomehost/g" $log
  [ "$nomehost" != "Debian" ] && [ "$nomehost" != "debian" ] && sed -i -e "s/${nomehost}/nomehost/g" "$log"
  [ "$utente" != "Debian" -a "$utente" != "debian" ] && sed -i -e "s/$utente/nomeutente/g" $log
  [ "$utente" != "Debian" ] && [ "$utente" != "debian" ] && sed -i -e "s/${utente}/nomeutente/g" "$log"


  # Nasconde gli ESSID gestiti attraverso Network Manager
  # Nasconde gli ESSID gestiti attraverso Network Manager
  local var file mydir="/etc/NetworkManager/system-connections/"
  local var file mydir="/etc/NetworkManager/system-connections/"


  if [ -d $mydir ]; then # se esiste la directory /etc/NetworkManager/system-connections/ ...
  if [ -d "$mydir" ]; then # se esiste la directory /etc/NetworkManager/system-connections/ ...
     for file in $mydir/*; do # ciclo attraverso il contenuto della directory
     for file in "$mydir"/*; do # ciclo attraverso il contenuto della directory
       if [ -f "$file" ]; then # se l'elemento è un file...
       if [ -f "$file" ]; then # se l'elemento è un file...
           var="`sed -n "s/ssid=//p" "$file"`" # ... var conterrà l'eventuale ESSID...
           var=$(sed -n "s/ssid=//p" "$file") # ... var conterrà l'eventuale ESSID...
           if [ "$var" ]; then # ... e se è diverso dalla stringa vuota...
           if [ -n "$var" ]; then # ... e se è diverso dalla stringa vuota...
             sed -i "s/$var/\*script-removed\*/g" $log # ... lo nasconde nel file di log
             sed -i "s/${var}/\*script-removed\*/g" "$log" # ... lo nasconde nel file di log
           fi
           fi
       fi
       fi
Riga 352: Riga 437:


  # Nasconde nel log i i nomi delle connessioni gestite da NetworkManager
  # Nasconde nel log i i nomi delle connessioni gestite da NetworkManager
  sed -i -r "s/(NetworkManager.*keyfile.*((parsing)|(read connection))).*/\1 \*script-removed\*/" $log
  sed -i -r "s/(NetworkManager.*keyfile.*((parsing)|(read connection))).*/\1 \*script-removed\*/" "$log"
}
}


Riga 361: Riga 446:
    
    
   if [ -f "$file" ]; then
   if [ -f "$file" ]; then
     lastdate=`sed -n '/^Start-Date/h ; $p' $file | awk '{print $2}'`
     lastdate=$(sed -n '/^Start-Date/h ; $p' "$file" | awk '{print $2}')
     # se il file history.log non contiene la data dell'ultimo aggiornamento, viene utilizzato history.log.1.gz
     # se il file history.log non contiene la data dell'ultimo aggiornamento, viene utilizzato history.log.1.gz
     [ -z "$lastdate" ] && [ -f "$file.1.gz" ] && lastdate=`zcat $file.1.gz | sed -n '/^Start-Date/h ; $p' | awk '{print $2}'`
     [ -z "$lastdate" ] && [ -f "${file}.1.gz" ] && lastdate=$(zcat "${file}.1.gz" | sed -n '/^Start-Date/h ; $p' | awk '{print $2}')


     # variabile che contiene la data in formato "giorno mese anno"
     # variabile che contiene la data in formato "giorno mese anno"
     convdate=`date +%d\ %B\ %Y -d "$lastdate"`
     convdate=$(date -d "$lastdate" '+%d %B %Y')
      
      
     echo -e "\nUltimo aggiornamento del sistema: $convdate" >> $log
     echo $'\n'"Ultimo aggiornamento del sistema: ${convdate}" >> "$log"
   fi
   fi
}
}
Riga 374: Riga 459:
# Funzione che stampa un messaggio che indica i file creati e poi termina lo script
# Funzione che stampa un messaggio che indica i file creati e poi termina lo script
function _exit {
function _exit {
   if [ -f $log ]; then
   if [ -f "$log" ]; then
     echo -e "\nFile contenente il log dello script: $BOLD$log$FINE"
     echo -n $'\nFile contenente il log dello script: '
    _bold "$log"
   else
   else
     echo -e "\nNon è stato creato un file di log"
     echo $'\nNon è stato creato un file di log'
   fi
   fi
    
    
   if [ -f $complog ]; then
   if [ -f "$complog" ]; then
     echo -e "File compresso da allegare alla discussione sul forum: $BOLD$complog$FINE"
     echo -n "File compresso da allegare alla discussione sul forum: "
    _bold "$complog"
   else
   else
     echo "Non è stato creato un file compresso del log"
     echo "Non è stato creato un file compresso del log"
   fi
   fi
    
    
   echo -e "Script terminato\n"
   echo $'Script terminato\n'
   exit 0
   exit 0
}
}
Riga 467: Riga 554:
   local risp alsaurl="http://www.alsa-project.org/alsa-info.sh"
   local risp alsaurl="http://www.alsa-project.org/alsa-info.sh"
    
    
   echo -e "\nI log relativi ai problemi audio sono ricavati attraverso lo script di debug"
   echo $'\nI log relativi ai problemi audio sono ricavati attraverso lo script di debug'
   echo "ALSA prelevabile all'indirizzo: $alsaurl"
   echo "ALSA prelevabile all'indirizzo: ${alsaurl}"
   echo -en "\nVerrà ora scaricato e eseguito lo script ALSA. Continuare [S/n]? "
   echo -n $'\nVerrà ora scaricato e eseguito lo script ALSA. Continuare [S/n]? '
   read risp
   read risp
   case $risp in
   case "$risp" in
     ""|[Ss])
     ""|[Ss])
  # wget esiste?
  # wget esiste?
Riga 479: Riga 566:
  fi
  fi
  # Crea un file temporaneo in /tmp che conterrà lo script ALSA
  # Crea un file temporaneo in /tmp che conterrà lo script ALSA
       local tempfile=`mktemp`
       local tempfile=$(mktemp)
       # Scarica lo script ALSA
       # Scarica lo script ALSA
          _prompt "Download script ALSA..."
  wget -q -O "$tempfile" "$alsaurl"
  wget -q -O "$tempfile" "$alsaurl"
  # Se il download riesce...
  # Se il download riesce...
Riga 489: Riga 577:
      nome_e_riga "Problemi audio"
      nome_e_riga "Problemi audio"
      # Esegue lo script ALSA
      # Esegue lo script ALSA
      su  -c "$tempfile --stdout >> $log" $utente && _ok "Script ALSA eseguito" || _error "Script ALSA non eseguito"
              _prompt "Script ALSA..."
      su  -c "$tempfile --stdout >> $log" "$utente" && _ok "Script ALSA eseguito" || _error "Script ALSA non eseguito"
  else
  else
      _error "Download script ALSA fallito"
      _error "Download script ALSA fallito"
Riga 495: Riga 584:
   
   
  # Rimuove il file temporaneo
  # Rimuove il file temporaneo
  rm $tempfile
  rm -- "$tempfile"
  ;;
  ;;
     *)
     *)
  echo "Lo script ALSA non è stato ancora eseguito."
  echo "Lo script ALSA non è stato ancora eseguito."
  echo "Avviare manualmente lo script prelevabile a questo indirizzo:"
  echo "Avviare manualmente lo script prelevabile a questo indirizzo:"
  echo "$alsaurl"
  _bold "$alsaurl"
  echo "Lo script ALSA va eseguito con i permessi di normale utente."
  echo "Lo script ALSA va eseguito con i permessi di normale utente."
   esac
   esac
Riga 537: Riga 626:
   _dir "/etc/X11/xorg.conf.d/"
   _dir "/etc/X11/xorg.conf.d/"
   _file "/var/log/Xorg.0.log"
   _file "/var/log/Xorg.0.log"
   _comando "/usr/bin/synclient -l" "su"
   # se $DISPLAY è vuota, usa :0 (default per il primo server X)
  DISPLAY=${DISPLAY:-:0} _comando "/usr/bin/synclient -l" "su"
}
}


Riga 552: Riga 642:
     nome_e_riga "$1"
     nome_e_riga "$1"
     if [ -f "$1" ]; then
     if [ -f "$1" ]; then
        _prompt "$1"
case "$1" in
case "$1" in
    /etc/network/interfaces)
    /etc/network/interfaces)
                       # Nasconde nel log gli ESSID e le password criptate contenute in /etc/network/interfaces
                       # Nasconde nel log gli ESSID e le password criptate contenute in /etc/network/interfaces
      sed -r "s/((wpa-ssid)|(wpa-psk)).*/\1 \*script-removed\*/" $1 &>> $log && _ok $1 || _error $1 ;;
      sed -r "s/((wpa-ssid)|(wpa-psk)).*/\1 \*script-removed\*/" "$1" &>> "$log" && _ok "$1" || _error "$1" ;;
    /var/log/syslog)
    /var/log/syslog)
      # se il file contiene la stringa "rsyslogd.*start" ...
      # se il file contiene la stringa "rsyslogd.*start" ...
      if [ `egrep -s1ci "rsyslogd.*start$" $1` -ne 0 ]; then
      if [ "$(grep -sci 'rsyslogd.*start$' "$1")" -ne 0 ]; then
# ... estrae da syslog tutto il contenuto dall'ultima occorrenza della stringa alla fine del file
# ... estrae da syslog tutto il contenuto dall'ultima occorrenza della stringa alla fine del file
sed -n 'H; /rsyslogd.*start$/h; ${g;p;}' $1 >> $log && _ok $1 || _error $1
sed -n 'H; /rsyslogd.*start$/h; ${g;p;}' "$1" >> "$log" && _ok "$1" || _error "$1"
      else
      else
# se syslog non contiene quella stringa, allora si effettuerà la stessa operazione su syslog.1 ($1.1)
# se syslog non contiene quella stringa, allora si effettuerà la stessa operazione su syslog.1 ($1.1)
# in questo caso l'intero contenuto del file syslog viene inviato al log
# in questo caso l'intero contenuto del file syslog viene inviato al log
cat $1 &>> $log && _ok $1 || _error $1
cat "$1" &>> "$log" && _ok "$1" || _error "$1"
nome_e_riga $1.1
nome_e_riga "$1".1
sed -n 'H; /rsyslogd.*start$/h; ${g;p;}' $1.1 >> $log && _ok $1.1 || _error $1.1
                        _prompt "$1".1
sed -n 'H; /rsyslogd.*start$/h; ${g;p;}' "$1".1 >> "$log" && _ok "$1".1 || _error "$1".1
      fi ;;
      fi ;;
    *)
    *)
      # per tutti i file non specificati sopra...
      # per tutti i file non specificati sopra...
      cat "$1" &>> $log && _ok "$1" || _error "$1"
      cat "$1" &>> "$log" && _ok "$1" || _error "$1"
esac
esac
     else
     else
       echo "File $1 non trovato" >> $log && _error $1
       echo "File \"$1\" non trovato" >> "$log" && _error "$1"
     fi
     fi
}
}
Riga 594: Riga 686:
   local var2=${1%% *} # var2 conterrà il comando ($1) privo di eventuali opzioni ma con il path
   local var2=${1%% *} # var2 conterrà il comando ($1) privo di eventuali opzioni ma con il path
   nome_e_riga "$var"
   nome_e_riga "$var"
  _prompt "$var"
    
    
   if [ -f "$var2" ]; then # il comando esiste?
   if [ -f "$var2" ]; then # il comando esiste?
       if [ $# -eq 2 ]; then # Se vi sono 2 parametri, viene utilizzato "su"
       if [ $# -eq 2 ]; then # Se vi sono 2 parametri, viene utilizzato "su"
  case $var2 in
          su -c "$1" "$utente" &>> "$log" && _ok "$var" || _error "$var"
    *)
# Comando per tutti gli altri casi non specificati in precedenza
su -c "$1" $utente &>> $log && _ok "$var" || _error "$var"
  esac
       else # non viene utilizzato "su"
       else # non viene utilizzato "su"
  case $var2 in
  case "$var2" in
      # per "iwconfig" e "iwlist scan" gli ESSID non vengono inviati al log
      # per "iwconfig" e "iwlist scan" gli ESSID non vengono inviati al log
      /sbin/iwconfig)
      /sbin/iwconfig)
  (iwconfig | sed -e '/ESSID:/{/off\/any/! s/ESSID:.*/ESSID:"*script-removed*"/g}' -e '/^[ ]*IE: Unknown:.*/d') &>> $log && _ok "$var" || _error "$var"
  (iwconfig | sed -e '/ESSID:/{/off\/any/! s/ESSID:.*/ESSID:"*script-removed*"/g}' -e '/^[ ]*IE: Unknown:.*/d') &>> "$log" && _ok "$var" || _error "$var"
  ;;
  ;;
      /sbin/iwlist)
      /sbin/iwlist)
  (iwlist scan | sed -e '/ESSID:.*/{/off\/any/! s/ESSID:.*/ESSID:"*script-removed*"/g}' -e '/^[ ]*IE: Unknown:.*/d') &>> $log && _ok "$var" || _error "$var"
  (iwlist scan | sed -e '/ESSID:.*/{/off\/any/! s/ESSID:.*/ESSID:"*script-removed*"/g}' -e '/^[ ]*IE: Unknown:.*/d') &>> "$log" && _ok "$var" || _error "$var"
  ;;
  ;;
      *)
      *)
  # per tutti gli altri comandi non specificati sopra l'output del comando è inviato inalterato al log
  # per tutti gli altri comandi non specificati sopra l'output del comando è inviato inalterato al log
  $1 &>> $log && _ok "$var" || _error "$var"
  $1 &>> "$log" && _ok "$var" || _error "$var"
  esac    
  esac    
       fi
       fi
   else
   else
       echo "Comando $var2 non trovato" >> $log && _error "$var"
       echo "Comando \"${var2}\" non trovato" >> "$log" && _error "$var"
   fi
   fi
}
}
Riga 627: Riga 716:
   # Se la directory non esiste, stampa un output sul log ed esce.
   # Se la directory non esiste, stampa un output sul log ed esce.
   if [ ! -d "$1" ]; then
   if [ ! -d "$1" ]; then
     echo "La directory non esiste" >> $log && _error "$1"
     echo "La directory non esiste" >> "$log" && _error "$1"
     return
     return
   fi
   fi
Riga 634: Riga 723:
   local file
   local file
   # numfile contiene il numero di file contenuti nella directory. Solo primo livello.
   # numfile contiene il numero di file contenuti nella directory. Solo primo livello.
   local numfile=`find "$1" -maxdepth 1 -type f | wc -l`
   local numfile=$(find "$1" -maxdepth 1 -type f | wc -l)
   # numdir contiene il numero di sottodirectory contenute nella directory. Solo primo livello.
   # numdir contiene il numero di sottodirectory contenute nella directory. Solo primo livello.
   local numdir=`find "$1" -maxdepth 1 -type d | wc -l`
   local numdir=$(find "$1" -maxdepth 1 -type d | wc -l)


   if [ $numfile -eq 0 -a $numdir -eq 1 ]; then
   if [ "$numfile" -eq 0 ] && [ "$numdir" -eq 1 ]; then
     echo "La directory non contiene file o directory" >> $log && _error "$1"
     echo "La directory non contiene file o directory" >> "$log" && _error "$1"
   else
   else
     echo "La directory contiene $numfile file e $((numdir-1)) directory" >> $log
     echo "La directory contiene ${numfile} file e $(($numdir - 1)) directory" >> "$log"
     ls -al "$1" >> $log
     ls -al "$1" >> "$log"
     # invia al log il contenuto dei file della directory
     # invia al log il contenuto dei file della directory
     for file in "$1"*; do
     for file in "$1"*; do
       if [ -f "$file" ]; then
       if [ -f "$file" ]; then
         nome_e_riga "$file"
         nome_e_riga "$file"
         cat "$file" &>> $log && _ok "$file" || _error "$file"
        _prompt "$file"
         cat "$file" &>> "$log" && _ok "$file" || _error "$file"
       fi
       fi
     done
     done
Riga 667: Riga 757:
function _pack {
function _pack {
   nome_e_riga "Pacchetti che contengono \"$1\""
   nome_e_riga "Pacchetti che contengono \"$1\""
  _prompt "$1"


   # Variabile che contiene i pacchetti trovati
   # Variabile che contiene i pacchetti trovati
   local packages=`dpkg -l | grep -i "$1"`
   local packages=$(dpkg -l | grep -i "$1")


   if [ -z "$packages" ]; then
   if [ -z "$packages" ]; then
     echo "Nessun pacchetto installato" >> $log && _error "$1"
     echo "Nessun pacchetto installato" >> "$log" && _error "$1"
   else
   else
     echo "$packages" >> $log && _ok "$1"
     echo "$packages" >> "$log" && _ok "$1"
   fi
   fi
}
}
Riga 691: Riga 783:
   local vers="" var=""
   local vers="" var=""
   nome_e_riga "$2"
   nome_e_riga "$2"
   if [ -f $1 ]; then
  _prompt "$2"
     case $1 in
   if [ -f "$1" ]; then
     case "$1" in
/usr/sbin/NetworkManager)
/usr/sbin/NetworkManager)
                                   vers=`NetworkManager --version`
                                   vers=$(NetworkManager --version)
                                   var="network-manager"
                                   var="network-manager"
                                   ;;
                                   ;;
/usr/sbin/wicd)
/usr/sbin/wicd)
                                   vers=`wicd -h | head -2 | tail -1`
                                   vers=$(wicd -h | head -2 | tail -1)
                                   var="wicd"
                                   var="wicd"
                                   ;;
                                   ;;
     esac
     esac
    
    
     echo "$2 è installato (versione "$vers")" >> $log && _ok "$2"
     echo "$2 è installato (versione "$vers")" >> "$log" && _ok "$2"
     invoke-rc.d "$var" status &>/dev/null
     invoke-rc.d "$var" status &>/dev/null
     [ $? -eq 0 ] && echo "$2 è in esecuzione" >> $log || echo "$2 non è in esecuzione" >> $log
     [ $? -eq 0 ] && echo "$2 è in esecuzione" >> "$log" || echo "$2 non è in esecuzione" >> "$log"
   else
   else
     echo "$2 non è installato" >> $log && _error "$2"
     echo "$2 non è installato" >> "$log" && _error "$2"
   fi
   fi
}
}
Riga 719: Riga 812:
   local var="/sys/class/dmi/id/*"
   local var="/sys/class/dmi/id/*"
   nome_e_riga "$var"
   nome_e_riga "$var"
  _prompt "$var"
   if [ -f /sys/class/dmi/id/sys_vendor ]; then
   if [ -f /sys/class/dmi/id/sys_vendor ]; then
     echo 'Produttore:' $(cat /sys/class/dmi/id/sys_vendor)      &>> $log
     echo "Produttore: $(cat /sys/class/dmi/id/sys_vendor)"     &>> "$log"
     echo 'Prodotto: ' $(cat /sys/class/dmi/id/product_name)    &>> $log
     echo "Prodotto:   $(cat /sys/class/dmi/id/product_name)"   &>> "$log"
     echo 'Versione: ' $(cat /sys/class/dmi/id/product_version) &>> $log
     echo "Versione:   $(cat /sys/class/dmi/id/product_version)" &>> "$log"
     echo 'BIOS vers.:' $(cat /sys/class/dmi/id/bios_version)    &>> $log && _ok "$var" || _error "$var"
     echo "BIOS vers.: $(cat /sys/class/dmi/id/bios_version)"   &>> "$log" && _ok "$var" || _error "$var"
   else
   else
     echo "File /sys/class/dmi/id/sys_vendor non trovato" >> $log && _error "$var"
     echo "File /sys/class/dmi/id/sys_vendor non trovato" >> "$log" && _error "$var"
   fi
   fi
}
}
Riga 733: Riga 827:
   local i var="Firmware"
   local i var="Firmware"
   nome_e_riga "$var"
   nome_e_riga "$var"
   dpkg -l | grep -i firmware >> $log && _ok "$var"
   dpkg -l | grep -i firmware >> "$log" && _ok "$var"
   echo "" >> $log
   echo >> "$log"


   # Elenca i file contenuti nelle directory specificate
   # Elenca i file contenuti nelle directory specificate
   for i in "/usr/lib/firmware" "/usr/local/lib/firmware" "/lib/firmware" "/run/udev/firmware-missing"; do
   for i in "/usr/lib/firmware" "/usr/local/lib/firmware" "/lib/firmware" "/run/udev/firmware-missing"; do
     if [ -d $i ]; then
     if [ -d "$i" ]; then
       echo "Contenuto di $i" >> $log
       echo "Contenuto di ${i}" >> "$log"
       ls -al $i >> $log
       ls -al "$i" >> "$log"
     else
     else
       echo "$i non trovata" >> $log
       echo "${i} non trovata" >> "$log"
     fi
     fi
     echo "" >> $log
     echo >> "$log"
   done
   done
}
# Stampa sullo standard output l'eseguibile associato a x-session-manager (il default)
function _x_session_manager {
  update-alternatives --query "x-session-manager" |
    awk '$1 ~ /^Value:$/ { print $2; exit 0 }'
}
# Stampa sullo standard output l'eseguibile associato a x-window-manager (il default)
function _x_window_manager {
  update-alternatives --query "x-window-manager" |
    awk '$1 ~ /^Value:$/ { print $2; exit 0 }'
}
# Stampa la lista dei pacchetti installati che soddisfano una data dipendenza
# con versione (del programma e in Debian) e archivio di provenienza
# Viene chiamata con un parametro:
# $1 - nome della dipendenza
function _soddisfa {
  echo "Installati (${1}):"
  aptitude search '?installed?provides('"$1"')' --disable-columns \
    --display-format "- %p (versione: %n [Debian: %v]; archivio: %t)"
}
# Restituisce un exit status di 0 solo se l'eseguibile con il nome scelto è in esecuzione da parte dell'utente ($utente)
# Viene chiamata con un parametro:
# $1 - comando di cui controllare l'esecuzione da parte di $utente
function _is_running {
  local list_pids_user list_pids_bin pid pid2
  list_pids_user=$(ps -U "$utente" -o pid) # lista di interi, separati da spazi, con i PID dei processi avviati da $utente
  list_pids_bin=$(pidof -- "$1")          # lista di interi, separati da spazi, con i PID dei processi del comando $1
  for pid in $list_pids_user; do
    for pid2 in $list_pids_bin; do
      if [ "$pid" = "$pid2" ]; then
        return 0  # trovato
      fi
    done
  done
  return 1        # non trovato!
}
}


Riga 751: Riga 884:
function _de_wm {
function _de_wm {
   nome_e_riga "Desktop Environment - Window Manager"
   nome_e_riga "Desktop Environment - Window Manager"
   if false; then :
   _prompt "DE/WM"
   elif [ -f /usr/bin/kde4-config -a -n "`ps -u $utente | grep ksmserver`" ]; then kde4-config --version >> $log && _ok "DE/WM" || _error "DE/WM"                       # KDE4
   {
   elif [ -f /usr/bin/gnome-shell -a -n "`ps -u $utente | grep gnome-shell`" ]; then gnome-shell --version >> $log && _ok "DE/WM" || _error "DE/WM"                    # Gnome Shell
    # impostazione di default
   elif [ -f /usr/bin/xfce4-about -a -n "`ps -u $utente | grep xfdesktop`" ]; then xfce4-about -V | head -n1 | cut -d ' ' -f2- >> $log && _ok "DE/WM" || _error "DE/WM" # Xfce4
    echo -n $'Default:\n- x-session-manager: '
    _x_session_manager
    echo -n "- x-window-manager: "
    _x_window_manager
    # installati
    _soddisfa "x-session-manager"
    #_soddisfa "x-window-manager" # non essenziale e impiega già tanto
  } >> "$log"
  # in esecuzione
  echo -n "In esecuzione: " >> "$log"
  if _is_running "ksmserver"; then kde4-config --version >> "$log" && _ok "DE/WM" || _error "DE/WM"                         # KDE4
   elif _is_running "gnome-shell"; then gnome-shell --version >> "$log" && _ok "DE/WM" || _error "DE/WM"                    # Gnome Shell
   elif _is_running "xfdesktop"; then xfce4-about -V | head -n1 | cut -d ' ' -f2- >> "$log" && _ok "DE/WM" || _error "DE/WM" # Xfce4
  elif _is_running "openbox"; then
    if [ "$(_x_session_manager)" != "/usr/bin/openbox-session" ]; then
      echo -n "(altro x-session-manager) + " >> "$log"                                                                      # Session manager (LXDE?) + Openbox
    fi
    openbox --version | head -n 1 >> "$log" && _ok "DE/WM" || _error "DE/WM"                                                # Openbox
   else
   else
     echo "Sconosciuto" >> $log && _error "DE/WM"
     echo "Sconosciuto" >> "$log" && _error "DE/WM"                                                                         # NON TROVATO
   fi
   fi
}
}
Riga 767: Riga 917:
   # "deb http://ftp.XX.debian.org" e che *non* contengono un nome di release.
   # "deb http://ftp.XX.debian.org" e che *non* contengono un nome di release.
   # Con "cut" viene prelevato il terzo campo (la release voluta)
   # Con "cut" viene prelevato il terzo campo (la release voluta)
   local release=`sed -e 's/^ *//' -e '/^deb http:\/\/ftp\...\.debian\.org.*\('$STABLE' \|stable \|'$TESTING' \|testing \|sid \|unstable \)/!d' /etc/apt/sources.list | cut -d ' ' -f3`
   local release=$(sed -e 's/^ *//' -e '/^deb http:\/\/ftp\...\.debian\.org.*\('"$STABLE"' \|stable \|'"$TESTING"' \|testing \|sid \|unstable \)/!d' /etc/apt/sources.list | cut -d ' ' -f3)
    
    
   # Numero di release trovate
   # Numero di release trovate
   local num=`echo "$release" | wc -l`
   local num=$(echo "$release" | wc -l)
    
    
   local var="Pacchetti esterni"
   local var="Pacchetti esterni"
  _prompt "$var"


   # Se il numero di release è diverso da 1, la funzione termina
   # Se il numero di release è diverso da 1, la funzione termina
   if [ $num -ne 1 ]; then
   if [ "$num" -ne 1 ]; then
     nome_e_riga "$var"
     nome_e_riga "$var"
     echo "Sono presenti $num release in sources.list" >> $log && _error "$var"
     echo "Sono presenti ${num} release in sources.list" >> "$log" && _error "$var"
     return
     return
   fi
   fi
Riga 784: Riga 935:


   # Se il numero di release è uguale a 1, la variabile pkg conterrà i pacchetti *non* facenti parte della release
   # Se il numero di release è uguale a 1, la variabile pkg conterrà i pacchetti *non* facenti parte della release
   case $release in
   case "$release" in
         $STABLE|stable)
         "$STABLE"|stable)
release="stable"
release="stable"
pkg=`aptitude -F '%p %v %t' search '~i !~Astable'  --disable-columns | column -t` ;;
pkg=$(aptitude -F '%p %v %t' search '~i !~Astable'  --disable-columns | column -t) ;;
         $TESTING|testing)
         "$TESTING"|testing)
release="testing"
release="testing"
pkg=`aptitude -F '%p %v %t' search '~i !~Atesting'  --disable-columns | column -t` ;;
pkg=$(aptitude -F '%p %v %t' search '~i !~Atesting'  --disable-columns | column -t) ;;
         sid|unstable)
         sid|unstable)
release="unstable"
release="unstable"
pkg=`aptitude -F '%p %v %t' search '~i !~Aunstable' --disable-columns | column -t` ;;
pkg=$(aptitude -F '%p %v %t' search '~i !~Aunstable' --disable-columns | column -t) ;;
   esac
   esac


   # Invia al log il contenuto di pkg (se esiste)
   # Invia al log il contenuto di pkg (se esiste)
   nome_e_riga "$var all'archivio \"$release\""
   nome_e_riga "${var} all'archivio \"${release}\""
   if [ -z "$pkg" ]; then
   if [ -z "$pkg" ]; then
     echo "Nessun pacchetto esterno installato" >> $log && _error "$var"
     echo "Nessun pacchetto esterno installato" >> "$log" && _error "$var"
   else
   else
     echo "$pkg" >> $log && _ok "$var"
     echo "$pkg" >> "$log" && _ok "$var"
   fi
   fi
}
}

Versione delle 17:35, 11 ago 2014

Debian-swirl.png Versioni Compatibili

Tutte le versioni supportate di Debian

Introduzione

Questo script permette la creazione di un file contenente informazioni utili che possono aiutare a comprendere meglio il proprio problema oppure che è possibile portare a conoscenza del forum per tentare di risolverlo insieme. Le informazioni riguardano i seguenti tipi di problema:

  • Connessioni di rete
  • Video
  • Audio (tramite lo script ALSA prelevabile qui)
  • Sottosistema APT
  • Mount/unmount di periferiche
  • Touchpad

Lo script crea due file:

log_data
contiene le informazioni in formato testo
log_data.{bz2,zip,tgz}
il file precedente ma in formato compresso. Può essere allegato ad una discussione sul forum

Se si vuole, attraverso lo script è anche possibile inviare il file direttamente a paste.debian.net per poterlo condividere pubblicamente, in questo caso il file non potrà superare la grandezza complessiva di 240K circa (diviso in parti della dimensione massima di 60K circa) e le informazioni saranno disponibili a chiunque per una settimana.
Prima di effettuare l'invio, lo script chiede un esplicito consenso all'utente.

Per usufruire del servizio offerto da paste.debian.net è necessaria l'installazione del pacchetto pastebinit:

# apt-get install pastebinit
Info.png Nota
Lo script è liberamente modificabile.
Per ogni segnalazione, informazione o suggerimento fare riferimento a questa discussione sul forum.


Utilizzo

  1. Eseguire un upgrade del sistema, se possibile, in modo che le informazioni raccolte dallo script siano aggiornate.
  2. Copiare il codice dello script in un file di testo. Il nome del file può essere scelto liberamente.
    Se si preferisce, è possibile eseguire il seguente comando:
    $ wget -q -O- "http://guide.debianizzati.org/index.php?title=Creazione_automatica_di_un_file_di_log_per_inviare_quesiti_al_forum&action=edit" | sed -n "/^== Script/{n;:a n; /^&lt/ ! {s/\&amp;/\&/g; p; ba}}" > nomefile
    Questo creerà il file di testo "nomefile" contenente lo script.
    Si presuppone che non esista nella directory corrente un file avente lo stesso nome (altrimenti verrà sovrascritto), che il pacchetto "wget" sia installato e che, ovviamente, la connessione alla Rete sia funzionante.
  3. Dare i permessi di esecuzione al file appena creato. Supponendo che si chiami nomefile:
    $ chmod +x nomefile
  4. Eseguire lo script con i permessi di root:
    # ./nomefile
    il comando precedente presuppone che sia eseguito nella stessa directory in cui risiede lo script.
    L'utilizzo dei permessi di root si rende necessario poiché alcuni comandi devono essere eseguiti necessariamente come utente privilegiato.
  5. Leggere le informazioni a video.

Script

#! /bin/bash

# --------------------------------------------------------------------------
# Impostazioni
# --------------------------------------------------------------------------

# I file creati saranno leggibili e scrivibili da tutti
umask 0011

# --------------------------------------------------------------------------
# Funzioni che sovrascrivono comandi
# --------------------------------------------------------------------------

# Rimpiazza echo ed echo -n, impedendo echo -e e le possibili combinazioni
# Sintassi accettata:
#  echo -n "testo"  # stampa senza a capo finale
#  echo "testo"     # stampa con a capo finale
#  echo             # stampa una riga vuota
function echo {
  if [ $# -gt 1 ] && [ "$1" = "-n" ]; then
    shift
    printf %s "$*"
  else
    printf %s\\n "$*"
  fi
}

# --------------------------------------------------------------------------
# Costanti
# --------------------------------------------------------------------------

# Codename per stable e testing. Da modificare nei successivi rilasci di Debian
readonly STABLE="wheezy"
readonly TESTING="jessie"

# Path dei comandi dello script
readonly PATH="/bin:/sbin:/usr/bin:/usr/sbin"

# Nome del file di log in base alla data corrente
readonly log="log_$(date '+%d%b_%H%M%S')"

# Nome del file compresso. Viene usata l'estensione .bz2 a meno
# che non venga modificata da _compress
readonly complog="${log}.bz2"

# nome utente
utente=$(logname) &&
[ "$utente" != "root" ] || {
  utente=
  tmputente=
  for tmputente in $(users); do
    if [ "$tmputente" = "root" ]; then
      continue
    elif [ -z "$utente" ]; then
      utente=$tmputente
    elif [ "$utente" != "$tmputente" ]; then
      utente=
      break
    fi
  done
  if [ -z "$utente" ]; then
    # NOTA: "root" è permesso (solo) se scelto esplicitamente dall'utente
    echo -n "Inserisci il tuo nome utente: "
    read tmputente &&
    # non può contenere: spazi, tabulazioni, nuove righe; né essere vuota
    [ -n "${tmputente##*[[:space:]]*}" ] &&
    # l'utente deve aver effettuato il login (anche in altre console)
    case " $(users) " in
      *" ${tmputente} "* ) true
                           ;;
      * ) false
          ;;
    esac || {
      echo "Nome utente invalido o non ha effettuato il login!" >&2
      exit 255
    }
    utente=$tmputente
  fi
  unset tmputente
}
readonly utente

# nome host
readonly nomehost=$(hostname)

# Codici stile carattere
readonly ROSSO="\033[01;31m" 	# colore rosso e grassetto
readonly VERDE="\033[01;32m" 	# colore verde e grassetto
readonly BOLD="\033[01m"        # grassetto
readonly FINE="\033[0m"         # reset

# --------------------------------------------------------------------------
# Funzioni iniziali
# --------------------------------------------------------------------------

# Funzione che stampa il messaggio introduttivo
function _intro {
 echo "
*********************************************************************************
*  www.debianizzati.org                                                         *
*                                                                               *
*  Script che crea un log utile alla risoluzione dei problemi più comuni        *
*  Versione 1.0.39                                                              *
*                                                                               *
*********************************************************************************"
}

# Funzione che stampa alcune avvertenze sullo script
function _avvertenze {
  local risp
  echo "
-- Lo script richiede i permessi di root per essere eseguito
-- Per inviare il log su paste.debian.net è necessario il pacchetto 'pastebinit'
-- L'invio del log a paste.debian.net avverrà solo dopo esplicito consenso
-- Verrà creato un file contenente l'output di questo script
-- Verrà creato un file in formato compresso da inviare al forum"
  echo -n "Continuare [S/n]? "
  read risp || risp="ERROR"
  
  # Se non viene premuto "s" o "S" o [Invio], lo script termina
  [ -z "$risp" ] || [ "$risp" = "s" ] || [ "$risp" = "S" ] || _exit
}

# Funzione che esegue un check preliminare
function _check {
  if [ $EUID -ne 0 ]; then # Lo script viene lanciato da root?
    echo "Lo script deve essere lanciato da root" && _exit
  fi
 
  # Se esiste già un file di log con lo stesso nome oppure file compressi con lo
  # stesso nome di quelli che verranno creati, lo script chiede se cancellarli o meno
  local risp
  if [ -f "$log" ] || [ -f "${log}.zip" ] || [ -f "${log}.bz2" ] || [ -f "${log}.tgz" ]; then
    echo $'\n'"Esiste già un file ${log}, ${log}.zip, ${log}.bz2 o ${log}.tgz nella directory corrente."
    echo -n "Sovrascivere [S/n]? "
    read risp
    case "$risp" in
      ""|[Ss]) rm -f -- "$log" "${log}.zip" "${log}.bz2" "${log}.tgz"  ;;
      *)       _exit
    esac
  fi
}

# --------------------------------------------------------------------------
# Funzioni per l'invio del log a paste.debian.net
# --------------------------------------------------------------------------

# Funzione per separare il log in parti per l'invio a paste.debian.net
function _split_and_send {
  local paste_url='http://paste.debian.net'
  local chunk_prefix='pastebin'
  local chunk_num=1
  local paste_exit_status=0
  local chunkfile pastelink
 
  # dimensione massima del singolo file da inviare
  local chunk_size='60k'

  # termina la funzione se il log è più grande di chunk_size x 4 (numero di parti impostate)
  if [ "$(du -k "$log" | cut -f1)" -gt 240 ]; then
     echo "Log troppo grande per essere inviato a paste.debian.net"
     echo "Allegare il file compresso alla discussione sul forum."
     return 1
  fi
 
  # rinomina parti di log preesistenti (se ve ne sono)
  # scarta i messaggi di errore (se presenti)
  rename "s/${chunk_prefix}/old-${chunk_prefix}-$(date '+%s')/" "$chunk_prefix".* > /dev/null 2>&1
 
  # dividi il file di log in parti di $chunk_size bytes senza spezzare le linee
  # scarta i messaggi di errore (se presenti) per log di dimensione superiore a 10 parti
  # (max 10 parti con l'opzione -a)
  split -a 1 -d -C "$chunk_size" "$log" "${chunk_prefix}." > /dev/null 2>&1
 
  # comunica il numero di parti inviate
  chunk_num=$(find . -maxdepth 1 -type f -name "${chunk_prefix}.*" -printf x |
              wc -c)
  if [ "$chunk_num" = 1 ]; then
      echo $'\nIl log sarà inviato in un singolo file.'
  else
      echo $'\n'"Il log sarà inviato in ${chunk_num} parti."
  fi
 
  # invia al massimo 4 parti
  echo $'\nIl log è consultabile ai seguenti indirizzi:'
  for chunkfile in "${chunk_prefix}."[0-3]; do
 
    # verifica l'esistenza del file da inviare
    if [ -f "$chunkfile" ]; then

    # invia dati tramite pastebinit, l'output d'errore viene soppresso
    pastelink=$(pastebinit -a '' -b "$paste_url" -i "$chunkfile" 2>/dev/null)
     
      if [ $? = 0 ]; then
	  # invio apparentemente riuscito (pastebinit exit status = 0)
      
	  # controlla URL restituita da pastebinit
	  case "$pastelink" in
	  # verifica in caso di url corretta
	  "$paste_url"/[0-9]*)
	      echo ".. inviato ${chunkfile} all'indirizzo ${pastelink}"
	      ;;
	  # verifica in caso di url non corretta
	  *)
	      echo ".. ${paste_url} ha restituito una URL non valida (${pastelink}) per ${chunkfile}!"
	      paste_exit_status=1
	  esac
  
      else
	  # Invio fallito (pastebinit exit status = 1)
	  echo ".. non riuscito invio ${chunkfile}"
	  paste_exit_status=1
      fi
 
    fi
 
  done
 
  # cancella le parti di log inviate
  for chunkfile in "./${chunk_prefix}."[0-9]*; do
    if [ -f "$chunkfile" ]; then
      rm -f -- "$chunkfile"
    fi
  done
 
  return $paste_exit_status
}

# Funzione che invia il log a paste.debian.net
function _upload {
  local risp
  # Pastebinit è installato?
  if [ ! -f /usr/bin/pastebinit ]; then
    echo $'\nNon è possibile inviare il log a paste.debian.net\nIl pacchetto "pastebinit" non è installato.'
    return 1
  fi
  # Invia il file log.txt a paste.debian.net
  echo -n $'\nInviare il log a http://paste.debian.net [S/n]? '
  read risp
  case "$risp" in
    ""|[Ss])
      _split_and_send
      if [ $? = 0 ]; then
        echo $'\nIl log è stato inviato'
      else
        echo $'\nSi sono verificati errori nell\'invio del log!'
      fi
      ;;
    *)
      echo "Il log non è stato inviato"
  esac
}

# --------------------------------------------------------------------------
# Funzioni di creazione del file compresso e messaggi di successo/fallimento
# --------------------------------------------------------------------------

# Funzione richiamata in caso di corretta/scorretta creazione del file compresso
function _compress_ok {
  echo "File compresso creato correttamente nella directory corrente."
}

function _compress_err {
  echo "Errore nella creazione del file compresso."
}

# Funzione che crea il file compresso
# Prova a creare nell'ordine: un file .bz2, un file .zip o un file .tgz
function _compress {
  local risp
  echo -n $'\nCreare un file compresso [S/n]? '
  read risp
  case "$risp" in
    ""|[Ss])
      echo "Sta per essere creato un file compresso..."
      sleep 1
      if [ -f /bin/bzip2 ]; then
        bzip2 -k9 "$log" && _compress_ok || _compress_err
      elif [ -f /usr/bin/zip ]; then
        zip "${log}.zip" "$log" && _compress_ok || _compress_err
        complog="${log}.zip"
      else
        tar czf "${log}.tgz" "$log" && _compress_ok || _compress_err
        complog="${log}.tgz"
      fi
      ;;
    *)
      echo "Non è stato creato un file compresso."
  esac
}

# --------------------------------------------------------------------------
# Funzione di stampa menù e selezione del problema
# --------------------------------------------------------------------------

function _scelta {
  local num
 
  clear
  _intro
  echo "
Selezionare il tipo di problema per il quale verrà generato il file di log
[1] Problemi relativi alle connessioni di rete
[2] Problemi video
[3] Problemi audio
[4] Problemi di gestione dei pacchetti (APT)
[5] Problemi di mount/unmount
[6] Problemi di funzionamento del touchpad
[7] Altro tipo di problema
[0] Uscita"
 
  while true; do
    echo -n "Scegliere il numero corrispondente: "
    read num
    case "$num" in
        [1-7])	_wait   ;;& # ;;& -> va alla successiva occorrenza del carattere immesso
            1)	echo $'### Problemi di rete ###\n'            > "$log" && _rete   ;;&
            2)	echo $'### Problemi video ###\n'              > "$log" && _video  ;;&
            3)	echo $'### Problemi audio ###\n'              > "$log" && _audio  ;;&
            4)	echo $'### Problemi APT ###\n'                > "$log" && _apt    ;;&
            5)	echo $'### Problemi mount-unmount ###\n'      > "$log" && _mount  ;;&
            6)	echo $'### Problemi touchpad ###\n'           > "$log" && _tpad   ;;&
            7)	echo $'### Solo informazioni generiche ###\n' > "$log" && _common ;;&
        [1-7])	break   ;; # Termina il ciclo 'while'
       0)	_exit   ;; # È stato inserito '0' . Uscita dallo script
       *)	# Tutti gli altri caratteri. Cancella l'input immesso e ripete la domanda
		tput cuu1 # in alto di una riga
		tput ed # cancella fino alla fine dello schermo
    esac
  done
}

# --------------------------------------------------------------------------
# Funzioni varie
# --------------------------------------------------------------------------

# Funzione che stampa solo lo spazio e il nome del comando, prima di eseguirlo
function _prompt {
  echo -n "[ ]  $*"
}

# Funzione che stampa un pallino di colore verde in caso di comando con output
function _ok {
  printf %b "\r[${VERDE}•${FINE}]  "
  echo -n "$*"
  # cancella fino a fine schermo e va a capo
  tput ed
  echo
}

# Funzione che stampa una pallino rosso in caso di comando privo di output
function _error {
  printf %b "\r[${ROSSO}•${FINE}]  "
  echo -n "$*"
  # cancella fino a fine schermo e va a capo
  tput ed
  echo
}

# Funzione che stampa in grassetto gli argomenti
function _bold {
  printf %b "$BOLD"
  echo -n "$*"
  printf %b\\n "$FINE"
}

# Funzione che invia nel file di log due righe tra le quali viene visualizzato il
# nome del comando (passato come primo parametro della funzione -> $1)
function nome_e_riga {
  echo "
******************************************
$1
******************************************" >> "$log"
}

# Funzione che stampa un messaggio di attesa e aspetta 2 secondi
function _wait {
  echo $'\nCreazione del log in corso...\n'
}

# Stampa la data corrente nel file di log
function _data {
  echo "Log creato il $(date '+%d %B %Y alle %H.%M')" >> "$log"
}

# Funzione che nasconde nel log alcune informazioni sensibili
function _hide {

 # Sostituisce il nome utente e il nome host con 'nomeutente' e 'nomehost' se diversi da [dD]ebian
 [ "$nomehost" != "Debian" ] && [ "$nomehost" != "debian" ] && sed -i -e "s/${nomehost}/nomehost/g" "$log"
 [ "$utente" != "Debian" ] && [ "$utente" != "debian" ] && sed -i -e "s/${utente}/nomeutente/g" "$log"

 # Nasconde gli ESSID gestiti attraverso Network Manager
 local var file mydir="/etc/NetworkManager/system-connections/"

 if [ -d "$mydir" ]; then # se esiste la directory /etc/NetworkManager/system-connections/ ...
    for file in "$mydir"/*; do # ciclo attraverso il contenuto della directory
       if [ -f "$file" ]; then # se l'elemento è un file...
          var=$(sed -n "s/ssid=//p" "$file") # ... var conterrà l'eventuale ESSID...
          if [ -n "$var" ]; then # ... e se è diverso dalla stringa vuota...
             sed -i "s/${var}/\*script-removed\*/g" "$log" # ... lo nasconde nel file di log
          fi
       fi
    done
 fi

 # Nasconde nel log i i nomi delle connessioni gestite da NetworkManager
 sed -i -r "s/(NetworkManager.*keyfile.*((parsing)|(read connection))).*/\1 \*script-removed\*/" "$log"
}

# Stabilisce la data dell'ultimo aggiornamento effettuato. Viene preso in
# considerazione il file /var/log/apt/history.log oppure il file /var/log/apt/history.log.1.gz
function _lastupd {
  local convdate lastdate file=/var/log/apt/history.log
  
  if [ -f "$file" ]; then
    lastdate=$(sed -n '/^Start-Date/h ; $p' "$file" | awk '{print $2}')
    # se il file history.log non contiene la data dell'ultimo aggiornamento, viene utilizzato history.log.1.gz
    [ -z "$lastdate" ] && [ -f "${file}.1.gz" ] && lastdate=$(zcat "${file}.1.gz" | sed -n '/^Start-Date/h ; $p' | awk '{print $2}')

    # variabile che contiene la data in formato "giorno mese anno"
    convdate=$(date -d "$lastdate" '+%d %B %Y')
    
    echo $'\n'"Ultimo aggiornamento del sistema: ${convdate}" >> "$log"
  fi
}

# Funzione che stampa un messaggio che indica i file creati e poi termina lo script
function _exit {
  if [ -f "$log" ]; then
    echo -n $'\nFile contenente il log dello script: '
    _bold "$log"
  else
    echo $'\nNon è stato creato un file di log'
  fi
  
  if [ -f "$complog" ]; then
    echo -n "File compresso da allegare alla discussione sul forum: "
    _bold "$complog"
  else
    echo "Non è stato creato un file compresso del log"
  fi
  
  echo $'Script terminato\n'
  exit 0
}

# --------------------------------------------------------------------------
# Funzioni relative a ciascun problema selezionato
# --------------------------------------------------------------------------

# Informazioni comuni a tutti i tipi di problema
function _common {
  _data
  _lastupd
  _dmi_decode
  _comando "/bin/uname -a"
  _file "/etc/debian_version"
  _de_wm
  _file "/etc/X11/default-display-manager"
  _comando "/usr/bin/groups" "su"
  _file "/var/log/syslog"
  _comando "/bin/dmesg -l err"
  _comando "/bin/dmesg -l warn"
  _comando "/bin/lsmod"
  _comando "/usr/bin/lspci -knn"
  _comando "/usr/bin/lsusb"
  _file "/etc/apt/sources.list"
  _dir "/etc/apt/sources.list.d/"
  _comando "/sbin/fdisk -l"
  _file "/etc/fstab"
  _comando "/bin/findmnt"
  _comando "/bin/df"
  _comando "/usr/bin/apt-cache policy"
  _comando "/usr/bin/apt-cache stats"
  _comando "/usr/bin/apt-get check"
  _firmware
  _extpack
}

# Funzione relativa ai problemi di rete
function _rete {
  _common
  _file "/etc/network/interfaces"
  _file "/etc/hosts"
  _comando "/sbin/ifconfig"
  _comando "/sbin/ifconfig -a"
  _comando "/usr/sbin/rfkill list all"
  _comando "/bin/ping -c3 8.8.8.8" #DNS di Google 8.8.8.8
  _comando "/bin/ip addr"
  _comando "/bin/ip route list"
  _comando "/sbin/iwconfig"
  _comando "/sbin/iwlist scan"
  _comando "/sbin/route -n"
  _pack "resolvconf"
  _file "/etc/resolv.conf"
  _pack "DHCP"
  _file "/etc/dhclient.conf"
  _file "/etc/NetworkManager/NetworkManager.conf"
  _demone "/usr/sbin/NetworkManager" "Network Manager"
  _demone "/usr/sbin/wicd" "Wicd"
}

# Funzione relativa a problemi video
function _video {
  _common
  _file "/etc/X11/xorg.conf"
  _dir "/etc/X11/xorg.conf.d/"
  _file "/var/log/Xorg.0.log"
  _comando "/usr/sbin/dkms status"
  _pack "xserver-xorg"
  _pack "nouveau"
  _pack "nvidia"
  _pack "mesa"
  _pack "fglrx"
}

# Funzione relativa ai problemi audio. Scarica ed esegue lo script ALSA
function _audio {
  _common
  _pack "alsa"
  
  local risp alsaurl="http://www.alsa-project.org/alsa-info.sh"
  
  echo $'\nI log relativi ai problemi audio sono ricavati attraverso lo script di debug'
  echo "ALSA prelevabile all'indirizzo: ${alsaurl}"
  echo -n $'\nVerrà ora scaricato e eseguito lo script ALSA. Continuare [S/n]? '
  read risp
  case "$risp" in
    ""|[Ss])
	  # wget esiste?
	  if [ ! -f /usr/bin/wget ]; then
	    echo "Impossibile scaricare lo script ALSA. Installare il pacchetto wget."
	    return
	  fi
	  # Crea un file temporaneo in /tmp che conterrà lo script ALSA
    	  local tempfile=$(mktemp)
    	  # Scarica lo script ALSA
          _prompt "Download script ALSA..."
	  wget -q -O "$tempfile" "$alsaurl"
	  # Se il download riesce...
	  if [ $? -eq 0 ]; then
	      _ok "Download script ALSA riuscito"
	      # Imposta i permessi dello script scaricato
	      chmod 777 "$tempfile"
	      nome_e_riga "Problemi audio"
	      # Esegue lo script ALSA
              _prompt "Script ALSA..."
	      su  -c "$tempfile --stdout >> $log" "$utente" && _ok "Script ALSA eseguito" || _error "Script ALSA non eseguito"
	  else
	      _error "Download script ALSA fallito"
	  fi
	  
	  # Rimuove il file temporaneo
	  rm -- "$tempfile"
	  ;;
    *)
	  echo "Lo script ALSA non è stato ancora eseguito."
	  echo "Avviare manualmente lo script prelevabile a questo indirizzo:"
	  _bold "$alsaurl"
	  echo "Lo script ALSA va eseguito con i permessi di normale utente."
  esac
  
}

# Funzione relativa alla gestione dei pacchetti attraverso il sistema APT
function _apt {
  _common
  _comando "/usr/bin/dpkg --print-architecture"
  _comando "/usr/bin/apt-get update"
  _comando "/usr/bin/apt-get -s -y upgrade"
  _comando "/usr/bin/apt-get -s -y dist-upgrade"
  _comando "/usr/bin/apt-get -s -y -f install"
  _comando "/usr/bin/apt-get -s -y autoremove"
  _comando "/usr/bin/apt-config dump"
  _file "/etc/apt/apt.conf"
  _dir "/etc/apt/apt.conf.d/"
  _file "/etc/apt/preferences"
  _dir "/etc/apt/preferences.d/"
}

# Funzione relativa a problemi di mount/unmount
function _mount {
  _common
  _comando "/usr/bin/udisks --dump"
  _pack "usbmount"
}

# Funzione relativa al funzionamento del touchpad
function _tpad {
  _common
  _pack "xserver-xorg"
  _pack "touchpad"
  _file "/etc/X11/xorg.conf"
  _dir "/etc/X11/xorg.conf.d/"
  _file "/var/log/Xorg.0.log"
  # se $DISPLAY è vuota, usa :0 (default per il primo server X)
  DISPLAY=${DISPLAY:-:0} _comando "/usr/bin/synclient -l" "su"
}

# --------------------------------------------------------------------------
# Funzioni utilizzate per tipo di problema (generiche)
# --------------------------------------------------------------------------

# Funzione che invia il contenuto di un file al file di log
# La funzione va richiamata specificando il path completo del file che sarà assegnato a $1
# Il contenuto dei file viene inviato inalterato al file di log. Se si ha necessità di
# modificare questo comportamento, creare una entry nel ciclo "case"

function _file {
    nome_e_riga "$1"
    if [ -f "$1" ]; then
        _prompt "$1"
	case "$1" in
	    /etc/network/interfaces)
                      # Nasconde nel log gli ESSID e le password criptate contenute in /etc/network/interfaces
		      sed -r "s/((wpa-ssid)|(wpa-psk)).*/\1 \*script-removed\*/" "$1" &>> "$log" && _ok "$1" || _error "$1" ;;
	    /var/log/syslog)
		      # se il file contiene la stringa "rsyslogd.*start" ...
		      if [ "$(grep -sci 'rsyslogd.*start$' "$1")" -ne 0 ]; then
			# ... estrae da syslog tutto il contenuto dall'ultima occorrenza della stringa alla fine del file
			sed -n 'H; /rsyslogd.*start$/h; ${g;p;}' "$1" >> "$log" && _ok "$1" || _error "$1"
		      else
			# se syslog non contiene quella stringa, allora si effettuerà la stessa operazione su syslog.1 ($1.1)
			# in questo caso l'intero contenuto del file syslog viene inviato al log
			cat "$1" &>> "$log" && _ok "$1" || _error "$1"
			nome_e_riga "$1".1
                        _prompt "$1".1
			sed -n 'H; /rsyslogd.*start$/h; ${g;p;}' "$1".1 >> "$log" && _ok "$1".1 || _error "$1".1
		      fi ;;
	    *)
		      # per tutti i file non specificati sopra...
		      cat "$1" &>> "$log" && _ok "$1" || _error "$1"
	esac
    else
      echo "File \"$1\" non trovato" >> "$log" && _error "$1"
    fi
}

# Invia l'output di un comando al file di log
# La funzione va richiamata specificando il path completo del comando (con eventuali opzioni)
# che sarà assegnato a $1 . L'output dei comandi viene inviato interamente al file di log. Se
# si ha necessità di modificare gli output, creare una entry nel ciclo "case"
# Es. _comando "/usr/bin/apt-get update"
#
# Nel caso in cui il comando debba essere eseguito tramite 'su', richiamare la funzione con
# due parametri:
# $1 = il comando da eseguire attraverso 'su'
# $2 = la stringa 'su'
# Es. _comando "/usr/bin/groups" "su"

function _comando {

  local var=${1##*/} # var conterrà il comando ($1) con le opzioni ma privo del path
  local var2=${1%% *} # var2 conterrà il comando ($1) privo di eventuali opzioni ma con il path
  nome_e_riga "$var"
  _prompt "$var"
  
  if [ -f "$var2" ]; then # il comando esiste?
      if [ $# -eq 2 ]; then # Se vi sono 2 parametri, viene utilizzato "su"
          su -c "$1" "$utente" &>> "$log" && _ok "$var" || _error "$var"
      else # non viene utilizzato "su"
	  case "$var2" in
	      # per "iwconfig" e "iwlist scan" gli ESSID non vengono inviati al log
	      /sbin/iwconfig)
		  (iwconfig | sed -e '/ESSID:/{/off\/any/! s/ESSID:.*/ESSID:"*script-removed*"/g}' -e '/^[ ]*IE: Unknown:.*/d') &>> "$log" && _ok "$var" || _error "$var"
		  ;;
	      /sbin/iwlist)
		  (iwlist scan | sed -e '/ESSID:.*/{/off\/any/! s/ESSID:.*/ESSID:"*script-removed*"/g}' -e '/^[ ]*IE: Unknown:.*/d') &>> "$log" && _ok "$var" || _error "$var"
		  ;;
	      *)
		  # per tutti gli altri comandi non specificati sopra l'output del comando è inviato inalterato al log
		  $1 &>> "$log" && _ok "$var" || _error "$var"
	  esac	  
      fi
  else
      echo "Comando \"${var2}\" non trovato" >> "$log" && _error "$var"
  fi
}

# Funzione che invia il contenuto dei file di una directory al file di log
function _dir {
  nome_e_riga "$1"

  # Se la directory non esiste, stampa un output sul log ed esce.
  if [ ! -d "$1" ]; then
    echo "La directory non esiste" >> "$log" && _error "$1"
    return
  fi

  # Variabili locali
  local file
  # numfile contiene il numero di file contenuti nella directory. Solo primo livello.
  local numfile=$(find "$1" -maxdepth 1 -type f | wc -l)
  # numdir contiene il numero di sottodirectory contenute nella directory. Solo primo livello.
  local numdir=$(find "$1" -maxdepth 1 -type d | wc -l)

  if [ "$numfile" -eq 0 ] && [ "$numdir" -eq 1 ]; then
    echo "La directory non contiene file o directory" >> "$log" && _error "$1"
  else
    echo "La directory contiene ${numfile} file e $(($numdir - 1)) directory" >> "$log"
    ls -al "$1" >> "$log"
    # invia al log il contenuto dei file della directory
    for file in "$1"*; do
      if [ -f "$file" ]; then
        nome_e_riga "$file"
        _prompt "$file"
        cat "$file" &>> "$log" && _ok "$file" || _error "$file"
      fi
    done

    # Funzione che invia al log il contenuto dei file presenti nelle sottodirectory
    # I due cicli for sono separati per permettere l'output di un file subito dopo
    # la directory a cui appartiene
    for file in "$1"*; do
      if [ -d "$file" ]; then
	_dir "$file/"
      fi
    done
  fi
}

# Funzione che elenca i pacchetti installati in base alla parola
# passata come parametro ($1)

function _pack {
  nome_e_riga "Pacchetti che contengono \"$1\""

  _prompt "$1"

  # Variabile che contiene i pacchetti trovati
  local packages=$(dpkg -l | grep -i "$1")

  if [ -z "$packages" ]; then
     echo "Nessun pacchetto installato" >> "$log" && _error "$1"
  else
     echo "$packages" >> "$log" && _ok "$1"
  fi
}

# Funzione che verifica l'esistenza e l'esecuzione di alcuni demoni
# Viene chiamata con due parametri:
# $1 - percorso dell'eseguibile
# $2 - nome da visualizzare
# Se si vuol visualizzare la versione del demone, inserire il comando adatto
# all'interno del ciclo 'case', allo stesso modo specificare al suo interno
# anche il nome dello script d'avvio per fermare, avviare, etc il demone

function _demone {

  # vers = versione del demone ; var = nome dello script d'avvio del demone
  local vers="" var=""
  nome_e_riga "$2"
  _prompt "$2"
  if [ -f "$1" ]; then
    case "$1" in
	/usr/sbin/NetworkManager)
                                  vers=$(NetworkManager --version)
                                  var="network-manager"
                                  ;;
	/usr/sbin/wicd)
                                  vers=$(wicd -h | head -2 | tail -1)
                                  var="wicd"
                                  ;;
    esac
   
    echo "$2 è installato (versione "$vers")" >> "$log" && _ok "$2"
    invoke-rc.d "$var" status &>/dev/null
    [ $? -eq 0 ] && echo "$2 è in esecuzione" >> "$log" || echo "$2 non è in esecuzione" >> "$log"
  else
    echo "$2 non è installato" >> "$log" && _error "$2"
  fi
}

# --------------------------------------------------------------------------
# Funzioni utilizzate per tipo di problema (particolari)
# --------------------------------------------------------------------------

# comando 'cat /sys/class/dmi/id/{sys_vendor,product_name,product_version,bios_version}'
function _dmi_decode {
  local var="/sys/class/dmi/id/*"
  nome_e_riga "$var"
  _prompt "$var"
  if [ -f /sys/class/dmi/id/sys_vendor ]; then
    echo "Produttore: $(cat /sys/class/dmi/id/sys_vendor)"      &>> "$log"
    echo "Prodotto:   $(cat /sys/class/dmi/id/product_name)"    &>> "$log"
    echo "Versione:   $(cat /sys/class/dmi/id/product_version)" &>> "$log"
    echo "BIOS vers.: $(cat /sys/class/dmi/id/bios_version)"    &>> "$log" && _ok "$var" || _error "$var"
  else
    echo "File /sys/class/dmi/id/sys_vendor non trovato" >> "$log" && _error "$var"
  fi
}

# esistenza di pacchetti contenenti firmware e firmware presente sulla macchina
function _firmware {
  local i var="Firmware"
  nome_e_riga "$var"
  dpkg -l | grep -i firmware >> "$log" && _ok "$var"
  echo >> "$log"

  # Elenca i file contenuti nelle directory specificate
  for i in "/usr/lib/firmware" "/usr/local/lib/firmware" "/lib/firmware" "/run/udev/firmware-missing"; do
    if [ -d "$i" ]; then
      echo "Contenuto di ${i}" >> "$log"
      ls -al "$i" >> "$log"
    else
      echo "${i} non trovata" >> "$log"
    fi
    echo >> "$log"
  done
}

# Stampa sullo standard output l'eseguibile associato a x-session-manager (il default)
function _x_session_manager {
  update-alternatives --query "x-session-manager" |
    awk '$1 ~ /^Value:$/ { print $2; exit 0 }'
}

# Stampa sullo standard output l'eseguibile associato a x-window-manager (il default)
function _x_window_manager {
  update-alternatives --query "x-window-manager" |
    awk '$1 ~ /^Value:$/ { print $2; exit 0 }'
}

# Stampa la lista dei pacchetti installati che soddisfano una data dipendenza
# con versione (del programma e in Debian) e archivio di provenienza
# Viene chiamata con un parametro:
# $1 - nome della dipendenza
function _soddisfa {
  echo "Installati (${1}):"
  aptitude search '?installed?provides('"$1"')' --disable-columns \
    --display-format "- %p (versione: %n [Debian: %v]; archivio: %t)"
}

# Restituisce un exit status di 0 solo se l'eseguibile con il nome scelto è in esecuzione da parte dell'utente ($utente)
# Viene chiamata con un parametro:
# $1 - comando di cui controllare l'esecuzione da parte di $utente
function _is_running {
  local list_pids_user list_pids_bin pid pid2
  list_pids_user=$(ps -U "$utente" -o pid) # lista di interi, separati da spazi, con i PID dei processi avviati da $utente
  list_pids_bin=$(pidof -- "$1")           # lista di interi, separati da spazi, con i PID dei processi del comando $1
  for pid in $list_pids_user; do
    for pid2 in $list_pids_bin; do
      if [ "$pid" = "$pid2" ]; then
        return 0  # trovato
      fi
    done
  done
  return 1        # non trovato!
}

# Funzione che <<cerca>> di ricavare il nome e la versione del DE/WM utilizzato
function _de_wm {
  nome_e_riga "Desktop Environment - Window Manager"
  _prompt "DE/WM"
  {
    # impostazione di default
    echo -n $'Default:\n- x-session-manager: '
    _x_session_manager
    echo -n "- x-window-manager: "
    _x_window_manager
    # installati
    _soddisfa "x-session-manager"
    #_soddisfa "x-window-manager" # non essenziale e impiega già tanto
  } >> "$log"
  # in esecuzione
  echo -n "In esecuzione: " >> "$log"
  if _is_running "ksmserver"; then kde4-config --version >> "$log" && _ok "DE/WM" || _error "DE/WM"                         # KDE4
  elif _is_running "gnome-shell"; then gnome-shell --version >> "$log" && _ok "DE/WM" || _error "DE/WM"                     # Gnome Shell
  elif _is_running "xfdesktop"; then xfce4-about -V | head -n1 | cut -d ' ' -f2- >> "$log" && _ok "DE/WM" || _error "DE/WM" # Xfce4
  elif _is_running "openbox"; then
    if [ "$(_x_session_manager)" != "/usr/bin/openbox-session" ]; then
      echo -n "(altro x-session-manager) + " >> "$log"                                                                      # Session manager (LXDE?) + Openbox
    fi
    openbox --version | head -n 1 >> "$log" && _ok "DE/WM" || _error "DE/WM"                                                # Openbox
  else
    echo "Sconosciuto" >> "$log" && _error "DE/WM"                                                                          # NON TROVATO
  fi
}

# Funzione che elenca i pacchetti non appartenenti alla release di default utilizzata
function _extpack {

  # Variabile che contiene la release attualmente utilizzata
  # Vengono tolti eventuali spazi iniziali e tolte le righe che *non* iniziano con la stringa
  # "deb http://ftp.XX.debian.org" e che *non* contengono un nome di release.
  # Con "cut" viene prelevato il terzo campo (la release voluta)
  local release=$(sed -e 's/^ *//' -e '/^deb http:\/\/ftp\...\.debian\.org.*\('"$STABLE"' \|stable \|'"$TESTING"' \|testing \|sid \|unstable \)/!d' /etc/apt/sources.list | cut -d ' ' -f3)
  
  # Numero di release trovate
  local num=$(echo "$release" | wc -l)
  
  local var="Pacchetti esterni"
  _prompt "$var"

  # Se il numero di release è diverso da 1, la funzione termina
  if [ "$num" -ne 1 ]; then
    nome_e_riga "$var"
    echo "Sono presenti ${num} release in sources.list" >> "$log" && _error "$var"
    return
  fi
  
  local pkg=""

  # Se il numero di release è uguale a 1, la variabile pkg conterrà i pacchetti *non* facenti parte della release
  case "$release" in
        "$STABLE"|stable)
			 release="stable"
			 pkg=$(aptitude -F '%p %v %t' search '~i !~Astable'   --disable-columns | column -t) ;;
        "$TESTING"|testing)
			 release="testing"
			 pkg=$(aptitude -F '%p %v %t' search '~i !~Atesting'  --disable-columns | column -t) ;;
        sid|unstable)	
			 release="unstable"
			 pkg=$(aptitude -F '%p %v %t' search '~i !~Aunstable' --disable-columns | column -t) ;;
  esac

  # Invia al log il contenuto di pkg (se esiste)
  nome_e_riga "${var} all'archivio \"${release}\""
  if [ -z "$pkg" ]; then
     echo "Nessun pacchetto esterno installato" >> "$log" && _error "$var"
  else
     echo "$pkg" >> "$log" && _ok "$var"
  fi
}

# --------------------------------------------------------------------------
# Main
# --------------------------------------------------------------------------

clear

_intro
_avvertenze
_check
_scelta
_hide
_upload
_compress
_exit

Changelog

1.0.38
Corretto il rilevamento di Xfce
Invio al log dell'intero file NetworkManager.conf
Corrette alcune variabili non quotate
S3v 17:15, 31 lug 2014 (CEST)
1.0.37
Corretto invio data ultimo aggiornamento in mancanza di history.log
Invio al log di "managed=true/false" contenuto in /etc/NetworkManager/NetworkManager.conf
S3v 07:34, 11 lug 2014 (CEST)
1.0.36
corretto errore di sintassi dovuta ad una mancata istruzione if
Selky 22:48, 10 lug 2014 (CEST)
1.0.35
All'inizio del log viene visualizzato il tipo di problema scelto
Non vengono nascosti il nome utente e il nome host se uguali a [Dd]ebian
La data dell'ultimo aggiornamento viene prelevata da history.log.1.gz
se non contenuta in history.log
Rimossa la funzione _extpack_supp (lentissima)
Modifiche minori
S3v 13:00, 4 lug 2014 (CEST)
1.0.34
Corretta la variabile contenente spazi
/etc/NetworkManager/system-connections
1.0.33
Corretta la funzione _extpack_supp che non mostrava correttamente tutti
i pacchetti con origine
S3v 23:46, 29 apr 2014 (CEST)
1.0.32
Create le funzioni _lastupd (visualizza la data dell'ultimo aggiornamento),
_extpack_supp (inserisce l'origine da cui provengono i pacchetti esterni)
Sostituito il comando mount con findmnt
S3v 13:04, 14 apr 2014 (CEST)
1.0.31
Modificata la funzione _comando per renderla più breve
Aggiunta l'informazione nel log sull'origine dei pacchetti esterni
Modifiche minori
S3v 00:19, 8 apr 2014 (CEST)
1.0.30
Bloccato l'invio a p.d.n per un file più grande di 60x4 K
Variabile "var" in _demone per tener conto del nome dello script d'avvio
S3v 19:41, 4 mar 2014 (CET)
1.0.29
Introduzione variabile in _pack e _extpack
Rilevamento Xfce4
Modifiche minori
S3v 14:39, 23 feb 2014 (CET)
1.0.28
Modificata la funzione _hide per nascondere nel log ulteriori informazioni
sensibili introdotte da NM
S3v 13:03, 17 feb 2014 (CET)
1.0.27
Aggiunto comando "rfkill list all" ai problemi di rete
S3v 20:51, 10 feb 2014 (CET)
1.0.26
Aggiunta funzione "_extpack" alla funzione "_common" per visualizzare i pacchetti installati
che non appartengono alla release di default utilizzata
Gnome Shell tra i DE rilevati
S3v 13:02, 5 feb 2014 (CET)
1.0.25
Aggiunti codici carattere e accorciato il "case" di scelta
Aggiunto comando "dkms status" a problemi video.
Modifiche minori
S3v 11:17, 31 dic 2013 (CET)
1.0.24
Aggiunta la scelta per problemi generici
Nascosto gli ESSID e nomi connessione inviati da NM in syslog
S3v 15:24, 6 dic 2013 (CET)
1.0.23
rimossa la variabile "stat_log" e modificato l'umask per permettere l'esecuzione dello script ALSA
logname al posto di who
create funzioni _audio (problemi audio) e _tpad (problemi touchpad)
creata la funzione _hide per sostituire il vero nome utente e il vero nome dell'host
rimossi i parametri da _compress_ok e _compress_error (inutilizzati)
modificato _comando per l'esecuzione del comando "su"
sostituito pgrep con ps
modifiche minori
S3v 18:51, 29 nov 2013 (CET)
1.0.22
create funzioni _exit, _data, _common (output per tutti i tipi di problema),
_apt (problemi con i pacchetti), _mount (problemi di mount/umount), _de_wm
(cerca di stabilire il DE/WM) e _demone (esistenza e versione di un demone)
cancellate le funzioni _altro (rinominata in _common), _nm e _wicd (inglobate in _demone),
_syslog (inglobata in _file), _iwconfig e _iwlist (inglobate in _comando)
output per ricavare il DM da /etc/X11/default-display-manager
tolto l'array da _firmware e "resolvconf in _pack"
nome del log in base alla data corrente e variabile "utente" (nome utente != root)
Modificata _comando per contemplare il comando "su"
modifiche minori
S3v 15:50, 22 nov 2013 (CET)
1.0.21
Modificata la funzione _file: essid e psk presenti in /etc/network/interfaces non vengono più riportati nel log
Metaldaze 18:34, 1 nov 2013 (CET)
1.0.20
Creata la funzione _pack per inviare al log i pacchetti installati in base ad una parola
Rimossa _dhcp, la sua funzione è stata inglobata in _pack
Invio al log dei pacchetti nVidia attraverso _pack
Invio al log dei pacchetti nouveau attraverso _pack
Invio al log dei pacchetti mesa attraverso _pack
S3v 20:01, 5 ott 2013 (CEST)
1.0.19
Funzione _dir - contemplato il caso di directory inesistente
S3v 14:42, 4 ott 2013 (CEST)
1.0.18
Creata la funzione _dir che invia al log il contenuto dei file di una directory
Modificate le funzioni _ok e _error per consentire lunghezze dell'output maggiori
Aggiunto in output il contenuto di xorg.conf, xorg.conf.d/ e sources.list.d/
S3v 13:59, 4 ott 2013 (CEST)
1.0.17
Aggiunta la funzione _video - Problemi video
S3v 13:31, 3 ott 2013 (CEST)
1.0.16
Aggiunta directory /run/udev/firmware-missing alla funzione _firmware
S3v 17:25, 26 ago 2013 (CEST)
1.0.15
Tolta la funzione _spazi (inutilizzata)
Soppresso l'output di errore di pastebinit
Modificate _iwconfig e _iwlist per mostrare ESSID=off/any
S3v 11:34, 21 giu 2013 (CEST)
1.0.14
Voce del menù per la risoluzione dei problemi di rete (funzione _rete)
Creata funzione _altro
_resolvconf inglobata in _comando
Introdotto il comando dmesg per filtrare errori e warning separatamente
S3v 20:49, 7 giu 2013 (CEST)
1.0.13
Reinserita la funzione _syslog per prelevare l'ultimo output utile solo da syslog o, eventualmente,
da syslog.1 e syslog
S3v 16:07, 1 giu 2013 (CEST)
1.0.12
Inserito il path di default
Sostituito il comando cat con echo nei messaggi a video
Inserito un menù di scelta e rimosso l'array delle funzioni
Inserite due funzioni per inviare al log un file o un output generico
lspci -knn
Rimossa _dmesg (l'ouput è fornito da syslog)
S3v 15:25, 23 mag 2013 (CEST)
1.0.11
Modificata la funzione _wicd
S3v 00:57, 15 mag 2013 (CEST)
1.0.10
Tolta la funzione iptables per motivi di sicurezza
Impostata una maschera di default per i file creati dallo script
Modifiche minori
S3v 11:19, 14 mag 2013 (CEST)
1.0.9
Aggiunta funzionalità per aggiungere i log di sistema (/var/log/syslog e /var/log/syslog.1)
Aki 14:20 3 mag 2013 (CEST);
1.0.8
Integrazione funzionalità upload per supportare la verifica della ricezione da parte di http://paste.debian.net
Revisione messaggistica in caso di fallito invio a http://paste.debian.net
Aki 12:40 2 mag 2013 (CEST);
1.0.7
Aggiunta funzionalità per identificazione produttore e modello del computer secondo lo standard SMBIOS/DMI
Aggiunta rimozione valore ESSID dall'output del comando iwconfig
Aggiunto controllo esito invio log verso http://paste.debian.net (in caso di falito invio)
Anticipazione ed unificazione nell'ordine del codice sorgente delle sezioni relative al controllo del sistema apt
Aki 13:40 27 apr 2013 (CEST);
1.0.6
Aggiunta funzionalità per verifiche sullo stato del gestiore dei pacchetti (comandi apt-cache policy, apt-cache status)
Aki 10:39 26 apr 2013 (CEST)
1.0.5
Aggiunta funzionalità frammentazione log per invio a http://paste.debian.net
Aggiunta funzionalità per verifiche sullo stato dei dischi (comandi fdisk -l , mount, df -h)
Aggiunta funzionalità per verifica del file /etc/fstab
Apportate alcune variazioni ai messaggi diagnostici
Collegamento con la guida su Come formulare quesiti tecnici al forum
Aki 13:30 25 apr 2013 (CEST)
1.0.4
Tolto qualche echo e inserito un messaggio di mancato invio log a p.d.n
S3v 18:15, 20 apr 2013 (CEST)
1.0.3
Aggiunta rimozione valore ESSID dalla scansione delle reti wireless
Aki 20:34 14 apr 2013 (CEST)
1.0.2
Aggiunta avvertenza su esplicito consenso all'invio verso paste.debian.net
S3v 14:56, 14 apr 2013 (CEST)
1.0.1
Corretta la funzione "dmesg" che svuotava il buffer e non produceva output
S3v 12:22, 14 apr 2013 (CEST)




Guida scritta da: S3v 23:38, 13 apr 2013 (CEST) Swirl-auth20.png Debianized 20%
Estesa da:
Verificata da:

Verificare ed estendere la guida | Cos'è una guida Debianized