שימוש בפסיקות (Interrupts) באסמבלי 8086¶
כאשר אנחנו כותבים קוד אסמבלי למעבד 8086, לעיתים קרובות נרצה לבצע פעולות מתקדמות: הדפסת טקסט למסך, קריאה מהמקלדת, גישה לקבצים ולכוננים, שינוי צבעים במסך, ועוד.
בהרצאה הבאה נציג כיצד אנחנו יכולים לכתוב קוד אסמבלי שיודע לדבר עם התקני הקלט והפלט כדי לבצע את הפעולות הללו בעצמכם.
בדרך כלל לא נהוג לכתוב קוד שיודע לבצע את הפעולות בעצמנו, במקום שנצטרך לממש את כל הדברים האלו בעצמנו – אנחנו יכולים לקרוא לשירותים שהמערכת מספקת, דרך מנגנון שנקרא פסיקות – Interrupts.
מהי פסיקה (Interrupt)?¶
פסיקה היא מנגנון שבו אנחנו מפסיקים את זרימת התוכנית, וקופצים לבצע קוד מיוחד שמוגדר מראש. (בדרך כלל מטרתו היא לדבר עם המקלדת, המסך וכו)
ישנן המון סוגים של פסיקות שאנחנו יכולים לקרוא להן, ובדרך כלל יש שני מערכות שאחראיות להוסיף פסיקות.
1. מערכת הBIOS- מערכת הBIOS היא קוד שרץ לפני שכל קוד במערכת רץ, חלק מהאחריות של הBIOS היא להגדיר פסיקות בסיסיות שימושיות- כמו הדפסת פיקסלים על המסך, קריאה של מידע מהמקלדת וכו.
2. לאחר שהBIOS סיים לרוץ, לרוב זה השלב שבו תרוץ מערכת ההפעלה. בדרך כלל גם מערכת ההפעלה מוסיפה פסיקות שונות לשימוש תוכנות שרצות במערכת ההפעלה
למעשה נוצר מצב שכשאנחנו כותבים תוכנות שרצות בms-dos קיימות לנו המון פסיקות שימושיות שהוגדרו על ידי הBIOS ומערכת ההפעלה שבאמצעותן נוכל לכתוב תוכנות שימושיות בקלות יותר.
פקודת INT¶
הפקודה:
תגרום למעבד לקפוץ ולבצע את הפונקציה המתאימה למספר הפסיקה. לדוגמה:
איך יודעים מה הפעולה שיבצעו?
דרך ערכים שאנחנו שמים ברגיסטר AH, ולפעמים גם ב־AL, BX, DX וכו'.
פסיקות חשובות ב־8086¶
פסיקת DOS – INT 21h¶
משמשת לביצוע שירותי מערכת תחת MS-DOS: הדפסת טקסט, קריאת קלט, פתיחת קבצים, גישה לדיסק וכו'.
| AH | פעולה |
|---|---|
| 01h | קריאת תו מהמקלדת |
| 02h | הדפסת תו (ב־DL) |
| 09h | הדפסת מחרוזת שמסתיימת ב־$ |
| 0Ah | קריאת מחרוזת מהמקלדת |
| 4Ch | יציאה מהתוכנית |
פסיקת BIOS – INT 10h¶
משמשת לפעולות הקשורות למסך ותצוגה: הדפסת תווים, שינוי מצב וידאו, שינוי צבעים ועוד.
בהמשך נדבר יותר על איך לעשות גרפיקה עם פסיקות של הBIOS
דוגמאות קוד: הדפסה וקלט¶
הדפסת תו בודד (INT 21h, AH=02h)¶
הדפסת מחרוזת (INT 21h, AH=09h)¶
שימו לב: המחרוזת חייבת להסתיים בסימן $ כדי שהפסיקה תדע מתי להפסיק להדפיס!
קריאת תו מהמקלדת (INT 21h, AH=01h)¶
קריאת מחרוזת מהמקלדת (INT 21h, AH=0Ah)¶
mov ah, 0Ah
mov dx, offset buffer
int 21h
...
buffer db 20 ; הגבלת אורך (עד 19 תווים)
db 0 ; מספר התווים שהוזנו בפועל (יוכנס ע"י DOS)
db 20 dup(0) ; מקום למחרוזת
לאחר הקריאה:
-
buffer+1יכיל את אורך המחרוזת -
buffer+2והלאה יכילו את התווים שהוקלדו
הדפסת תווים עם פסיקת BIOS (INT 10h, AH=0Eh)¶
mov ah, 0Eh
mov al, 'A'
mov bh, 0 ; עמוד (page) 0
mov bl, 7 ; צבע (foreground)
int 10h ; ידפיס A למסך עם גלילה
הפסיקה הזו כותבת למסך תווים גולמיים, ומתקדמת שורה אוטומטית.
יציאה מהתוכנית (INT 21h, AH=4Ch)¶
זהו הסיום התקני של תוכנית DOS. ללא זה, התוכנית עלולה "לרוץ" אל זיכרון לא תקף ולקרוס.
מה זה BIOS?¶
הBIOS = Basic Input Output System
זהו קוד שנמצא בתוך שבב ROM על לוח האם של המחשב, ופועל מיד עם הדלקת המחשב.
המטרה של ה-BIOS היא לספק קוד בסיסי ביותר להפעלת רכיבי המחשב, כולל:
-
טעינת מערכת ההפעלה
-
קריאה וכתיבה לזיכרון
-
גישה למסך, מקלדת, דיסק, יציאות וכו'
ה-BIOS מספק שירותים חשובים בתור פסיקות, כמו:
-
הדפסת תו למסך (
INT 10h) -
קריאה מהמקלדת (
INT 16h) -
גישה לדיסק (
INT 13h) -
מדידת זמן (
INT 1Ah) -
ועוד
איך פועלות פסיקות?¶
כאשר אנחנו כותבים למשל:
המעבד מבצע את הצעדים הבאים:
-
מחשב את הכתובת בזיכרון שבה מאוחסן ה־Vector של הפסיקה (עוד רגע נסביר מה זה).
-
קורא מ־Vector זה את כתובת הקוד (Segment:Offset) שממומשת ע"י BIOS.
-
קופץ לביצוע הקוד הזה – כאילו זו קריאה לפונקציה.
טבלת וקטורי הפסיקה – Interrupt Vector Table¶
בזיכרון שמתחיל מהכתובת 0000:0000 (כתובת לינארית 0x00000)
יש טבלה בגודל 1024 בתים (0x400)
שבה יש 256 רשומות של פסיקות, כל אחת בגודל 4 בתים:
-
2 בתים – offset
-
2 בתים – segment
כלומר:
-
INT 00h → וקטור נמצא בכתובת
0000:0000 -
INT 01h →
0000:0004 -
INT 10h →
0000:0040 -
INT 21h →
0000:0084
וכך הלאה.
לדוגמה, עבור INT 10h, המעבד יקרא את 4 הבתים החל מהכתובת 0x0040:
-
נניח שהערכים הם:
00 F0 00 C0 -
אז ה־offset =
F000h, segment =C000h -
כלומר, כתובת הביצוע היא
C000:F000
איפה נמצא ה־BIOS בזיכרון?¶
לרוב, ה־BIOS ממופה לזיכרון הגבוה ביותר של המערכת –
החל מהכתובת F000:0000 (כתובת פיזית 0xF0000), בגודל 64KB.
שם נמצא הקוד עצמו שה־interrupt vectors מפנים אליו.
דוגמה – איך INT 10h באמת עובד?¶
המעבד קורא את ה־vector מהכתובת 0000:0040, למשל:
כלומר – הקוד שאחראי להדפסת תווים במסך נמצא בתוך ה־ROM של ה־BIOS.
האם אפשר לשנות פסיקות?¶
כן – ניתן לשנות פסיקות בצורה חוקית ומבוקרת ע"י טעינת כתובת אחרת ל־IVT.
כלומר – אנחנו יכולים לשים קוד משלנו בזיכרון, ואז לשנות את ה־vector שיפנה לקוד שלנו.
דוגמה – החלפת INT 60h לקוד משלך¶
mov ax, seg myhandler
mov ds, ax
mov word ptr [0x0060*4], offset myhandler ; offset
mov word ptr [0x0060*4+2], ax ; segment
כעת כל קריאה ל־INT 60h תקפוץ ל־myhandler שלך.
דוגמה לפונקציה משלך¶
פקודת IRET חשובה מאוד – היא לא RET רגיל, אלא מחזירה גם את ערכי ה־flags.
שימושים נפוצים לשינוי פסיקות¶
-
קריאה לפסיקה מותאמת אישית: כמו INT 60h-6Fh (לא בשימוש ע"י BIOS)
-
ביצוע "Hook" לפסיקות קיימות: לדוגמה, פסיקות מקלדת, טיימר, או הדפסה, כדי להוסיף קוד משלך או שינוי של הפסיקות הקיימות.
-
בכתיבת מערכת הפעלה, נהוג ליצור פסיקות- כמו בms-dos שיש לנו המון קריאות מערכת שאנחנו יכולים לעשות עם int 21.
פסיקות לא מתכוננות¶
פסיקה היא פעולה שעוצרת את כל מה שהמעבד עושה, "מפסיקה" את מה שהמעבד עושה, כדי לבצע פעולה מגודרת מראש בטבלת הivt.
עד כו למדנו על פסיקות שאנחנו קוראים להם בעצמנו עם הפקודה int.
אבל פסיקות יכולות לקרות גם אם לא קראנו להם בכלל, פסיקות יכולות לקרות גם אם
המשתמש לחץ על מקש.
הגיע מידע מהכונן הקשיח. (הhard disk, האחסון)
בעתיד נלמד על פסיקות שעלולות לקרות למעבד, בנתיים- זכרו שיש המון סוגי פסיקות- ופסיקות יכולות לקרות גם אם לא תכננו.