#!/bin/bash

# VierScan 1.1 - Ein freier Vieren-Scanner - a free Vieren-scanner
#
# Copyright (C) 2005, 2007 Peter Gerwinski <http://www.peter.gerwinski.de>
#
# VierScan 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 3 of the License,
# or (at your option) any later version.
#
# VierScan 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 VierScan; if not, see <http://www.gnu.org/licenses/>.

sigfile=$HOME/.vierscan/signatures
substfile=$HOME/.vierscan/substitution
grep="grep"
sed="sed"
rxsep="\\|"

while [ -n "$*" ]; do
  arg="$1"
  shift
  case "$arg" in
    -h|--help)
      cat << EOF
VierScan 1.1 - Ein freier Vieren-Scanner - a free Vieren-scanner
Copyright (C) 2005, 2007 Peter Gerwinski <http://www.peter.gerwinski.de>

VierScan is free software according to the GNU GPL - see
<http://www.gnu.org/licenses/gpl.html>.

usage: "$0" <options>
 
Valid options are:
 -h, --help           output this help text and exit successfully
 -H, --history        explain the history of this program (in German language)
 -v, --verbose        enter "verbose" mode
 -V, --version        output the version number and exit successfully
 -q, --quiet          suppress all non-error output
 -r, --remove         pipe to stdout, removing all found Vieren
 -R, --replace        replace each found Vier by a virus (use with care!)
 -s x, --sigfile x    use the signature file "x" instead of
                      \$HOME/.vierscan/signatures for reading the
                      regular expressions which identify a Vier
 -S x, --substfile x  use the substitution file "x" instead of
                      \$HOME/.vierscan/substitution for substituting viruses
 -E, --extended-regexp, --regexp-extended   use extended regular expressions

return value: 1 on error, 2 on an unsuccessful scan, 0 on success

(Remark: "Vier" is the German word for "four" (the number 4). Its plural
is "Vieren" which looks similar to "Viren" (= "viruses"). There are many
scanners against computer Viren, but this one is the first elaborate
scanner against Vieren.:-)
EOF
      exit 0
    ;;
    -H|--history)
      cat << EOF
Zur Geschichte von VierScan
~~~~~~~~~~~~~~~~~~~~~~~~~~~
Vielleicht haben Sie auch schon Anzeigen folgenden Typs gesehen?

  "Schützen Sie Ihren Computer gegen Vieren
  - mit unserer Super-Software!!!!!"

Wenn man nachbohrt, stellt sich häufig heraus, daß sich da
wohl ein Schreibfehler eingeschlichen habe und es sich bei der
"Super-Software" in Wirklichkeit nur um einen handelsüblichen
Viren-Scanner handelt. Aber wo bleibt der Schutz gegen Vieren? Wie
lange noch sollen Millionen von Computern ungeschützt dem Beschuß
von täglich hunderten bis tausenden von Vieren ausgesetzt sein?

Selbst kompetente Kollegen konnten mir zu diesem Thema häufig nicht
mehr sagen als "sed -e 's/4//g' # ;-)". Dabei sind Vieren in E-Mail
und auf Webseiten sogar wesentlich häufiger anzutreffen als die
weithin gefürchteten Viren - was wohl hauptsächlich daran liegt, daß
selbst die kompaktesten Viren eine Größe im Kilobyte-Bereich haben,
während Vieren für ihre Verbreitung nur ein einziges(!) Byte
benötigen.

Aus dieser Situation heraus entstand mein Entschluß, den ersten
wirklich ausgearbeiteten Vieren-Scanner zu schreiben und der
Allgemeinheit als freie Software unter der GNU GPL zur Verfügung
zu stellen. VierScan ist das Ergebnis.

