Jag försöker hitta ett effektivt sätt att göra nivå 5 i OverTheWire-banditutmaningen .

Hur som helst, jag har en massa filer, och det finns bara en som respekterar följande kriterier:

  • Mänsklig
  • 1033 byte i storlek
  • Ej körbar

Just nu använder jag kommandot find , och jag kan hitta filerna som matchar de två sista kriterierna:

find . -size 1033c ! -executable 

Jag vet dock inte hur man kan utesluta icke-läsbara filer Lösningar som jag hittade för den utmaningen använder testparametern -readable, men jag tycker inte att det fungerar. -readable tittar bara på filernas behörigheter och inte på dess innehåll, medan utmaningsbeskrivningen ber om en ASCII-fil eller något liknande.

Kommentarer

  • Hur definierar du mänskligt läsbart? Inte binärt?
  • filkommandot är din vän 🙂
  • Kanske duplikat av: stackoverflow.com/questions/14505218/…
  • Människor är en av de mest intelligenta kända arterna på jorden. De ’ är också de enda kända för datorer. De kan läsa de flesta filer förutsatt att de kan ta reda på typen och få tag i krypteringsnycklarna för krypterad.
  • SPOILER ALERT !!

Svar

Ja, du kan använda find för att leta efter icke-körbara filer av rätt storlek och använd sedan file för att söka efter ASCII. Något som:

find . -type f -size 1033c ! -executable -exec file {} + | grep ASCII 

Questi på är dock inte så enkelt som det låter. ”Mänskligt läsbart” är en fruktansvärt vag term. Förmodligen menar du text. OK, men vilken typ av text? Latinsk karaktär endast ASCII? Full Unicode? Tänk till exempel på dessa tre filer:

$ cat file1 abcde $ cat file2 αβγδε $ cat file3 abcde αβγδε $ cat file4 #!/bin/sh echo foo 

Allt detta är text och läsbart för människor. Låt oss nu se vad file gör av dem:

$ file * file1: ASCII text file2: UTF-8 Unicode text file3: UTF-8 Unicode text file4: POSIX shell script, ASCII text executable 

Så, find -kommandot ovan hittar bara file1 (för exemplets skull, låt oss föreställa oss att filerna hade 1033 tecken). Du kan utöka find för att leta efter strängen text:

find . -type f -size 1033c ! -executable -exec file {} + | grep -w text 

Med -w skriver grep bara rader där text finns som ett fristående ord. Det ska vara ganska nära det du vill, men jag kan inte garantera att det inte finns någon annan filtyp vars beskrivning också kan innehålla strängen text.

Svar

Medan -exec oftast används för att göra något med filerna som där det finns kan det också fungera som ett test. Därför kan vi lägga till det i dina andra kriterier:

find . \ -size 1033c \ -not -executable \ -exec sh -c "file {} | grep "text$"" \; 

Kom ihåg, grep returnerar icke-noll när mönstret inte hittades, och sh -c "COMMAND" returnerar utvärderingsresultatet (så länge det är giltigt). skriv bara ut filer där file <filename> spottar något som slutar med text, t.ex. ”UTF-8 Unicode-text” eller ”ASCII-text”, men inte ”Icke-ISO-utökad ASCII-text, med escape-sekvenser”.

På en enda rad hamnar den till och med kortare än att gå över xargs:

find . -size 1033c -not -executable -exec sh -c "file {} | grep "text$"" \; 

Håll i tänk på att du kan ersätta sh -c "file {} | grep "text$"" med valfritt anpassat kommando. Om du vill söka efter något väldigt komplext kan det vara en bättre idé att tillhandahålla ett skalskript och använda det istället:

find . -size 1033c -not -executable -exec is_human_readable.sh {} \; 

som på lång sikt kör, är lättare att underhålla än din skalhistorik:

#!/bin/sh file "$@" | grep "text$" > /dev/null 

Kommentarer

  • Trevligt! Observera dock att matchning av text$ utesluter saker som känns igen som skalskript. Allt med en shebang identifieras som ett manus och de är helt mänskliga läsbara.
  • @terdon sant, men skript tenderar att vara körbara: D. Med detta sagt bör ett korrekt skript också känna igen PDF-filer. Men å andra sidan, är en PDF som innehåller en bild mänsklig läsbar ? Är en PNG av någon text läsbar ? Antagligen. Jag antar att ett fullständigt test kommer att vara … utmanande.

Svar

Du behöver bara använda:

find inhere -size 1033c 

Det ger dig den enda filen som innehåller lösenordet.

Kommentarer

  • varför returnerar + 1033c fler filer? är det som ett större eller lika tecken?

Svar

find . -size 1033c ! -executable -exec file {} + 

Svar

Kör bara följande mot innehållet i katalogen:

$ file -- * -file00: data -file01: data -file02: data -file03: data -file04: data -file05: data -file06: data -file07: ASCII text -file08: data -file09: data $ cat -- \-file07 <output> 

Svar

Det finns bara 1 fil med 1033 byte i storlek.

bandit5@bandit:~$ find -size 1033c ./inhere/maybehere07/.file2 bandit5@bandit:~$ 

Varför 1033c och inte 1033? Kontrollera man sidan

 -size n[cwbkMG] File uses n units of space, rounding up. The following suffixes can be used: `b" for 512-byte blocks (this is the default if no suffix is used) `c" for bytes `w" for two-byte words `k" for Kilobytes (units of 1024 bytes) `M" for Megabytes (units of 1048576 bytes) `G" for Gigabytes (units of 1073741824 bytes) 

