AppCompat ב-Windows: compatibility mode, shims ו-Compatibility Administrator
· עודכן בתאריך: · Go Komura · Windows, compatibility mode, Shims, AppCompat, Compatibility Administrator, legacy apps, פיתוח Windows, מערכות קיימות
היסטוריית עדכונים (גרסה ראשונה, פורסמה בתאריך 20 Aug 2026)
- פרסום ראשון
לצטט את המאמר הזה(DOI: 10.5281/zenodo.22176300)
מאמר זה מאוחסן בארכיון Zenodo. להלן גם ה-DOI שתמיד מפנה לגרסה האחרונה וגם ה-DOI המקובע לגרסה שאתם קוראים.
Go Komura (2026). AppCompat ב-Windows: compatibility mode, shims ו-Compatibility Administrator. KomuraSoft LLC. https://doi.org/10.5281/zenodo.22176300 https://comcomponent.com/he/blog/windows-appcompat-shims-compatibility-mode/
- DOI (הגרסה האחרונה)
- 10.5281/zenodo.22176300
- DOI (הגרסה הזו)
- 10.5281/zenodo.22176301
קיבלנו לא פעם פנייה כזו: «אפליקציה עסקית בת עשר שנים, בלי source, לא עולה על Windows 11 חדש. סימנתי Windows XP בלשונית Compatibility במאפיינים — והיא פשוט רצה. מה זה בעצם עושה? מותר להמשיך להסתמך על זה?»
כשתיבת סימון אחת מחזירה משהו לחיים, זה דווקא מדאיג. Compatibility mode נראה כמו קסם, אבל מתחתיו רצות פיסות קוד קטנות שנקראות shims: הן יושבות בין האפליקציה ל-Windows API ומחזירות תשובה ישנה במקום התשובה האמיתית. Windows עצמו משתמש ב-workaround הזה בהיקף גדול כדי להשאיר אפליקציות מדורות קודמים באוויר, וחושף חלק ממנו למשתמשים ולמנהלים.
בלי להבין את המנגנון מקבלים תחזוקה שברירית: «אסור לגעת, כי לא ברור למה זה עובד». אחרי שמבינים אותו אפשר להחליט עם נימוקים עד כמה אפשר להסתמך, מה ישבור את זה, ומתי צריך לשכתב.
flowchart TB
accTitle: הבנת המנגנון משנה את איכות ההמשך
accDescr: שימוש ב-compatibility mode בלי להבין את המנגנון מוביל להמשך שביר שאסור לגעת בו; הבנת המנגנון מאפשרת החלטה מנומקת עד כמה אפשר להסתמך, מה ישבור, ומתי לשכתב
unknown["שימוש בלי להבין את המנגנון"] --> fear["המשך שביר שאסור לגעת בו"]
known["שימוש אחרי שמבינים את המנגנון"] --> judge["החלטות עם נימוקים"]
judge -.-> j1["עד כמה אפשר להסתמך"]
judge -.-> j2["מה ישבור את זה"]
judge -.-> j3["מתי צריך לשכתב"]
איור 1: גם כשממשיכים להריץ את אותה אפליקציה, האיכות שונה בין חרדה מאי-ידיעה לבין החלטה שמבוססת על הבנת המנגנון.
המאמר מיועד לאנשי IT בעסקים קטנים ובינוניים ולמפתחי Windows שמטפלים באפליקציות עסקיות ישנות. הוא מסדר, לפי מקורות ראשוניים של Microsoft Learn, מה shim עושה מתחת ל-compatibility mode, מה ה-shims הנפוצים באמת יכולים, איך מחילים אותם בארגון עם Compatibility Administrator, איפה shim לא מציל, ואיך מחליטים אם להמשיך להריץ או לעבור.
1. קודם כל, המסקנות
- Compatibility mode הוא צרור shims (שכבת תאימות). הגדרות מלשונית Compatibility נכתבות אל
HKCU\Software\Microsoft\Windows NT\CurrentVersion\AppCompatFlags\Layers, ובהפעלה מוחל צרור shims על ה-process.12 - Shim הוא user-mode API hook שכותב מחדש את Import Address Table (IAT). הוא מיירט את הנתיב שבו האפליקציה קוראת ל-Windows API ומחזיר את אותן תשובות ש-Windows ישן היה מחזיר. הוא לא משנה את ה-OS עצמו.3
- מה ש-shim יכול לעשות הוא אותו טווח שתיקון בקוד האפליקציה יכול לעשות. הוא לא עוקף מנגנוני אבטחה, ולא מתקן בעיות ב-kernel mode (device drivers).3
- Microsoft שולחת הרבה shims מוכנים — spoof של גרסת OS, מיפוי מחדש של נתיבי קבצים, זיוף Registry, זיוף בדיקת Administrator ועוד. אפשר להחיל אותם על EXE בודד מ-Compatibility Administrator.4
- Windows עצמו מחיל shims כברירת מחדל. בכל הפעלה יש matching מול מסד התאימות הסטנדרטי של ה-OS (
.sdb), ו-PCA (Program Compatibility Assistant) יכול לזהות בעיה ולהחיל הגדרת תאימות אוטומטית.15 - «לענות כאילו זה Windows ישן יותר» הוא כבר ברירת המחדל. מ-Windows 8.1 ואילך
GetVersionExלא מחזיר גרסת OS שהאפליקציה לא הכריזה ב-manifest. Compatibility mode הוא הרחבה של אותו מנגנון.67 - Shims לא עובדים על אפליקציות 16-bit, תלות ב-kernel driver, או גישה ישירה לחומרה. במיוחד, אפליקציות 16-bit לא יכולות לרוץ בכלל על Windows 64-bit.8
- לאפליקציות ש«דורשות Administrator אבל לא צריכות אותו באמת», RunAsInvoker הוא הצעד הסטנדרטי.
__COMPAT_LAYER=RunAsInvokerמדכא את בקשת ה-elevation ומשאיר את האפליקציה בהרשאות רגילות.9 - ריצה תחת shim אומרת שאפשר להמשיך בינתיים, אבל הכיוון הנכון הוא «לרוץ בלי shim». אם מחליטים להשאיר אותה באוויר, מתעדים אילו shims גורמים לה לרוץ ומנהלים את זה כחומר להחלטת שכתוב.
2. שכבות התאימות לאחור שכבר יש ב-Windows
לפני shims, כדאי לראות את שכבות התאימות ש-Windows כבר מחזיק לאפליקציות ישנות. גם כשאומרים «זה התחיל לעבוד ב-compatibility mode», מה שמציל את האפליקציה בפועל הוא אחת מהשכבות האלה, או שילוב שלהן.
| שכבה | מה היא עושה | יעד טיפוסי |
|---|---|---|
| Shims (compatibility mode) | מיירטים קריאות API ומחזירים את אותן תגובות ש-Windows ישן היה נותן | אפליקציות שנכתבו מול OS ישן יותר |
| UAC virtualization (קבצים / Registry) | מפנים כתיבות ל-HKLM\Software או Program Files בלי הרשאה אל VirtualStore לפי משתמש |
אפליקציות 32-bit שנכתבו בהנחת הרשאות Administrator |
| WOW64 | מריץ אפליקציות 32-bit כמות שהן על Windows 64-bit (מספק תצוגות 32-bit של Registry ומערכת הקבצים) | אפליקציות 32-bit בכלל |
| DPI virtualization | גורם לאפליקציה שאינה DPI-aware לצייר ב-96 DPI ומציג אותה במתיחת bitmap | אפליקציות ישנות על צגים עם DPI גבוה |
UAC virtualization הוא מעבר זמני לתהליכים אינטראקטיביים 32-bit בלי manifest, ו-Microsoft עצמה כותבת שזו «טכנולוגיה זמנית שאנחנו מתכוונים להסיר מגרסת Windows עתידית».10 הנזק האמיתי מ-redirect ל-Wow6432Node ומ-VirtualStore, ואיך מתמודדים איתו, מכוסה בפירוט ב«מלכודות 32-bit/64-bit Registry redirection ו-virtualization». המאמר הזה משאיר shims במרכז ומזכיר את השכבות האחרות רק כשצריך.
flowchart TB
accTitle: איפה יושבת UAC virtualization
accDescr: UAC virtualization היא מעבר זמני לתהליכים אינטראקטיביים 32-bit בלי manifest; היא מפנה כתיבות אל VirtualStore לפי משתמש אבל Microsoft עצמה אומרת שזו טכנולוגיה זמנית המיועדת להסרה מ-Windows עתידי
proc["תהליך אינטראקטיבי 32-bit בלי manifest"] --> uacv["UAC virtualization נכנסת לפעולה"]
uacv --> vs["הפניה אל VirtualStore לפי משתמש"]
uacv -.-> tmp["טכנולוגיה זמנית שמיועדת להסרה בהמשך"]
איור 2: UAC virtualization היא מעבר זמני לתהליכי 32-bit בלי manifest, ואי אפשר להסתמך עליה לצמיתות.
הערה על DPI virtualization: אפליקציה שלא הכריזה DPI awareness מטופלת כאילו היא מציירת ב-96 DPI (100%), ו-Windows מוחח את ה-bitmap לתצוגה. לכן אפליקציות ישנות נראות מטושטשות על צג עם DPI גבוה, ו«Override high DPI scaling behavior» בלשונית Compatibility הוא המתג שמשנה את התנהגות ה-virtualization הזו.11
flowchart TB
accTitle: איך פועלת DPI virtualization
accDescr: אפליקציה שלא הכריזה DPI awareness מטופלת כמציירת ב-96 DPI; Windows מוחח את ה-bitmap כך שהיא נראית מטושטשת, ו-override של DPI גבוה בלשונית Compatibility מחליף את התנהגות ה-virtualization
app["אפליקציה שאינה מכריזה DPI awareness"] --> treat["מטופלת כמציירת ב-96 DPI"]
treat --> stretch["ה-bitmap נמתח לתצוגה"]
stretch --> blur["נראית מטושטשת על צג DPI גבוה"]
tab["Override של DPI גבוה"] -.->|מחליף את התנהגות ה-virtualization| treat
איור 3: אפליקציה שאינה DPI-aware מטופלת כ-96 DPI ונמתחת; ה-override בלשונית Compatibility הוא המתג של ה-virtualization הזו.
3. מה shim באמת עושה — יירוט API דרך כתיבה מחדש של ה-IAT
3.1. השכבה שיושבת בין האפליקציה ל-OS
קובץ הפעלה של Windows (פורמט PE) קורא ל-API ב-DLL חיצוני דרך Import Address Table (IAT). כשהאפליקציה קוראת ל-GetVersionEx היא רק קופצת לכתובת שכתובה ב-IAT. מנגנון ה-shim מנצל את זה. בזמן load הוא כותב מחדש את רשומת ה-IAT של ה-API היעד לכתובת קוד ה-shim, ומכניס את עצמו בין האפליקציה ל-Windows. API שמתקבלים דינמית דרך GetProcAddress מטופלים ב-hook על GetProcAddress עצמו.3
אחרי היירוט, shim עשוי להחזיר מספר גרסה ישן ל«מה גרסת ה-OS הנוכחית?», או למפות מחדש גישת קובץ לנתיב שאי אפשר לכתוב אליו, ואז לקרוא ל-API האמיתי אם צריך. מהאפליקציה זה נראה כאילו «רצה על Windows ישן»; מה-OS זה נראה כאילו «אפליקציה מנומסת רצה» — ה-shim מתרגם בין השניים.
flowchart TB
accTitle: הנתיב שבו shim מיירט קריאת API
accDescr: קריאת API של האפליקציה עוברת דרך ה-IAT; כתיבה מחדש של רשומת ה-IAT אל ה-shim ב-load מאפשרת יירוט, החזרת אותה תגובה ש-Windows ישן היה נותן, ואז קריאה ל-API האמיתי אם צריך
app["אפליקציה"] -->|קריאת API| iat["רשומת IAT"]
iat -->|נכתבת מחדש אל ה-shim ב-load| shim["Shim (שכבת יירוט)"]
shim -->|אם צריך| api["Windows API האמיתי"]
shim -.-> lie["מחזיר את אותה תגובה ש-Windows ישן היה נותן"]
gpa["קריאות דרך GetProcAddress"] -.->|מטופלות ב-hook| shim
איור 4: Shim מיירט בין האפליקציה ל-Windows API. מה שנכתב מחדש הוא ה-IAT בצד האפליקציה; ה-OS עצמו לא משתנה.
שלוש תכונות חשובות נובעות מהעיצוב הזה.3
- Shim רץ כקוד בצד האפליקציה. הוא לא חלק מה-OS, ולכן כפוף לאותן מגבלות אבטחה כמו האפליקציה. Shim לא יכול לעקוף את מנגנוני האבטחה של Windows, ואין צורך להרפות הגדרות אבטחה כדי להשתמש בו.
- מה ש-shim יכול לתקן, תיקון בקוד האפליקציה יכול גם לתקן. Shim הוא תחליף כשאין source או כשאי אפשר לתקן; הוא לא חזק יותר מתיקון קוד.
- User mode בלבד. בעיות תאימות ב-device drivers שרצים ב-kernel mode אי אפשר לתקן ב-shim.
3.2. מסד ה-shim (.sdb) ו-matching
טבלת ההתאמה «איזה shim להחיל על איזה EXE» היא shim database, קובץ בינארי עם סיומת .sdb. קובצי ההפעלה של האפליקציה היעד נרשמים במסד לפי תכונות כמו שם קובץ, גודל, checksum וגרסה (matching attributes), ומותאמים בהפעלת ה-process. התיקונים כוללים Appfix (shim) שמזריק API hook, ו-Apphelp שמציג הודעת «לאפליקציה הזו יש בעיית תאימות». צרור של כמה shims ודגלים הוא compatibility layer (compatibility mode).1
קל לפספס: ה-matching הזה רץ לא רק על אפליקציות עם compatibility mode מוגדר, אלא בכל הפעלת process. Windows שולח מסד סטנדרטי של ה-OS עם תיקונים לאלפי אפליקציות ידועות (הקבצים חיים תחת %WINDIR%\AppPatch), ובמחשב שלכם היום כמעט בוודאי אפליקציה ישנה כלשהי עולה עם shim מחובר בלי שאף אחד שם לב. תיקוני תאימות ש-Microsoft מספקת נשלחים כחלק מ-Windows ומתעדכנים דרך Windows Update.3
flowchart TB
accTitle: Matching מול מסד ה-shim בהפעלת process
accDescr: כל הפעלת process מותאמת מול מסד ה-shim; אם רישום תואם את matching attributes, Appfix מזריק shim או Apphelp מציג הודעה, אחרת ה-process עולה כמות שהוא
start["הפעלת process"] --> db["Matching מול .sdb"]
db -.-> attr["שם קובץ, גודל וכו"]
db --> hit{"יש רישום?"}
hit -->|כן| appfix["Appfix: הזרקת shim"]
hit -->|כן| apphelp["Apphelp: הודעה"]
hit -->|לא| plain["הפעלה רגילה"]
layer["Compatibility layer"] -.->|צרור shims ודגלים| appfix
איור 5: ה-matching רץ בכל הפעלת process, לא רק על אפליקציות שיש להן compatibility mode מוגדר.
3.3. PCA — המנגנון שמחיל shims אוטומטית
נתיב נוסף שבו shim יכול להיות מוחל בלי שמנהל התכוון לכך הוא PCA (Program Compatibility Assistant). PCA עוקב אחרי הרצת אפליקציה, וכשהוא מזהה סימנים לבעיית תאימות ידועה הוא מציע למשתמש להחיל תיקון או, במקרים מסוימים, מחיל הגדרת תאימות אוטומטית. למשל אפליקציה שקורסת בקריאה לקוד בתוך DLL שכבר שוחרר מקבלת PINDLL, ואפליקציה שנכשלת בכתיבה לקובץ Windows מוגן מקבלת WRPMITIGATION.5
flowchart TB
accTitle: איך PCA מחיל הגדרת תאימות אוטומטית
accDescr: PCA עוקב אחרי הרצת אפליקציה וכשהוא מזהה סימנים לבעיית תאימות ידועה מציע למשתמש להחיל תיקון או במקרים מסוימים מחיל הגדרת תאימות אוטומטית
run["הרצת אפליקציה"] --> pca["PCA עוקב"]
pca --> sign{"סימנים לבעיה ידועה?"}
sign -->|כן| resp{"איזה מקרה?"}
resp -->|מטופל בהצעה| suggest["הצע להחיל תיקון"]
resp -->|מקרים מסוימים| auto["החל הגדרת תאימות אוטומטית"]
sign -->|לא| none["הרץ כרגיל"]
auto -.-> ex["דוגמה: PINDLL או WRPMITIGATION"]
איור 6: PCA עוקב אחרי הרצת אפליקציה, וכשהוא מזהה סימנים לבעיה ידועה מציע תיקון או מחיל אותו אוטומטית.
«מעולם לא הגדרתי כלום, אבל בשלב כלשהו תיבת compatibility mode הייתה מסומנת» — במקרים רבים זה PCA. זו לא תקלה ולא לחיצה שגויה; זה Windows מתנהג כפי שתוכנן.
4. מה ה-shims הנפוצים באמת יכולים
מתוך ה-shims המוכנים ש-Microsoft מפרסמת, הנה מבחר שעולה לעיתים קרובות כשממשיכים להריץ אפליקציה עסקית ישנה.4
| Shim | מה הוא יכול (בקצרה) |
|---|---|
| WinXPSP3VersionLie ומשפחת VersionLie | להחזיר גרסה ישנה יותר שצוינה לשאילתות גרסת OS (spoof של גרסה) |
| CorrectFilePaths | למפות מחדש גישה לנתיב קובץ שאי אפשר לכתוב אליו או שאינו קיים |
| VirtualRegistry | להפנות או לזייף קריאות וכתיבות Registry (כולל spoof של גרסה ומפתחות שאינם קיימים) |
| ForceAdminAccess | להחזיר זמנית True לבדיקת «האם אתה חבר בקבוצת Administrators?» |
| RunAsAdmin / RunAsHighest / RunAsInvoker | לתת מבחוץ execution level שקול ל-requireAdministrator / highestAvailable / asInvoker ב-manifest |
| WRPMitigation | לזייף הצלחה לכתיבות לקובצי OS מוגנים ולמפתחות Registry כדי שהאפליקציה תוכל להמשיך |
| EmulateGetDiskFreeSpace | לדווח על שטח דיסק פנוי כמקסימום 2GB (לאפליקציות שגולשות על דיסקים גדולים) |
| GlobalMemoryStatusLie | לזייף את ערכי מצב הזיכרון המדווחים (לאפליקציות שנכשלות בבדיקת זיכרון בהפעלה) |
| LoadLibraryRedirect | לטעון את ה-DLL הנוכחי של Windows במקום DLL מערכת ישן שהאפליקציה מצרפת |
מסתכלים על הרשימה ורואים שרוב ה-shims הם «תשובה שהאפליקציה הישנה מצפה לה, במקום המציאות». הדיסק לכל היותר 2GB, ה-OS הוא XP, אתה Administrator — הם יוצרים מחדש, בתוך אותו process בלבד, את תמונת העולם של התקופה שבה נולדה האפליקציה.
Spoof של גרסה הפך להתנהגות ברירת מחדל רשמית
Spoof של גרסה אינו hack מיוחד. מ-Windows 8.1 ואילך הערך ש-GetVersionEx מחזיר תלוי ב-manifest של האפליקציה. אפליקציה בלי הכרזת <supportedOS> במדור <compatibility> של ה-manifest מקבלת תמיד שווה-ערך ל-Windows 8 (6.2), יהא אשר יהא ה-OS בפועל. כשיש הכרזה מוחזר הערך עד ה-OS הגבוה ביותר שהוכרז (למשל אם הכרזתם עד ה-GUID של Windows 8.1 תקבלו 6.3 גם ב-Windows 11).67
כלומר «גרסת Windows שהאפליקציה רואה» נקבעת בשלבים האלה.
- מוחזר הערך עד ה-OS שהוכרז ב-manifest (6.2 אם אין הכרזה)
- אם מוחל compatibility mode (shim ממשפחת VersionLie), מוחזרת גרסת ה-OS שנבחרה6
flowchart TB
accTitle: איך נקבעת גרסת ה-OS שהאפליקציה רואה
accDescr: הערך ש-GetVersionEx מחזיר נקבע לפי הכרזת supportedOS ב-manifest; בלי הכרזה מוחזר 6.2 שווה-ערך ל-Windows 8, עם הכרזה מוחזר הערך עד ה-OS הגבוה ביותר, ואם מוחל shim ממשפחת VersionLie הוא נדרס בגרסת ה-OS שנבחרה
q["שאילתת GetVersionEx"] --> m{"יש הכרזת supportedOS?"}
m -->|לא| v62["מוחזר שווה-ערך Windows 8 (6.2)"]
m -->|כן| decl["ערך עד ה-OS הגבוה שהוכרז"]
v62 --> lie{"הוחל shim ממשפחת VersionLie?"}
decl --> lie
lie -->|כן| fake["ערך ה-OS שנבחר ב-compatibility mode"]
lie -->|לא| asis["הערך מוחזר כמות שהוא"]
איור 7: גרסת Windows שהאפליקציה רואה נקבעת בשלבים לפי ה-manifest ולפי shims.
אם אפליקציה פנימית «מתפצלת לפי גרסת OS, ובאופן מבלבל נשפטת כ-8 אף שזה Windows 11», חשדו קודם בהכרזת supportedOS ב-manifest. ולהפך: אפליקציה ישנה שמסרבת לעלות על סמך בדיקת גרסה יכולה, בהסתברות גבוהה, לעבור עם shim ממשפחת VersionLie. במקרים רבים היא רק מסתכלת על מספר הגרסה, וההתנהגות בפועל תקינה על OS חדש יותר.
flowchart TB
accTitle: שני תסמינים שנגרמים מגרסה ואיך לטפל
accDescr: אם אפליקציה פנימית נשפטת כ-8 אף שזה Windows 11 חשדו בהכרזת supportedOS ב-manifest; אפליקציה ישנה שמסרבת לעלות בבדיקת גרסה יכולה לעבור בהסתברות גבוהה עם VersionLie
sym1["נשפטת כ-8 אף שזה Windows 11"] --> fix1["חשדו בהכרזת supportedOS"]
sym2["סירוב הפעלה בבדיקת גרסה"] --> fix2["נסו לעבור עם VersionLie"]
fix2 -.-> why["ההתנהגות בפועל לעיתים קרובות תקינה על OS חדש"]
איור 8: כשהשיפוט מיושן חשדו ב-manifest; כשההפעלה מסורבת חשדו ב-VersionLie.
5. מה תיבת הסימון של compatibility mode באמת עושה
הגדרות ממאפיינים → לשונית Compatibility נשמרות במפתח Registry AppCompatFlags\Layers. גם הגדרות תאימות אפליקציות DXGI וכדומה משתמשות באותו מפתח כמקום לציין compatibility layer.2 בואו נסתכל בפועל.
reg query "HKCU\Software\Microsoft\Windows NT\CurrentVersion\AppCompatFlags\Layers"
ל-EXE שעליו הגדרתם «Windows XP (Service Pack 3)», «Run this program as an administrator» ו-«Override high DPI scaling behavior» בלשונית Compatibility תראו ערך כמו הבא.
HKEY_CURRENT_USER\Software\Microsoft\Windows NT\CurrentVersion\AppCompatFlags\Layers
C:\LegacyApp\Gyomu.exe REG_SZ ~ WINXPSP3 RUNASADMIN HIGHDPIAWARE
התאמות נפוצות בין פריטי התיבה לערכים (אושרו ב-Windows 11; שמות פריטים וערכים יכולים להשתנות לפי גרסת OS).
| פריט לשונית Compatibility | ערך שנכתב (דוגמה) | מה זה באמת |
|---|---|---|
| Compatibility mode: Windows XP (Service Pack 3) | WINXPSP3 | Compatibility layer שמצררת spoof של גרסה וכמה shims אחרים |
| Reduced color mode (8-bit / 256 colors) | 256COLOR | הקלה למצב הצבע הישן |
| Run in 640 × 480 screen resolution | 640X480 | הרצה ברזולוציה נמוכה |
| Disable fullscreen optimizations | DISABLEDXMAXIMIZEDWINDOWEDMODE | השבת אופטימיזציות ציור במסך מלא |
| Override high DPI scaling behavior (Application) | HIGHDPIAWARE | עצור DPI virtualization (מתיחת bitmap)11 |
| Run this program as an administrator | RUNASADMIN | בקש elevation בהפעלה |
שלוש נקודות לשמור.
- «Run this program as an administrator» נכתב באותו מקום. Compatibility mode ודגל ה-elevation חיים יחד באותו מפתח Layers, ומשם נולדת הבלבול «הגדרתי compatibility mode ו-elevation הגיע / נעלם». הסתכלות ישירה בערך מפרידה בין השניים.
- מה שנכתב ב-HKCU הוא «הגדרת אותו משתמש». אם מגדירים מ-«Change settings for all users», זה נכתב למפתח בעל אותו שם בצד HKLM וחל על כל המשתמשים. כשמפיצים ב-image, היו מודעים לאיזה צד כותבים.
- התיבה היא רק הכניסה לשכבות המוכנות. הלשונית מאפשרת לבחור layers נפוצים בלבד; אי אפשר לבחור shims בודדים ולשלב אותם. זה מה ש-Compatibility Administrator בפרק הבא עושה.
flowchart TB
accTitle: הנתיב מהגדרת לשונית Compatibility עד לתוקף
accDescr: הגדרות לשונית Compatibility נשמרות כנתיב EXE וערך במפתח Layers של AppCompatFlags; בפעם הבאה שה-EXE עולה ה-loader קורא את הערך ומחיל את compatibility layer המתאימה על ה-process
tab["הגדרה בלשונית Compatibility"] --> reg["שמירת נתיב EXE והערך במפתח Layers"]
reg --> boot["הפעלת EXE הבאה"]
boot --> loader["ה-loader קורא את הערך"]
loader --> apply["החלת compatibility layer על ה-process"]
reg -.-> hkcu["HKCU לאותו משתמש בלבד"]
reg -.-> hklm["HKLM חל על כל המשתמשים"]
איור 9: התיבה במציאות היא כתיבה למפתח Layers, וההחלה קורה בהפעלה הבאה.
6. Compatibility Administrator בפועל — בניית .sdb מותאם והפצתו
6.1. איך משיגים אותו, והסתייגויות
Compatibility Administrator הוא כלי הכלול ב-Windows ADK (Windows Assessment and Deployment Kit).12 אחרי התקנה קיימות מהדורות 32-bit ו-64-bit, וחייבים להשתמש במהדורת 32-bit לאפליקציות 32-bit ובמהדורת 64-bit לאפליקציות 64-bit.13
יש הסתייגות חשובה נוספת. אם מפעילים את Compatibility Administrator elevated (כ-Administrator) ובודקים, UAC virtualization ו-redirect לא מתנהגים כפי שהיו מתנהגים למשתמש אמיתי, ואפשר לשפוט בטעות ש«זה תוקן». תמיד מאשרים את אפקט התיקון באותו חשבון ובהרשאות כמו המשתמש בפועל.4
flowchart TB
accTitle: שתי הסתייגויות בשימוש ב-Compatibility Administrator
accDescr: השתמשו במהדורת 32-bit לאפליקציות 32-bit ובמהדורת 64-bit לאפליקציות 64-bit ואשרו את אפקט התיקון באותו חשבון והרשאות כמו המשתמש בפועל לא במצב elevated
app32["אפליקציית 32-bit"] --> tool32["השתמשו במהדורת 32-bit"]
app64["אפליקציית 64-bit"] --> tool64["השתמשו במהדורת 64-bit"]
elev["בדיקה במצב elevated"] -.-> wrong["עלולים לשפוט תיקון בטעות"]
user["בדיקה בהרשאות המשתמש בפועל"] --> ok["אשרו את האפקט"]
איור 10: בחירת מהדורת 32-bit או 64-bit, ואישור באותן הרשאות כמו המשתמש בפועל, הן הסתייגויות הכניסה.
6.2. הליך בניית מסד תאימות מותאם
הקווים הכלליים כדלקמן.14
- בחלונית השמאלית של Compatibility Administrator צרו מסד חדש תחת «Custom Databases» ובחרו «Create New» → «Application Fix»
- הזינו את שם האפליקציה ושם הספק, וציינו את קובץ ה-EXE היעד
- בחרו את compatibility mode (ה-layer) להחלה — ניסיון צרור כמו «Windows XP compatibility» קודם הוא הנתיב הקצר
- אם צריך, הוסיפו compatibility fixes בודדים (shims) — אפשר לצמצם לסט מינימלי כמו VersionLie בלבד או CorrectFilePaths בלבד
- אשרו את תנאי ה-matching (גודל קובץ, checksum, גרסה וכן הלאה) ושמרו
תנאי ה-matching הם המפתח ל«החל זאת רק על ה-EXE הזה». תנאי היסוד כברירת מחדל מספיקים בדרך כלל, אבל כדאי להשאיר תנאי שיכול לזהות את גרסת האפליקציה. זה מונע את התאונה ש-workaround ישן ממשיך לחול על גרסה חדשה כשהספק שולח אחר כך מהדורה מתוקנת.1415
flowchart TB
accTitle: הליך בניית מסד תאימות מותאם
accDescr: צרו Application Fix במסד חדש, ציינו שם אפליקציה ו-EXE יעד, נסו קודם צרור compatibility mode ואז צמצמו ל-shims בודדים אם צריך, אשרו תנאי matching ושמרו
new["יצירת מסד חדש"] --> fix["בחירת Application Fix"]
fix --> info["ציון שם האפליקציה וה-EXE היעד"]
info --> layer["ניסיון צרור compatibility mode"]
layer --> single["אם צריך צמצום ל-shims בודדים"]
single --> match["אישור תנאי matching ושמירה"]
match -.-> ver["השארת תנאי שמזהה את הגרסה"]
איור 11: ל-Application Fix נסו קודם צרור compatibility mode, צמצמו לסט מינימלי, והגבילו את היעד בתנאי matching.
בדקו את ה-.sdb שיצרתם קודם במכונת בדיקה. ברגע שהוא עובד כמתוכנן מפיצים אותו לארגון.
6.3. הפצה עם sdbinst
הפקודה שמחילה .sdb מותאם על כל מחשב היא sdbinst.exe (דורשת הרשאות Administrator).15
:: Install (-q is silent with no confirmation)
sdbinst -q "C:\Deploy\MyCorpFixes.sdb"
:: Uninstall (by file)
sdbinst -q -u "C:\Deploy\MyCorpFixes.sdb"
:: Uninstall (by database GUID)
sdbinst -q -u -g {database GUID}
כאסטרטגיית פריסה ארגונית Microsoft ממליצה לגבש למסד מותאם אחד ברמת החברה (או המחלקה) ולנהל אותו מרכזית, במקום לשלוח .sdb נפרד עם ה-installer של כל אפליקציה. ככל שיש יותר תיקונים קל יותר לעדכן ולהפיץ מחדש מסד אחד מאשר להפיץ מסדי שורה אחת רבים. למסד מותאם יש GUID משלו, והתקנת גרסה חדשה עם אותו GUID מחליפה אוטומטית את הגרסה הישנה, כך שגם פעולות עדכון נשארות פשוטות. שימו את ההפצה עצמה על נתיב קיים שיכול לרוץ בהרשאות Administrator, כמו אריזה כ-MSI או startup script.15
flowchart TB
accTitle: הנתיב מיצירת .sdb מותאם עד הפצתו
accDescr: צרו מסד תאימות מותאם ב-Compatibility Administrator, בדקו במכונת בדיקה, החילו על כל מחשב עם sdbinst, ובעדכון התקינו גרסה חדשה עם אותו GUID כך שהישנה מוחלפת אוטומטית
make["יצירה ב-Compatibility Administrator"] --> test["בדיקה במכונת בדיקה"]
test --> deploy["החלה על כל מחשב עם sdbinst"]
deploy --> update["התקנת גרסה חדשה עם אותו GUID"]
update -.-> replace["הגרסה הישנה מוחלפת אוטומטית"]
deploy -.-> inv["רישום בתוכניות ותכונות"]
איור 12: .sdb מותאם מגולגל דרך יצירה, בדיקה והפצת sdbinst, ועדכונים מנוהלים לפי GUID.
מסד מותאם מותקן נרשם כפריט ב«תוכניות ותכונות (אפליקציות מותקנות)», כך שאפשר גם לאשר מלאי והסרה משם. אילו מחשבים נושאים איזה .sdb הוא מידע ששייך ל-inventory של ניהול הנכסים.
7. מקרים שבהם זה לא עובד, והגבולות
Shims אינם כדור כסף. לפי העיצוב הם לא עובדים במקרים הבאים.
- בעיות kernel mode. Shim רץ בתוך process ב-user mode, ולכן אי-תאימות של device driver אי אפשר לתקן. אם ה-driver של מכשיר מדידה ישן, USB dongle או מדפסת אינו תומך ב-Windows 11, שום דבר שתחיל בצד האפליקציה לא יפתור זאת. קוד שרץ ב-kernel, כמו חלקים מתוכנת antivirus, אותו דבר.3
- אפליקציות 16-bit. Windows 64-bit אינו תומך בהרצת אפליקציות 16-bit. ל-handles יש 32 סיביות תקפות ב-Windows 64-bit ואי אפשר לקטוע אותן כדי להעביר לאפליקציית 16-bit, ולכן ההפעלה נכשלת עם
ERROR_BAD_EXE_FORMAT.8 גם כשהאפליקציה עצמה היא 32-bit קיימות חבילות מאותה תקופה שה-stub של ה-installer הוא 16-bit, והן מופיעות כ«האפליקציה הייתה רצה, אבל אי אפשר להתקין אותה». - גישה ישירה לחומרה. אפליקציות תעשייתיות שמניחות שהן יכולות לגעת ב-I/O ports או בזיכרון פיזי ישירות אינן מורשות לעשות זאת מ-user mode ב-Windows מודרני מלכתחילה, וזה מעבר לטווח ש-shim יכול לזייף.
- עקיפת מנגנוני אבטחה. כי shim רץ תחת אותן מגבלות אבטחה כמו האפליקציה, הוא אינו יכול להפוך «משהו שאי אפשר לעשות מחוסר הרשאה» לאפשרי. ForceAdminAccess ו-WRPMitigation רק מזייפים הצלחה של בדיקה או כתיבה כדי שהאפליקציה תוכל להמשיך; הם אינם כותבים מחדש בפועל משאב מוגן.34
- אפליקציות שבודקות את שלמותן בעצמן. אפליקציות עם copy protection ישן או זיהוי חבלה יכולות לטפל ב-API hook עצמו כחריג ולהפסיק לעבוד.
flowchart TB
accTitle: מקרים שבהם shim אינו עובד
accDescr: Shim רץ בתוך process ב-user mode ולכן אינו עובד על בעיות kernel driver, אפליקציות 16-bit, גישה ישירה לחומרה או עקיפת מנגנוני אבטחה
shim["Shim (רץ ב-user mode)"] -->|אינו עובד| drv["Kernel driver"]
shim -->|אינו עובד| b16["אפליקציית 16-bit"]
shim -->|אינו עובד| hw["גישה ישירה לחומרה"]
shim -->|אינו עובד| sec["עקיפת מנגנוני אבטחה"]
b16 -.-> fmt["ב-64-bit ההפעלה עצמה נכשלת"]
sec -.-> fake["רק מזייף הצלחה כדי שהאפליקציה תמשיך"]
איור 13: Shim הוא user mode בלבד ואינו מגיע ל-kernel, לאפליקציות 16-bit, לגישה ישירה לחומרה או לעקיפת אבטחה.
והגבול המהותי המשותף לכל shim הוא שהוא workaround זמני. Shim הוא תשובה מזויפת המותאמת לשימוש מסוים ב-API מסוים, ואם המימוש בצד ה-OS משתנה ההנחה קורסת. Shims ש-Microsoft מספקת מתוחזקים כחלק מ-Windows דרך Windows Update,3 אבל הטיפול ב-workarounds שהחלתם במסד מותאם הוא עבודת הארגון שלכם. תקצבו, כעלות המשך ההרצה, פעולה שמוודאת את «רשימת האפליקציות שמוחזקות באוויר על ידי shims» בכל feature update.
flowchart TB
accTitle: Shims כ-workaround זמני ומי אחראי לתחזוקתם
accDescr: Shim הוא תשובה מזויפת המותאמת לשימוש API מסוים וההנחה קורסת אם המימוש בצד ה-OS משתנה; shims של Microsoft מתוחזקים דרך Windows Update אבל הטיפול ב-workarounds של מסד מותאם הוא עבודת הארגון ואימות בכל feature update הוא עלות ההמשך
shim["Shim = workaround זמני"] --> break["שינוי ב-OS שובר אותו"]
ms["Shims של Microsoft"] --> wu["דרך Windows Update"]
own["Workarounds של מסד מותאם"] --> self["הארגון מטפל בהם"]
self --> cost["אימות בכל feature update הוא עלות ההמשך"]
איור 14: האחריות לתחזוקת ה-workaround של ה-shim מחולקת בין הסט ש-Microsoft מספקת לסט המותאם של הארגון שלכם.
8. הערך המעשי של RunAsInvoker — לדכא רק את בקשת ה-elevation
בין ה-shims, זה שעולה ביותר בעבודת IT יומיומית הוא RunAsInvoker.
אפליקציות עסקיות ישנות מסוימות מכריזות requireAdministrator ב-manifest, או מזוהות בטעות כ-installer משם ה-EXE או מתוכנו, ומבקשות UAC elevation בכל הפעלה. רבות מהן, עם זאת, רק מבקשות Administrator מאינרציה של עידן XP ואינן משתמשות בהרשאות Administrator באמת. החלת shim של RunAsInvoker דורסת גם זיהוי installer וגם manifest, והאפליקציה עולה עם ה-token שעבר בירושה מתהליך האב (= הרשאות משתמש רגיל).9
flowchart TB
accTitle: איך RunAsInvoker מדכא בקשת elevation
accDescr: הכרזת requireAdministrator ב-manifest או זיהוי שגוי כ-installer גורמים לבקשת UAC elevation בהפעלה אבל החלת RunAsInvoker דורסת את שניהם והאפליקציה עולה עם token של תהליך האב
manifest["הכרזת requireAdministrator"] --> shim{"הוחל RunAsInvoker?"}
detect["זוהה בטעות כ-installer"] --> shim
shim -->|לא| uac["בקשת UAC elevation בכל הפעלה"]
shim -->|כן| token["עולה עם token של האב"]
token -.-> limit["עבודה שבאמת צריכה Administrator נכשלת בתוך האפליקציה"]
איור 15: RunAsInvoker רק דורס את סיבת בקשת ה-elevation; ההרשאות אינן גדלות.
גם בלי לבנות .sdb ב-Compatibility Administrator אפשר להחיל את אותה שכבה זמנית עם משתנה הסביבה __COMPAT_LAYER.
:: Apply RunAsInvoker to child processes started from this command prompt
set __COMPAT_LAYER=RunAsInvoker
start "" "C:\LegacyApp\Gyomu.exe"
# In PowerShell
$env:__COMPAT_LAYER = 'RunAsInvoker'
Start-Process 'C:\LegacyApp\Gyomu.exe'
אם הופכים את שני השורות האלה לקובץ batch ומפיצים אותו כקיצור דרך, אפשר להימנע ממסירת הרשאות local Administrator למשתמשים רגילים, ו-IT כבר אינו נקרא בכל פעם לסיסמת UAC. זו טכניקת תאימות שמקשיחה את ההגנה, בהתאם ל-least privilege.
flowchart TB
accTitle: האפקט של הפצת batch של RunAsInvoker
accDescr: הפצת batch בן שתי שורות שמגדיר RunAsInvoker כקיצור דרך פירושה הימנעות ממסירת הרשאות Administrator למשתמשים רגילים, אי-קריאה ל-IT לסיסמת UAC, ותפעול שעוקב אחרי least privilege
bat["הפיצו batch בן שתי שורות"] --> noadmin["אפשר להימנע ממסירת הרשאות Administrator"]
bat --> nocall["IT אינו נקרא בגלל UAC"]
noadmin --> lp["תפעול שעוקב אחרי least privilege"]
nocall --> lp
איור 16: הפצת batch לבדה יכולה להפחית גם מסירת הרשאות Administrator וגם קריאה בגלל UAC.
גם ההסתייגויות, בבירור.
- ההרשאות אינן גדלות. עבודה שבאמת צריכה הרשאות Administrator (כתיבות ל-HKLM, עדכונים תחת Program Files וכן הלאה) תיכשל בתוך האפליקציה, או, אם התנאים מתקיימים, תופנה אל ה-VirtualStore על ידי UAC virtualization.10 אם שמירת הגדרות «הפסיקה לעבוד» פתאום, חשדו ב-virtualization.
- שיטת משתנה הסביבה חלה רק על child processes. להחלה קבועה, הגדרה ישירה במפתח Layers (ל-RUNASINVOKER אין פריט בלשונית) או הפצה דרך
.sdbאמינה. - תיקון יעד הכתיבה הוא הנתיב האמיתי. אם אפשר לשנות את האפליקציה, העבירו את קובץ ההגדרות תחת
%APPDATA%והכריזוasInvokerב-manifest — זו הצורה הנכונה.9
flowchart TB
accTitle: החלה זמנית וקבועה של RunAsInvoker
accDescr: החלה דרך משתנה COMPAT_LAYER חלה רק על child processes שמתחילים משם; להחלה קבועה השתמשו בהגדרה ישירה במפתח Layers או בהפצה דרך .sdb
env["הגדרה דרך משתנה סביבה"] --> child["חלה רק על child processes"]
child -.-> tmp["החלה זמנית"]
layers["הגדרה ישירה במפתח Layers"] --> always["החלה קבועה"]
sdb["הפצה דרך sdb"] --> always
איור 17: שיטת משתנה הסביבה היא החלה זמנית המוגבלת ל-child processes; הפיכתה לקבועה נעשית במפתח Layers או ב-.sdb.
9. להמשיך להריץ או לעבור — מה לחשוב אחרי שזה עובד תחת shim
הרגע שבו זה עובד תחת shim הוא הקלה, אבל חשוב לא לעצור את החשיבה שם. עבודה תחת shim פירושה רק שזה במקרה התאים לכלי קיבול ש-Windows הכין. צירי ההחלטה, בטבלה.
| ציר החלטה | תנאים שנוטים להמשך הרצה (shim) | תנאים שנוטים להגירה / שכתוב |
|---|---|---|
| תקופת שימוש נותרת | מתוכנן לפרוש עם העסק תוך 1–2 שנים | מונח להמשיך 5 שנים או יותר |
| Source code | אין (הספק נעלם, או אבד) | קיים, או אפשר לשחזר את הנכס |
| עומק התלות | בעיית תאימות API ב-user mode בלבד | תלוי ב-driver, ב-16-bit או בחומרה ייעודית |
| חלופות | אין מוצר ארוז או גרסה חדשה | מוצר היעד והטכנולוגיה ברורים |
| השפעה כשנכשל | העסק יכול לרוץ בנוהל גיבוי | העסק הליבתי נפגע ישירות |
| כושר בדיקה | אפשר לאשר התנהגות בכל feature update | אין משאב בדיקה, ונוטה לקפיאה |
אם מחליטים להמשיך להריץ, הכניסו את שלוש הנקודות הבאות לתפעול כסט.
- תעדו. איזה EXE, איזה shim/layer, ולמה. השאירו את ערך מפתח Layers ואת GUID של ה-
.sdbב-inventory. «אף אחד לא יודע למה זה עובד» הוא החוב הגדול ביותר שמשאירים לאדם הבא. זו אותה תפיסת שימור שמכוסה ב«When You Inherit a System With No Source Code and No Documentation». - בדקו. כללו הפעלה ופעולות עיקריות של אפליקציות שמוחזקות באוויר על ידי shims בפריטי הבדיקה ל-feature update של Windows. קשרו זאת גם לתוכנית החלפת ה-OS (Practical Options After Windows 10 End of Support).
- קבעו תאריך יעד. החליטו את סוף ההמשך — «עד רענון מערכת הליבה הבא», «עד מרץ 2028» — והריצו שיקולי הגירה במקביל.
flowchart TB
accTitle: סט התפעול התלת-נקודתי אחרי החלטה להמשיך להריץ
accDescr: תעדו ב-inventory איזה shim גורם לזה לרוץ, בדקו התנהגות של אפליקציות שמוחזקות באוויר על ידי shims בכל feature update, קבעו תאריך יעד לסוף ההמשך והריצו שיקולי הגירה במקביל
decide["החליטו להמשיך להריץ"] --> rec["תעדו: איזה shim גורם לזה לרוץ ב-inventory"]
rec --> verify["בדקו: אשרו התנהגות בכל feature update"]
verify --> deadline["תאריך יעד: החליטו את סוף ההמשך"]
deadline --> mig["הריצו שיקולי הגירה במקביל"]
איור 18: המשך הרצה מתופעל כסט תלת-נקודתי של תיעוד, בדיקה ותאריך יעד, כולל שיקולי הגירה במקביל.
בצד ההגירה האפשרויות הסטנדרטיות משתנות עם טכנולוגיית האפליקציה. ל-VB6 הבחירה המשולשת של שכתוב מלא, המרה אוטומטית והגירה מדורגת שמסודרת ב«How Long Will VB6 Apps Keep Running?»; לתלות ב-ActiveX/OCX טבלת ההחלטה לשמר / לעטוף / להחליף ב«איך מתייחסים היום ל-ActiveX / OCX». הדרך הבריאה למקם shim היא כקניית זמן כדי שתקופת השיקול וההכנה של פרויקט ההגירה ההוא תוכל לרוץ בבטחה.
flowchart TB
accTitle: אפשרויות בצד ההגירה ואיפה יושב shim
accDescr: אפשרויות ההגירה הסטנדרטיות משתנות עם טכנולוגיית האפליקציה; ל-VB6 הבחירה המשולשת שכתוב המרה אוטומטית או הגירה מדורגת ולתלות ActiveX טבלת לשמר לעטוף או להחליף ו-shim ממוקם כקניית זמן לשיקולי פרויקט ההגירה ולהכנתו
tech{"מה טכנולוגיית האפליקציה?"} -->|VB6| vb["שכתוב, המרה אוטומטית או הגירה מדורגת"]
tech -->|תלות ActiveX| ax["לשמר, לעטוף או להחליף"]
shim["המשך הרצה דרך shim"] -.->|קונה זמן לשיקול ולהכנה| tech
איור 19: אפשרויות ההגירה הסטנדרטיות נקבעות לפי טכנולוגיית האפליקציה, ו-shim ממוקם כקניית זמן לאותו שיקול.
10. סיכום
- Compatibility mode הוא צרור shims. הגדרות מלשונית Compatibility נכתבות למפתח AppCompatFlags\Layers ומוזרקות ל-process בהפעלה כ-API hook דרך כתיבה מחדש של ה-IAT.
- Shims הם אוסף תשובות שהאפליקציה הישנה מצפה להן. מסופקים shims מוכנים ל-spoof של גרסה, מיפוי מחדש של נתיבים, זיוף Registry, זיוף בדיקות Administrator וכדומה.
- Windows עצמו משתמש במספר גדול של shims כברירת מחדל, ו-PCA יכול להחיל אותם אוטומטית. הסתמכות על compatibility mode עצמה היא בחירה סבירה שרוכבת על מנגנון רשמי של ה-OS.
- יש גבול עקרוני של user mode בלבד בלי עקיפת אבטחה, ו-kernel drivers, אפליקציות 16-bit וגישה ישירה לחומרה אי אפשר להציל.
- פריסה ארגונית היא בניית
.sdbמותאם ב-Compatibility Administrator (Windows ADK) והפצתו עם sdbinst. בחירת מהדורת 32/64-bit, בדיקה בחשבון המשתמש בפועל וניהול עדכונים לפי GUID הן הנקודות המעשיות. - אפליקציות ש«דורשות Administrator אבל אינן צריכות אותו באמת» אפשר להוריד להרשאות רגילות עם
__COMPAT_LAYER=RunAsInvoker. זו טכניקה הגנתית שמדכאת את בקשת ה-elevation במקום למסור הרשאות. - ריצה תחת shim היא המשך, לא פתרון. תיעוד מה גורם לזה לרוץ, בדיקה בכל feature update, וקביעת תאריך יעד כדי שההגירה תרוץ במקביל — הסט התלת-נקודתי הזה כלול בהחלטה «להסתמך על compatibility mode».
בפעם הבאה שאפליקציה ישנה מתחילה לעבוד אחרי תיבת compatibility mode, שאלו שוב. «בזכות איזה workaround האפליקציה הזו רצה? כמה זמן ה-workaround הזה ימשיך לעבוד?» אם אפשר לענות, המשך הרצה הוא אסטרטגיה מכובדת.
מאמרים קשורים
- Registry 32-bit/64-bit Redirection and Virtualization Pitfalls — Wow6432Node and the “The Value I Wrote Isn’t There” Problem
- How Long Will VB6 Apps Keep Running? — Runtime Support Status and a Practical Path to .NET Migration
- איך מתייחסים היום ל-ActiveX / OCX — טבלת החלטה: לשמר, לעטוף או להחליף
- Practical Options After Windows 10 End of Support — A Decision Table for ESU, LTSC, and Replacement
- When You Inherit a System With No Source Code and No Documentation — A Practical Playbook for Keeping It Running
- Context menu ו-file association ב-Windows 11 — IExplorerCommand, MSIX ו-sparse package
תחומי ייעוץ קשורים
KomuraSoft LLC מטפלת בחקירת איך מתנהגות אפליקציות עסקיות ישנות בלי source ובתכנון המשך ההרצה שלהן (בחירת shims ו-compatibility mode, בניית .sdb מותאם ופריסתו), באימות תאימות של אפליקציות קיימות להגירת Windows 11, ובתכנון שכתוב או הגירה שרצים במקביל להמשך. ייעוץ משלב «התחיל לעבוד ב-compatibility mode, אבל מותר להשאיר כך?» בסדר.
- שימוש חוזר והעברה של נכסים קיימים
- Windows Custom Software Development
- ייעוץ טכני וסקירת תכנון
- יצירת קשר
קישורי עיון
-
Microsoft Learn, Application Compatibility Database. שתשתית התאימות מנהלת בעיות ותיקונים במסד בפורמט
.sdb, matching לפי תכונות קובץ הפעלה, Apphelp (הצגת הודעה) ו-Appfix (API hook דרך shim), ו-compatibility layer (mode) שמצררת כמה shims ודגלים. ↩ ↩2 ↩3 -
Microsoft Learn, DXGI overview. שהגדרות תאימות אפליקציות נשמרות במפתח Registry HKCU\SOFTWARE\Microsoft\Windows NT\CurrentVersion\AppCompatFlags\Layers (תוך שימוש בהגדרות תאימות DXGI כדוגמה). ↩ ↩2
-
Microsoft Learn, Understanding and Using Compatibility Fixes. שתיקון תאימות (shim) מפנה קריאות API בכתיבה מחדש של ה-IAT (Import Address Table), שקישור דינמי מטופל ב-hook על GetProcAddress, ש-shim כפוף לאותן מגבלות אבטחה כמו האפליקציה ואינו יכול לעקוף מנגנוני אבטחה של ה-OS, שהוא user mode בלבד ואינו יכול לתקן בעיות driver, שתיקון אפשרי עם shim אפשרי גם עם תיקון קוד, תרחישי שימוש כמו אפליקציות שתמיכת הספק שלהן הסתיימה, ושתיקוני תאימות ש-Microsoft מספקת נשלחים כחלק מ-Windows ומתעדכנים דרך Windows Update. ↩ ↩2 ↩3 ↩4 ↩5 ↩6 ↩7 ↩8
-
Microsoft Learn, Compatibility Fixes for Windows 10, Windows 8, Windows 7, and Windows Vista. רשימה ותיאור של תיקוני תאימות ידועים כולל CorrectFilePaths, VirtualRegistry, ForceAdminAccess, RunAsAdmin/RunAsHighest/RunAsInvoker, WRPMitigation, EmulateGetDiskFreeSpace, GlobalMemoryStatusLie, LoadLibraryRedirect ומשפחת VersionLie; בחירת מהדורת 32/64-bit של Compatibility Administrator; ושבדיקה במצב elevated פירושה ש-virtualization ו-redirect אינם מתנהגים כמצופה, ולכן יש לאמת בחשבון המשתמש בפועל. ↩ ↩2 ↩3 ↩4
-
Microsoft Learn, Program Compatibility Assistant scenarios for Windows 8. ש-PCA עוקב אחרי הרצת אפליקציה, מזהה סימנים לבעיית תאימות ידועה, ומציע להחיל תיקון מומלץ או מחיל אותו אוטומטית (PINDLL, DISABLEUSERCALLBACKEXCEPTION, VIRTUALIZEDELETE, WRPMITIGATION וכדומה), והחלת תיקון מלשונית Compatibility ומ-Program Compatibility Troubleshooter. ↩ ↩2
-
Microsoft Learn, GetVersionExW function. שמ-Windows 8.1 ואילך הערך ש-GetVersionEx מחזיר תלוי ב-manifest, שאפליקציה שאינה מנושרת ל-Windows 8.1/10 מקבלת את ערך גרסת Windows 8 (6.2), ושכאשר compatibility mode מופעל מדווחת גרסת ה-OS שנבחרה. ↩ ↩2 ↩3
-
Microsoft Learn, Targeting your application for Windows. איך להכריז GUIDs של מערכות נתמכות עם רכיב supportedOS במדור compatibility של manifest האפליקציה, ההתנהגות כשאין הכרזה, ואפליקציית x86 32-bit אינטראקטיבית שאינה כוללת trustInfo כפופה ל-UAC file virtualization (הפניית כתיבה אל VirtualStore). ↩ ↩2
-
Microsoft Learn, Running 32-bit Applications. ש-WOW64 היא שכבת emulation שמריצה אפליקציות 32-bit על Windows 64-bit ומבודדת התנגשויות קבצים ו-Registry, וש-Windows 64-bit אינו תומך בהרצת אפליקציות 16-bit, עם כשל הפעלה ב-ERROR_BAD_EXE_FORMAT בגלל מספר הסיביות התקפות ב-handle. ↩ ↩2
-
Microsoft Learn, Using the RunAsInvoker Fix. שתיקון התאימות RunAsInvoker מפעיל את האפליקציה עם ה-token שעבר בירושה מתהליך האב, שהוא דורס גם זיהוי installer וגם עיבוד manifest, שהוא מוחל כדגל loader בלי ליירט API, ושכאשר אפשר לתקן את הקוד התיקון הנכון הוא להכריז asInvoker ב-manifest. ↩ ↩2 ↩3
-
Microsoft Learn, Registry Virtualization. ש-Registry virtualization היא טכנולוגיית תאימות שמפנה בשקיפות כתיבות גלובליות אל HKLM\Software אל VirtualStore לפי משתמש, שרק תהליכים אינטראקטיביים 32-bit בטווח והיא מבוטלת לתהליכים שמציינים requestedExecutionLevel ב-manifest ולתהליכי 64-bit, ושהיא ממוקמת כטכנולוגיה זמנית המיועדת להסרה מ-Windows עתידי. ↩ ↩2
-
Microsoft Learn, High DPI Desktop Application Development on Windows. שאפליקציה שאינה DPI-aware מטופלת כמציירת ב-96 DPI קבוע ועל צג עם DPI גבוה Windows מוחח את ה-bitmap כך שהיא נראית מטושטשת, וההבדלים בין מצבי DPI awareness (Unaware/System/Per-Monitor). ↩ ↩2
-
Microsoft Learn, Download and install the Windows ADK. ש-Windows ADK כולל Compatibility Administrator ו-Standard User Analyzer, ואיך לחשוב על בחירת גרסת ADK ואיך להוריד ולהתקין אותה. ↩
-
Microsoft Learn, Compatibility Administrator User’s Guide. ש-Compatibility Administrator מספק החלת compatibility fixes, compatibility modes והודעות AppHelp ויצירת מסד מותאם, ושמהדורות 32 ו-64-bit מותקנות שתיהן וחייבים להשתמש במהדורת 32-bit לאפליקציות 32-bit ובמהדורת 64-bit לאפליקציות 64-bit. ↩
-
Microsoft Learn, Creating a Custom Compatibility Fix in Compatibility Administrator. שתיקון תאימות (שנקרא בעבר shim) הוא פיסת קוד קטנה שמיירטת קריאת API; הליך יצירת Application Fix במסד מותאם (ציון שם אפליקציה, ספק ו-EXE יעד, בחירת compatibility mode, בחירת shims נוספים, הגדרת תנאי matching); ושצריך להשאיר תנאים שמזהים נכון את האפליקציה תוך צמצום מידע ה-matching. ↩ ↩2
-
Microsoft Learn, Compatibility Fix Database Management Strategies and Deployment. שמסד מנוהל מרכזית מומלץ כאסטרטגיית ניהול למסד תאימות מותאם, שתיקון תאימות צריך לכלול בדיקת גרסה (תנאי matching) כדי שלא יוחל על גרסה חדשה, התקנה מקומית עם Sdbinst.exe (אפשרויות -q, -u, -g), שהתקנת גרסה חדשה עם אותו GUID מסד מסירה אוטומטית את הישנה, ושיטות הפצה דרך MSI או script. ↩ ↩2 ↩3
מאמרים קשורים
מאמרים עדכניים עם אותן תגיות, להעמקה בנושאים קרובים.
הרשת עובדת אבל Windows מציג "אין אינטרנט" — לבודד NCSI, DNS, Proxy ו-VPN ב-Windows
למה Windows מציג "אין אינטרנט" בזמן שהרשת עובדת — נקודת המוצא היא קביעת הקישוריות של NCSI. כאן מפרידים בין DNS, proxy, VPN ו-captive port...
מה Fast Startup באמת עושה — למה "Shut down" ב-Windows אינו אותו דבר כמו Restart
Shutdown ב-Windows הוא hybrid shutdown כברירת מחדל, ושומר את ה-kernel ואת ה-drivers ל-hiberfil.sys. למה רק restart מאפס אותם, ומתי לכבות ...
Time Travel Debugging — להקליט ולהריץ אחורה באגים שלא משתחררים באפליקציות ארוכות-ריצה
באג פעם בחודש משאיר ב-crash dump רק את התוצאה. מקליטים ומריצים אחורה את הביצוע עם WinDbg Time Travel Debugging (TTD): TTD.exe, ring buffe...
למה arguments נשברים — כללי command-line arguments ב-Windows
Windows מעביר ל-CreateProcess מחרוזת אחת שהמקבל מפצל. מכסה את כללי CommandLineToArgvW, CRT ו-.NET, ArgumentList, ובניה ב-C++.
סיום התמיכה ב-printer drivers של Windows — איך אפליקציות עסקיות מתכוננות להדפסת דוחות ותוויות
Microsoft מפסיקה בהדרגה printer drivers מסוג v3/v4. מה Windows protected print mode מסיר, ואיך עושים inventory ומכינים הדפסת דוחות ותוויו...
נושאים קשורים
העמודים האלה ממקמים את הנושא בהקשר רחב יותר של שירותים והחלטות.
נושאים טכניים ב-Windows
שער לנושאי פיתוח Windows, חקירת תקלות וניצול נכסים קיימים.
שירותים הקשורים לנושא הזה
המאמר קשור ישירות לשירותים הבאים.
פיתוח יישומי Windows
יישומים עסקיים, חיבור התקנים וכלי תקשורת, מהגדרת הדרישות ועד הפיתוח.
שאלות נפוצות
שאלות נפוצות בפניות בנושא המאמר.
- אם האפליקציה התחילה לעבוד אחרי שסימנתי compatibility mode, אפשר להמשיך כך?
- להמשך עבודה בטווח הקרוב — כן. Compatibility mode הוא user-mode API hook שנקרא shim, מנגנון רשמי של Windows. אבל shim הוא workaround: הוא מריץ את האפליקציה בלי לתקן אותה, ועדכון OS יכול לשבור את ההנחות שוב. תעדו שהיא רצה ב-compatibility mode, ותחברו את זה להחלטה אם לשכתב אותה או להשאיר אותה באוויר בכוונה.
- מה תיבת הסימון של compatibility mode באמת עושה?
- כששומרים את לשונית Compatibility במאפייני הקובץ, Windows כותב את נתיב ה-EXE וערך כמו "WINXPSP3" או "HIGHDPIAWARE" תחת HKCU\Software\Microsoft\Windows NT\CurrentVersion\AppCompatFlags\Layers. בהפעלה הבאה ה-loader קורא את הערך ומחיל על ה-process את שכבת התאימות המתאימה (צרור shims). Windows XP compatibility mode, למשל, מחזיר ערך ישן מ-API של שאילתת גרסה. ה-OS עצמו לא משתנה; רק לאותו process מוצג Windows ישן.
- אפשר להריץ אפליקציות 16-bit ב-compatibility mode על Windows 64-bit?
- לא. Windows 64-bit מריץ אפליקציות 32-bit דרך WOW64, אבל לא תומך ב-16-bit, וניסיון הפעלה נכשל עם ERROR_BAD_EXE_FORMAT. זו מגבלת ארכיטקטורה ש-shim לא יכול לעקוף. גם חבילות ישנות שה-stub של ה-installer הוא 16-bit נופלות מאותה סיבה. אם באמת צריך אותן, מחפשים מחוץ ל-compatibility mode — למשל VM עם Windows 32-bit.
- אפשר להריץ אפליקציה ש"לא עולה בלי Run as administrator" תחת משתמש רגיל?
- שווה לנסות RunAsInvoker. מריצים set __COMPAT_LAYER=RunAsInvoker ב-command prompt ואז מפעילים את האפליקציה: בקשות elevation מ-manifest של requireAdministrator או מזיהוי installer מדוכאות, והיא רצה באותן הרשאות (משתמש רגיל) כמו התהליך הקורא. לאפליקציה שרק מבקשת Administrator ולא משתמשת בזה בפועל, זה יכול להוציא elevation מהיום-יום. ההרשאות לא גדלות, אז פעולה שבאמת צריכה Administrator תיכשל בתוך האפליקציה. מאמצים רק אחרי שבודקים שההתנהגות תקינה.
- מאיפה מורידים את Compatibility Administrator?
- הוא חלק מ-Windows ADK (Windows Assessment and Deployment Kit). מורידים את ה-ADK מאתר Microsoft, ובהתקנה בוחרים את Application Compatibility Tools. מותקנות גם מהדורת 32-bit וגם 64-bit; משתמשים ב-32-bit לאפליקציות 32-bit וב-64-bit לאפליקציות 64-bit. מסד תאימות מותאם (.sdb) שיוצרים מחילים עם sdbinst על כל מחשב.