VierScan wird in einer Pipe verwendet. Wenn es eine Vier entdeckt,
schreibt es (außer mit Option -q oder --quiet) eine Warnung zur
Standard-Fehlerausgabe. Es sind aber auch folgende Alternativen
möglich:

 * Kommentarloses Löschen aller Vieren
   (Option -r oder --remove)

 * Ersetzen jeder Vier durch ein Virus (Option -R oder --replace).
   Die auf diese Weise aufbereiteten Daten lassen sich anschließend
   problemlos mit einem handelsüblichen Viren-Scanner ausfiltern.
   (Wir empfehlen ClamAV: http://www.clamav.net)

   WARNUNG: Es gibt einen Hersteller, dessen Betriebssysteme
   tatsächlich anfällig gegenüber Viren sind! Für eventuelle Schäden
   beim nicht-fachgerechten Umgang mit Viren übernehmen wir keinerlei
   Haftung!

   Als Virus für die Substitution kommt beispielsweise die
   EICAR-AntiVirus-Test-Datei in Frage. Da deren Lizenzbedingungen
   leider inkompatibel mit der GNU GPL sind, müssen Sie sich diese
   ggf. selbst unter http://www.eicar.org/anti_virus_test_file.htm
   herunterladen und unter \$HOME/.vierscan/substitution ablegen.

Um auch zukünftigen Anforderungen gerecht werden zu können, greift
VierScan auf eine Signatur-Datei zu, in der Sie stets aktuelle
Vieren-Signaturen ablegen können. Diese Datei liegt standardmäßig
unter \$HOME/.vierscan/signatures und enthält, durch Leerzeilen,
Zeilenenden oder Tabulatoren getrennt, reguläre Ausdrücke für die
von VierScan zu erkennenden Vieren.

Hier ein Beispiel für einen gültigen Inhalt der Signatur-Datei:

  4
  vier
  four quatre quattro dört quattuor kvar
  [cq]uatro 2[+*^]2

Mehr über reguläre Ausdrücke erfahren Sie in der man-Page von grep(1).

VierScan-kompatible Signatur-Updates sind vielerorts im WWW verfügbar,
z.B. unter: http://www.blinde-kuh.de/sprachen/zahlen1-10.html

Noch eine WARNUNG: Dieses Programm wurde bislang nicht in einer
Produktivumgebung getestet! Verwendung auf eigene Gefahr!

    Peter Gerwinski, http://www.peter.gerwinski.de
EOF
      exit 0
    ;;
    -v|--verbose)
      if [ "$quiet" = "y" ]; then
        echo "$0: cannot use --verbose together with --quiet" 1>&2
        exit 1
      fi
      verbose="y"
    ;;
    -V|--version)
      echo "1.1"
      exit 0
    ;;
    -q|--quiet)
      if [ "$verbose" = "y" ]; then
        echo "$0: cannot use --quiet together with --verbose" 1>&2
        exit 1
      fi
      quiet="y"
    ;;
    -r|--remove)
      if [ "$replace" = "y" ]; then
        echo "$0: cannot use --remove together with --replace" 1>&2
        exit 1
      fi
      remove="y"
    ;;
    -R|--replace)
      if [ "$remove" = "y" ]; then
        echo "$0: cannot use --replace together with --remove" 1>&2
        exit 1
      fi
      replace="y"
    ;;
    -s|--sigfile)
      sigfile="$1"
      shift
    ;;
    -S|--substfile)
      substfile="$1"
      shift
    ;;
    -E|--extended-regexp|--regexp-extended)
      grep="grep -E"
      sed="sed -r"
      rxsep="|"
    ;;
    *)
      echo -e "$0: invalid option(s) - please try \"$0 --help\"" 1>&2
      exit 1
    ;;
  esac
done

if [ "$verbose" = "y" ]; then
  echo -e "$0: using signature file \"$sigfile\"" 1>&2
  if [ "$replace" = "y" ]; then
    echo -e "$0: using substitution file \"$substfile\"" 1>&2
  fi
  if [ "$sed" = "sed -r" ]; then
    echo -e "$0: using extended regular expressions" 1>&2
  fi
fi

if [ -e "$sigfile" ]; then
  if [ "$verbose" = "y" ]; then
    echo -e "$0: reading signature file ..." 1>&2
    echo -n "$0: " 1>&2
  fi
  regexp=""
  for x in `IFS="" cat "$sigfile"`; do
    if [ "$verbose" = "y" ]; then
      echo -n " $x" 1>&2
    fi
    if [ -z "$regexp" ]; then
      regexp="$x"
    else
      regexp="$regexp$rxsep$x"
    fi
  done
  if [ "$verbose" = "y" ]; then
    echo 1>&2
    echo "$0: ... done." 1>&2
    echo -e "$0: using regexp \"$regexp\"" 1>&2
  fi
else
  regexp="4"
  if [ "$verbose" = "y" ]; then
    echo -e "$0: no signature file - using the regexp \"$regexp\" instead" 1>&2
  fi
fi

if [ "$quiet" != "y" ]; then
  cat << EOF 1>&2
VierScan 1.1 - Ein freier Vieren-Scanner - a free Vieren-scanner
Copyright (C) 2005, 2007 Peter Gerwinski <http://www.peter.gerwinski.de>
VierScan is free software according to the GNU GPL - see
<http://www.gnu.org/licenses/gpl.html>.

Please enter the text to be scanned.
EOF
fi

if [ "$remove" = "y" ]; then
  if [ "$verbose" = "y" ]; then
    echo "$0: starting removal ..." 1>&2
  fi
  $sed -e "s/$regexp//g"
  if [ "$verbose" = "y" ]; then
    echo "$0: ... done." 1>&2
  fi
  exit 0
fi

if [ "$replace" = "y" ]; then
  if [ -f "$substfile" ]; then
    if [ "$verbose" = "y" ]; then
      echo "$0: starting replacement ..." 1>&2
    fi
    $sed -e "s/$regexp/`cat $substfile`/g"
    if [ "$verbose" = "y" ]; then
      echo "$0: ... done." 1>&2
    fi
    exit 0
  else
    echo -e "$0: substitution file \"$substfile\" not found" 1>&2
    exit 1
  fi
fi

if [ "$verbose" = "y" ]; then
  echo "$0: starting scan ..." 1>&2
fi
if $grep "$regexp" > /dev/null; then
  found="y"
fi
if [ "$verbose" = "y" ]; then
  echo "$0: ... done." 1>&2
  if [ "$found" = "y" ]; then
    echo "$0: result: Vieren found" 1>&2
  else
    echo "$0: result: no Vieren" 1>&2
  fi
fi
if [ "$found" = "y" ]; then
  if [ "$quiet" != "y" ]; then
    echo "Vieren FOUND" 1>&2
  fi
  exit 0
else
  exit 2
fi
