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

מה ההגנה בעצם דוחה

אנדרואיד מגן על אינטראקציות רגישות מפני tapjacking, שבו חלון אחר יושב מעל הדיאלוג וגונב את ההקשה או הופך אותה לדו-משמעית. תצוגה מצטרפת באמצעות View.setFilterTouchesWhenObscured, והאירוע מגיע עם MotionEvent.FLAG_WINDOW_IS_OBSCURED כאשר חלון אחר מסומן כמכסה חלקית או מלאה. אז האירוע נזרק במקום להימסר למקום הלא נכון. אנדרואיד 12 (API 31) הרחיב את אותה הגנה בחסימת מגעים לא מהימנים במשטחי ההסכמה של המערכת, ולכן דיאלוג האישור יכול לסרב להקשה משכבת כיסוי שאפליקציות אחרות עדיין היו מקבלות.

שלושה דברים יוצרים מכשול באופן שגרתי: אפליקציה עם הרשאת הצגה מעל אפליקציות אחרות, שירות נגישות שמצייר תוכן, ווידג’ט צף של מקליט מסך או כלי סינון. תכונות תצוגה מסוימות של היצרן מוסיפות שכבה משלהן, ולכן אותו דיאלוג יכול להתנהג אחרת בשני טלפונים עם אותה גרסת אנדרואיד. חלון שמכסה חלקית מגדיר FLAG_WINDOW_IS_PARTIALLY_OBSCURED, והמגע נזרק לפני שהכפתור רואה אותו בכלל. זו תכונה של המסך, לא של הרשת. שום דבר לא נשלח לשרת ה-VPN ברגע זריקת ההקשה, ולכן שום שינוי בצד השרת לא יכול להשפיע על התוצאה.

הפרידו בין הקשה מתה לחיבור שנכשל

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

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

adb shell cmd appops get com.example.vpn SYSTEM_ALERT_WINDOW
adb shell settings get secure enabled_accessibility_services

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

הסירו את המכשול ואז נסו שוב את הזרימה הרגילה

זהו קודם איזו אפליקציה ביקשה אישור VPN, כדי שתדעו איזו הסכמה אתם נותנים. אחר כך עצרו את שכבת הכיסוי המסוימת מההגדרה שלה, ולא על ידי שלילת הרשאה רחבה שאולי תזדקקו לה בהמשך. מסנן מסך בדרך כלל כולל מתג באפליקציה שלו; ווידג’ט צף כולל בקרת סגירה; מצב תצוגה של היצרן כולל מתג בהגדרות התצוגה.

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

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

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

מה לא לעשות כדי לעבור את הדיאלוג

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

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

במכשיר מנוהל, מדיניות שמגבילה שינויי VPN היא החלטת המנהל. ניסוי בשכבת כיסוי אינו הרשאה לעקוף אותה. באותה מידה, כפתור הסכמה שלא מגיב אינו סיבה להחליש אימות תעודות או לשנות פרטי חשבון: אף אחת משתי ההגדרות אינה מסירה מכשול מגע מקומי.

אם זה עדיין נכשל, דווחו את ההתנהגות המדויקת

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

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

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

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

מאמרים קשורים