{$M 65520,0,655360}
program dekodavimas_6_bitais;
  { 142 u‘davinys }
  { programa dekoduoja u‘koduot… byl… }

  const
   BITAI = 6;         { bit— grup‚s ilgis }
   LENT: string[64] = { kodavimui naudojami simboliai }
          '0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz+-';
   MAX = 10000; { maksimalus u‘koduotos bylos dydis baitais }

  procedure klaida;
  { nutraukia programos darb… d‚l Ťvedimo/ižvedimo klaidos }
  begin
    writeln ('­vedimo/ižvedimo klaida!');
    halt;
  end; { klaida }

  procedure atidar_bylas (var fskait: text; var fras: file);
  { patikrina parametrus ir atidaro bylas }
  begin
    writeln;
    if paramcount <> 2 { jei nenurodyti tinkami parametrai }
       then begin
              writeln ('Naudojimas: ');
              writeln( ' 142_DEK.EXE  duom.dat rez.dat' );
              writeln;
              halt;
            end;
    assign (fskait, paramstr(1));
    {$I-}
    reset (fskait);
    {$I+}
    if ioresult <> 0
       then klaida;
    assign (fras, paramstr(2));
    {$I-}
    rewrite (fras, 1);
    {$i+}
    if ioresult <> 0
       then klaida;
  end; { atidar_bylas }

  procedure uzdar_bylas (var fskait: text; var fras: file);
  begin
    close (fras);
    close (fskait);
  end; { u‘dar_bylas }

  function numeris (c: char): integer;
  { randa simbolio c numerŤ lentel‚je LENT }
    var rasta: boolean;
        i: integer;
  begin
    i := 0; rasta := false;
    while (i < 64) and not rasta do
      begin
        i := i + 1;
        rasta := c = LENT[i];
      end;
    if rasta
       then numeris := i
       else numeris := 0
  end; { numeris }

  procedure dekodavimas (var fskait: text; var fras: file);
  { dekoduoja duomenis }
    var rez: array [1..MAX] of byte;
        num, nr, poslinkis, dydis: integer;
        simb: char;
  begin
    { inicializuojame rezultat— masyv… }
    fillchar (rez, sizeof(rez), 0);
    poslinkis := 0; { poslinkis baito prad‘ios at‘vilgiu }
    nr := 1; { baito numeris atkoduotame tekste }
    while not eof (fskait) do
      begin
        { iž u‘koduotos bylos perskaitome simbolŤ }
        read (fskait, simb);
        { randame jo numerŤ simboli— eilut‚je lent }
        num := numeris (simb);
        { jei tokio numerio nerasta }
        if num = 0
           then klaida;
        { dekoduojame bait… }
        rez[nr] := byte(rez[nr] + (num-1) shl poslinkis);
        if poslinkis > 2
           then rez[nr+1] := byte((num-1) shr (8 - poslinkis));
        { perskai‡iuojame poslinkŤ }
        poslinkis := poslinkis + BITAI;
        if poslinkis > 7
           then begin
                  poslinkis := poslinkis - 8;
                  nr := nr + 1
                end;
      end;
    { suma‘iname nr reikžmŠ: arba ji buvo padidinta be reikalo }
    { arba paskutinysis baitas u‘pildytas u‘koduojant papildomai }
    { priražytais nuliais }
    nr := nr - 1;
    { Ťražome dekoduotus duomenis Ť rezultat— byl… }
    blockwrite (fras, rez, nr, dydis);
    if nr <> dydis
       then klaida;
  end; { kodavimas }

  var fskait: text;
      fras: file;
begin
  atidar_bylas (fskait, fras);
  dekodavimas (fskait, fras);
  uzdar_bylas (fskait, fras);
end.


