Jak jsem stavěl HTPC
Protože mi nevyhovoval můj rekordér tak jsem se rozhodl postavit si vlastní, neboť i kupované mi nevyhovovaly z důvodu buď velké ceny a nebo z důvodu programování (málo pozic, nemožné některé kombinace atd....)
Takže na čem to postavit aby to bylo levné a použitelné?
Po prohlédnutí různých MB jsem se rozhodl pro ASUS AT3N7A-I kterou jsem zavřel s TV kartou AverTV Hybrid+FM PCI A16D kterou už jsem měl koupenou. Vše jsem to vestavěl do skříně s 200W zdrojem a zde nastal první problém, dle manuálu od MB tato deska potřebuje 400W zdroj ! A nebo aspoň na větvi +12V zdoj co dodá 15A což můj nesplňuje dodá pouze 10A ovšem to mě neodradilo a seskládal jsem to dohromady s tím že pokud s toho nebudu ždímat maximum a připojovat hromadu věcí tak by to zdroj měl utáhnout.
No zatím to šlape ovšem co za OS?
No než jsem tam nainstaloval linux tak jsem vyskoušel windows, měl jsem windows visty basic 32b které nechodily nic moc, instalace windows XP tak to chodilo o hodně rychleji, ovšem SW se mi nepozdával tak jsem přikročil k instalaci linuxu.
Takže co tam nainstalovat no rozhodl jsem se že vyskouším mythbuntu ovšem to se mi nepovedlo rozchodit a nějak jsem nepátral proč a odložil jsem ho. No a rozhodl jsem se nainstalovat svoji oblíbenou distribuci Fedora 11 64b.
No po instalaci jsem sprovoznil TV kartu a pomocí mencoderu nahrávám OK ovšem co s toho když budu chtít nahrát něco když nejsem doma?
No protože pro HTCP nic moc není tak jsem se rozhodl že vyskouším mythtv.
Ovšem pod fedorou jsem to taky nerozchodil, lépe řečeno rozchodil i naladil analogové programy ovšem jak jsem je chtěl přepnout v mythtv tak to hodilo vždy chybu zobrazení.
Takže jsem se na to vykašlal a budu nahrávat přímo pomocí mencoderu a cronu.
Toto má několik úskalí, zatím do cronu zadávám vše ručně pomocí crontab -e
a napsal jsem si skrypt který provede záznam, nazval jsem ho záznam a umístil do svého domovského adresáře do složky bin.
Soubor zaznam v /home/petr/bin
#!/usr/bin/perl die "$0 má špatný počet parametrů.\n\nSprávně má být:\n$0 Kanál norma délka_záznamu\n$0 E5 PAL-DK 01:00:00\n\n" if @ARGV != 3; $soubor_avi=`LC_TIME="cs_CZ.UTF-8" date +%A-%d.%m.%Y-%H:%M.avi`; if ( not (`ps -A | grep "mencoder"` or `ps -A | grep "mplayer"`)) { system "mencoder tv://$ARGV[0] -tv driver=v4l2:norm=$ARGV[1]:input=0:alsa:adevice=hw.1,0:audiorate=32000:forceaudio:immediatemode=0 -ovc lavc -lavcopts vcodec=mpeg4:vbitrate=3000 -oac mp3lame -lameopts cbr:br=128 -endpos $ARGV[2] -o /home/petr/Videa/$soubor_avi >/dev/null 2>>/home/petr/error.txt"; } # Uzivatelsky cron podle ktereho budeme spoustet PC $SOUBOR_CRON="/tmp/petr_crontab.txt"; # Pri debug 1 vypisujeme co delame (0 = jsme potichu) $DEBUG=0; system "crontab -l > /tmp/petr_crontab.txt"; open(DATA, "<", $SOUBOR_CRON) or die "Nelze otevřít soubor: $!"; $cas=0; $starycas=0; while ($radek=<DATA>) { chomp $radek; # je neco na radku - spracujeme if (length($radek)>0) { if ($DEBUG==1) { print $radek . "\n"; } use Schedule::Cron::Events; my $cron = new Schedule::Cron::Events( $radek, Seconds => time()); my ($sec, $min, $hour, $day, $month, $year) = $cron->nextEvent; if ($DEBUG==1) { printf("Další start: %2d:%02d:%02d on %d.%02d.%d\n", $hour, $min, $sec, $day, ($month+1), ($year+1900)); } # turn a local date into a Unix time use Time::Local; my $epochSecs = timelocal($sec, $min, $hour, $day, $month, $year); if ($DEBUG==1) { print "počet " . $epochSecs . " sekund co je " . localtime($epochSecs) . "\n"; } # Vybirame nejdrivejsi cas if ($starycas==0) { $starycas=$epochSecs; $cas=$epochSecs; } if ($epochSecs<$starycas) { $cas=$epochSecs; $starycas=$epochSecs; } # konec spracovani radku } # konec spracovani souboru } close DATA; if ($DEBUG==1) { print "Ted je cas: " . time() . "\n"; } # Odecteme 10 minut $cas-=600; if ($cas>time() and `w | grep " 1 user"` ) { exec "sudo /sbin/shutdown -h now 2>>/home/petr/error.txt"; }
Tímto skriptem budeme nahrávat, pokud bude pouze automaticky přihlášený jeden uživatel tak vypneme PC a proto musíme nastavit sudo aby uživatelé mohly spustit /sbin/shutdown
bez hesla.
Teď potřebujeme něco co zajistí aby se cron spustil i kdž se pouze spustí PC a nikdo se nepřihlásí, uživatelský cron se spustí pouze jak se uživatel přihlásí a protože nepotřebujeme bezpečnost upravíme druhou textovou konzoli aby se tam automaticky přihlašoval uživatel petr.
Takže upravíme soubor /etc/event.d/tty2
# tty2 - getty # # This service maintains a getty on tty2 from the point the system is # started until it is shut down again. start on stopped rc2 start on stopped rc3 start on stopped rc4 start on started prefdm stop on runlevel 0 stop on runlevel 1 stop on runlevel 6 respawn exec /sbin/mingetty --autologin petr tty2
Tak po spuštění PC se přihlásí automaticky uživatel petr na konzoli tty2
Teď musíme zajistit aby při vypnutí PC se nastavilo probuzení PC.
Jak postupovat při probuzení jsem nastudoval z ACPI wakeup a MythTv ACPI Wakeup.
Teď potřebujeme přečíst uživatelský cron a podle něho nastavit probuzení. Na to jsem čerpal nápad od Dotaz: Převod "0 20 * * 2,4" na aktuální čas a vylezl ztoho nakonec skript cron.pl.
#!/usr/bin/perl # Uzivatelsky cron podle ktereho budeme spoustet PC $SOUBOR_CRON="/var/spool/cron/petr"; # Zapisem do souboru nastavime alarm $ACPI_WAKE_UP="/sys/class/rtc/rtc0/wakealarm"; # Pri debug 1 vypisujeme co delame (0 = jsme potichu) $DEBUG=1; open(DATA, "<", $SOUBOR_CRON) or die "Nelze otevřít soubor: $!"; $cas=0; $starycas=0; while ($radek=<DATA>) { chomp $radek; # je neco na radku - spracujeme if (length($radek)>0) { if ($DEBUG==1) { print $radek . "\n"; } use Schedule::Cron::Events; my $cron = new Schedule::Cron::Events( $radek, Seconds => time()); my ($sec, $min, $hour, $day, $month, $year) = $cron->nextEvent; if ($DEBUG==1) { printf("Další start: %2d:%02d:%02d on %d.%02d.%d\n", $hour, $min, $sec, $day, ($month+1), ($year+1900)); } # turn a local date into a Unix time use Time::Local; my $epochSecs = timelocal($sec, $min, $hour, $day, $month, $year); if ($DEBUG==1) { print "počet " . $epochSecs . " sekund co je " . localtime($epochSecs) . "\n"; } # Vybirame nejdrivejsi cas if ($starycas==0) { $starycas=$epochSecs; $cas=$epochSecs; } if ($epochSecs<$starycas) { $cas=$epochSecs; $starycas=$epochSecs;} # konec spracovani radku } # konec spracovani souboru } close DATA; # pokud neni cas vetsi jak aktualni nic nedelame if ($cas>time()) { if ($DEBUG==1) { print "Ted je cas: " . time() . "\n"; } if ($DEBUG==1) { print "Nejblizsi cas spusteni nahravani " . $cas . " sekund co je " . localtime($cas) ."\n"; } # Odecteme 5 minut $cas-=300; if ($DEBUG==1) { print "Nejblizsi cas spusteni HTPC (cas nahravani - 5 minut) " . $cas . " sekund co je " . localtime($cas) ."\n"; } # reset Alarm open(ALARM, ">", $ACPI_WAKE_UP) or die "Nelze otevřít soubor: $!"; print ALARM "0"; close ALARM; # Zapis alarmu open(ALARM, ">", $ACPI_WAKE_UP) or die "Nelze otevřít soubor: $!"; print ALARM $cas; close ALARM; }
No a teď ten skript musíme při vypnutí PC nějak zavolat. No pod fedorou jsem to vyřešil že jsem upravil /etc/rc.d/init.d/halt
v kterém jsem našel: [ -x /sbin/hwclock ] && action $"Syncing hardware clock to system time" /sbin/hwclock --systohc
a za to dodal spuštění skriptu cron.pl což jsem provedl vložením:
#Nastaveni alarmu [ -x /home/petr/bin/cron.pl ] && /home/petr/bin/cron.pl
A teď to chce naplnit cron záznamy pro nahrávání a otestovat zda to funguje.
Doufám že se to bude někomu hodit, samozřejmě řádky s mencoderem a mplayerem třeba upravit podle potřeb, tak stejně různé parametry.
Pro normální dívání používám script tv:
#!/usr/bin/perl die "$0 má špatný počet parametrů.\n\nSprávně má být:\n$0 Kanál\n$0 nova\n\n" if @ARGV != 1; if ( $ARGV[0] eq "ex" or $ARGV[0] eq "stv1" or $ARGV[0] eq "ct24" ) { $norma="PAL-BG";} else{ $norma="PAL-DK"; } #printf "argument: " . $ARGV[0] ; if ( not (`ps -A | grep "mencoder"` or `ps -A | grep "mplayer"`)) { system "mplayer tv://$ARGV[0] -tv driver=v4l2:norm=$norma:volume=100:alsa=on:adevice=hw.1,0:amode=1:audiorate=32000:forceaudio:immediatemode=0:channels=r12-ct1,r8-ct2,r10-nova,r6-prima,se7-stv1,se13-ex,r7-ct24"; }