Verifiera det med kommandot ls -l och file så får du allt svar.

bandit5@bandit:~$ ls -l ./inhere/maybehere07/.file2 -rw-r----- 1 root bandit5 1033 May 7 20:15 ./inhere/maybehere07/.file2 bandit5@bandit:~$ bandit5@bandit:~$ file ./inhere/maybehere07/.file2 ./inhere/maybehere07/.file2: ASCII text, with very long lines bandit5@bandit:~$ 
  1. läsbart för människor (ASCII text)
  2. 1033 byte i storlek (även i ls -l output)
  3. inte körbar (-rw-r-----)

Svar

find . -size 1033c ! -executable|xargs file|grep "ASCII text" |awk -F: "{print $1}" 

Försök med de här kombinerade kommandona. det fungerar på min station.

Svar

Du kan prova detta

find . -size 1033c ! -executable -exec file {} + 

Din utmaning tillåter inte grep. lösenordsfil kommer att rapporteras som ”ASCII-text, med mycket långa rader”

Svar

För att filtrera bort mänskligt läsbara filnamn, du kan använda [:print:] ( utskrivbar ) teckenklass namn. Du hittar mer om sådana klasser i handboken för grep.

find . -type f -size 1033c -name "[[:print:]]*" ! -executable 

På en andra tanke , kan ”mänskligt läsbart” krav hänvisa till filens innehåll istället för dess namn. Med andra ord skulle du söka efter text filer. Det är lite mer knepigt. Som @ D_Bye föreslog i en kommentar, använd sedan kommandot file för att bestämma filinnehållstypen. Men det skulle inte vara en bra idé att köra file efter ett rör, eftersom det skulle komplicera uppgiften att visa filens namn. Här är vad jag föreslår:

find . -type f -size 1033c ! -executable -exec sh -c "file -b $0 | grep -q text" {} \; -print 

Så här fungerar file -delen:

  • -exec predikat utför sh -c "file -b $0 | grep -q text" FILENAME för varje FILENAME som uppfyller alla tidigare villkor (typ, storlek, ej körbar).
  • För var och en av dessa filer , ett skal (sh) kör detta korta skript : file -b $0 | grep -q text, ersätter $0 med filnamnet.
  • file bestämmer innehållstypen för varje fil och matar ut denna information. Alternativet -b förhindrar utskrift av Namn på varje testad fil.
  • grep filter produktionen kommer från

program, söker efter rader som innehåller ”text” . (Se själv hur en typisk utgång frånfileser ut.)

  • Men grep mata ut den filtrerade texten, för den har -q (tyst) alternativet ges . Vad den gör är att bara ändra utgångsstatus till antingen 0 (vilket representerar ”sant” – den filtrerade texten hittades) eller 1 (vilket betyder ”fel ”- texten ” text ” visas inte i utdata från file).
  • Den sanna / falska utgångsstatusen kommer från grep skickas vidare av sh till find och fungerar som slutresultatet av helheten ”-exec sh -c "file $0 | grep -q text" {} \;” test.
  • Om ovanstående test returnerade true , -print kommandot körs (dvs. namnet på den testade filen skrivs ut).
  • Svar

    bandit4@bandit:~$ ls inhere bandit4@bandit:~$ file inhere/* inhere/-file00: data inhere/-file01: data inhere/-file02: data inhere/-file03: data inhere/-file04: data inhere/-file05: data inhere/-file06: data inhere/-file07: ASCII text inhere/-file08: data inhere/-file09: data bandit4@bandit:~$ pwd /home/bandit4 bandit4@bandit:~$ cat /home/bandit4/inhere/-file07 koReBOKuIDDepwhWk7jZC0RTdopnAYKh bandit4@bandit:~$ 

    Kommentarer

    • Använd bara filen inhere / * och cat / home / bandit4 / inhere / -file07

    Svar

    find -type f ! -executable -size 1033c 

    ger dig filen från övningen

    Svara

    find . -type f -size 1033c ! -executable | xargs file | grep text 

    Fläkt av en linje

    Svar

    Jag tror att det längre beskrivningen av lösenordet för denna banditnivå som nämns av de flesta ovan med hjälp av find och grep är det mest beskrivande kommandot.

    find . -type f -size 1033c ! -executable -exec file {} + | grep ASCII

    Men efter att ha använt kommandot ”file” mer insåg jag att det är ganska lätt att hitta mänskliga läsbara filer (aka ASCII på den här nivån) på detta sätt genom att kontrollera en hel katalogtyp.Inhere-katalogen innehåller filer med namnet ”-filexx” eller kolla snabbt hela inhere-katalogen med file ./*

    Här var mitt tillvägagångssätt.

    bandit4@bandit:~/inhere$ file ./* ./-file00: data ./-file01: data ./-file02: data ./-file03: data ./-file04: data ./-file05: data ./-file06: data ./-file07: ASCII text ./-file08: data ./-file09: data bandit4@bandit:~/inhere$ cat ./-file07 koReBOKuIDDepwhWk7jZC0RTdopnAYKh 

    Lämna ett svar

    Din e-postadress kommer inte publiceras. Obligatoriska fält är märkta *