util: Wait for initial name owners in DBusSenderCheck before checking
Otherwise an allowed caller might get rejected if the call is right after a gnome-shell restart and the watchers have not finished running their callbacks yet. Fixes: https://gitlab.gnome.org/GNOME/gnome-shell/-/issues/4813 Part-of: <https://gitlab.gnome.org/GNOME/gnome-shell/-/merge_requests/2048>
This commit is contained in:
parent
37271ffe70
commit
85609a232d
@ -117,9 +117,9 @@ var IntrospectService = class {
|
|||||||
type == Meta.WindowType.UTILITY;
|
type == Meta.WindowType.UTILITY;
|
||||||
}
|
}
|
||||||
|
|
||||||
GetRunningApplicationsAsync(params, invocation) {
|
async GetRunningApplicationsAsync(params, invocation) {
|
||||||
try {
|
try {
|
||||||
this._senderChecker.checkInvocation(invocation);
|
await this._senderChecker.checkInvocation(invocation);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
invocation.return_gerror(e);
|
invocation.return_gerror(e);
|
||||||
return;
|
return;
|
||||||
@ -128,13 +128,13 @@ var IntrospectService = class {
|
|||||||
invocation.return_value(new GLib.Variant('(a{sa{sv}})', [this._runningApplications]));
|
invocation.return_value(new GLib.Variant('(a{sa{sv}})', [this._runningApplications]));
|
||||||
}
|
}
|
||||||
|
|
||||||
GetWindowsAsync(params, invocation) {
|
async GetWindowsAsync(params, invocation) {
|
||||||
let focusWindow = global.display.get_focus_window();
|
let focusWindow = global.display.get_focus_window();
|
||||||
let apps = this._appSystem.get_running();
|
let apps = this._appSystem.get_running();
|
||||||
let windowsList = {};
|
let windowsList = {};
|
||||||
|
|
||||||
try {
|
try {
|
||||||
this._senderChecker.checkInvocation(invocation);
|
await this._senderChecker.checkInvocation(invocation);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
invocation.return_gerror(e);
|
invocation.return_gerror(e);
|
||||||
return;
|
return;
|
||||||
|
@ -486,20 +486,42 @@ var DBusSenderChecker = class {
|
|||||||
constructor(allowList) {
|
constructor(allowList) {
|
||||||
this._allowlistMap = new Map();
|
this._allowlistMap = new Map();
|
||||||
|
|
||||||
|
this._uninitializedNames = new Set(allowList);
|
||||||
|
this._initializedPromise = new Promise(resolve => {
|
||||||
|
this._resolveInitialized = resolve;
|
||||||
|
});
|
||||||
|
|
||||||
this._watchList = allowList.map(name => {
|
this._watchList = allowList.map(name => {
|
||||||
return Gio.DBus.watch_name(Gio.BusType.SESSION,
|
return Gio.DBus.watch_name(Gio.BusType.SESSION,
|
||||||
name,
|
name,
|
||||||
Gio.BusNameWatcherFlags.NONE,
|
Gio.BusNameWatcherFlags.NONE,
|
||||||
(conn_, name_, owner) => this._allowlistMap.set(name, owner),
|
(conn_, name_, owner) => {
|
||||||
() => this._allowlistMap.delete(name));
|
this._allowlistMap.set(name, owner);
|
||||||
|
this._checkAndResolveInitialized(name);
|
||||||
|
},
|
||||||
|
() => {
|
||||||
|
this._allowlistMap.delete(name);
|
||||||
|
this._checkAndResolveInitialized(name);
|
||||||
|
});
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* @param {string} name - bus name for which the watcher got initialized
|
||||||
|
*/
|
||||||
|
_checkAndResolveInitialized(name) {
|
||||||
|
if (this._uninitializedNames.delete(name) &&
|
||||||
|
this._uninitializedNames.size === 0)
|
||||||
|
this._resolveInitialized();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @async
|
||||||
* @param {string} sender - the bus name that invoked the checked method
|
* @param {string} sender - the bus name that invoked the checked method
|
||||||
* @returns {bool}
|
* @returns {bool}
|
||||||
*/
|
*/
|
||||||
_isSenderAllowed(sender) {
|
async _isSenderAllowed(sender) {
|
||||||
|
await this._initializedPromise;
|
||||||
return [...this._allowlistMap.values()].includes(sender);
|
return [...this._allowlistMap.values()].includes(sender);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -507,15 +529,16 @@ var DBusSenderChecker = class {
|
|||||||
* Check whether the bus name that invoked @invocation maps
|
* Check whether the bus name that invoked @invocation maps
|
||||||
* to an entry in the allow list.
|
* to an entry in the allow list.
|
||||||
*
|
*
|
||||||
|
* @async
|
||||||
* @throws
|
* @throws
|
||||||
* @param {Gio.DBusMethodInvocation} invocation - the invocation
|
* @param {Gio.DBusMethodInvocation} invocation - the invocation
|
||||||
* @returns {void}
|
* @returns {void}
|
||||||
*/
|
*/
|
||||||
checkInvocation(invocation) {
|
async checkInvocation(invocation) {
|
||||||
if (global.context.unsafe_mode)
|
if (global.context.unsafe_mode)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if (this._isSenderAllowed(invocation.get_sender()))
|
if (await this._isSenderAllowed(invocation.get_sender()))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
throw new GLib.Error(Gio.DBusError,
|
throw new GLib.Error(Gio.DBusError,
|
||||||
|
@ -37,7 +37,7 @@ var ScreenshotService = class {
|
|||||||
Gio.DBus.session.own_name('org.gnome.Shell.Screenshot', Gio.BusNameOwnerFlags.REPLACE, null, null);
|
Gio.DBus.session.own_name('org.gnome.Shell.Screenshot', Gio.BusNameOwnerFlags.REPLACE, null, null);
|
||||||
}
|
}
|
||||||
|
|
||||||
_createScreenshot(invocation, needsDisk = true, restrictCallers = true) {
|
async _createScreenshot(invocation, needsDisk = true, restrictCallers = true) {
|
||||||
let lockedDown = false;
|
let lockedDown = false;
|
||||||
if (needsDisk)
|
if (needsDisk)
|
||||||
lockedDown = this._lockdownSettings.get_boolean('disable-save-to-disk');
|
lockedDown = this._lockdownSettings.get_boolean('disable-save-to-disk');
|
||||||
@ -55,7 +55,7 @@ var ScreenshotService = class {
|
|||||||
return null;
|
return null;
|
||||||
} else if (restrictCallers) {
|
} else if (restrictCallers) {
|
||||||
try {
|
try {
|
||||||
this._senderChecker.checkInvocation(invocation);
|
await this._senderChecker.checkInvocation(invocation);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
invocation.return_gerror(e);
|
invocation.return_gerror(e);
|
||||||
return null;
|
return null;
|
||||||
@ -200,7 +200,7 @@ var ScreenshotService = class {
|
|||||||
"Invalid params");
|
"Invalid params");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
let screenshot = this._createScreenshot(invocation);
|
let screenshot = await this._createScreenshot(invocation);
|
||||||
if (!screenshot)
|
if (!screenshot)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
@ -223,7 +223,7 @@ var ScreenshotService = class {
|
|||||||
|
|
||||||
async ScreenshotWindowAsync(params, invocation) {
|
async ScreenshotWindowAsync(params, invocation) {
|
||||||
let [includeFrame, includeCursor, flash, filename] = params;
|
let [includeFrame, includeCursor, flash, filename] = params;
|
||||||
let screenshot = this._createScreenshot(invocation);
|
let screenshot = await this._createScreenshot(invocation);
|
||||||
if (!screenshot)
|
if (!screenshot)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
@ -246,7 +246,7 @@ var ScreenshotService = class {
|
|||||||
|
|
||||||
async ScreenshotAsync(params, invocation) {
|
async ScreenshotAsync(params, invocation) {
|
||||||
let [includeCursor, flash, filename] = params;
|
let [includeCursor, flash, filename] = params;
|
||||||
let screenshot = this._createScreenshot(invocation);
|
let screenshot = await this._createScreenshot(invocation);
|
||||||
if (!screenshot)
|
if (!screenshot)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
@ -269,7 +269,7 @@ var ScreenshotService = class {
|
|||||||
|
|
||||||
async SelectAreaAsync(params, invocation) {
|
async SelectAreaAsync(params, invocation) {
|
||||||
try {
|
try {
|
||||||
this._senderChecker.checkInvocation(invocation);
|
await this._senderChecker.checkInvocation(invocation);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
invocation.return_gerror(e);
|
invocation.return_gerror(e);
|
||||||
return;
|
return;
|
||||||
@ -289,9 +289,9 @@ var ScreenshotService = class {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
FlashAreaAsync(params, invocation) {
|
async FlashAreaAsync(params, invocation) {
|
||||||
try {
|
try {
|
||||||
this._senderChecker.checkInvocation(invocation);
|
await this._senderChecker.checkInvocation(invocation);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
invocation.return_gerror(e);
|
invocation.return_gerror(e);
|
||||||
return;
|
return;
|
||||||
@ -311,7 +311,7 @@ var ScreenshotService = class {
|
|||||||
}
|
}
|
||||||
|
|
||||||
async PickColorAsync(params, invocation) {
|
async PickColorAsync(params, invocation) {
|
||||||
const screenshot = this._createScreenshot(invocation, false, false);
|
const screenshot = await this._createScreenshot(invocation, false, false);
|
||||||
if (!screenshot)
|
if (!screenshot)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
@ -81,13 +81,14 @@ var GnomeShell = class {
|
|||||||
/**
|
/**
|
||||||
* Focus the overview's search entry
|
* Focus the overview's search entry
|
||||||
*
|
*
|
||||||
|
* @async
|
||||||
* @param {...any} params - method parameters
|
* @param {...any} params - method parameters
|
||||||
* @param {Gio.DBusMethodInvocation} invocation - the invocation
|
* @param {Gio.DBusMethodInvocation} invocation - the invocation
|
||||||
* @returns {void}
|
* @returns {void}
|
||||||
*/
|
*/
|
||||||
FocusSearchAsync(params, invocation) {
|
async FocusSearchAsync(params, invocation) {
|
||||||
try {
|
try {
|
||||||
this._senderChecker.checkInvocation(invocation);
|
await this._senderChecker.checkInvocation(invocation);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
invocation.return_gerror(e);
|
invocation.return_gerror(e);
|
||||||
return;
|
return;
|
||||||
@ -100,13 +101,14 @@ var GnomeShell = class {
|
|||||||
/**
|
/**
|
||||||
* Show OSD with the specified parameters
|
* Show OSD with the specified parameters
|
||||||
*
|
*
|
||||||
|
* @async
|
||||||
* @param {...any} params - method parameters
|
* @param {...any} params - method parameters
|
||||||
* @param {Gio.DBusMethodInvocation} invocation - the invocation
|
* @param {Gio.DBusMethodInvocation} invocation - the invocation
|
||||||
* @returns {void}
|
* @returns {void}
|
||||||
*/
|
*/
|
||||||
ShowOSDAsync([params], invocation) {
|
async ShowOSDAsync([params], invocation) {
|
||||||
try {
|
try {
|
||||||
this._senderChecker.checkInvocation(invocation);
|
await this._senderChecker.checkInvocation(invocation);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
invocation.return_gerror(e);
|
invocation.return_gerror(e);
|
||||||
return;
|
return;
|
||||||
@ -138,13 +140,14 @@ var GnomeShell = class {
|
|||||||
/**
|
/**
|
||||||
* Focus specified app in the overview's app grid
|
* Focus specified app in the overview's app grid
|
||||||
*
|
*
|
||||||
|
* @async
|
||||||
* @param {string} id - an application ID
|
* @param {string} id - an application ID
|
||||||
* @param {Gio.DBusMethodInvocation} invocation - the invocation
|
* @param {Gio.DBusMethodInvocation} invocation - the invocation
|
||||||
* @returns {void}
|
* @returns {void}
|
||||||
*/
|
*/
|
||||||
FocusAppAsync([id], invocation) {
|
async FocusAppAsync([id], invocation) {
|
||||||
try {
|
try {
|
||||||
this._senderChecker.checkInvocation(invocation);
|
await this._senderChecker.checkInvocation(invocation);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
invocation.return_gerror(e);
|
invocation.return_gerror(e);
|
||||||
return;
|
return;
|
||||||
@ -157,13 +160,14 @@ var GnomeShell = class {
|
|||||||
/**
|
/**
|
||||||
* Show the overview's app grid
|
* Show the overview's app grid
|
||||||
*
|
*
|
||||||
|
* @async
|
||||||
* @param {...any} params - method parameters
|
* @param {...any} params - method parameters
|
||||||
* @param {Gio.DBusMethodInvocation} invocation - the invocation
|
* @param {Gio.DBusMethodInvocation} invocation - the invocation
|
||||||
* @returns {void}
|
* @returns {void}
|
||||||
*/
|
*/
|
||||||
ShowApplicationsAsync(params, invocation) {
|
async ShowApplicationsAsync(params, invocation) {
|
||||||
try {
|
try {
|
||||||
this._senderChecker.checkInvocation(invocation);
|
await this._senderChecker.checkInvocation(invocation);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
invocation.return_gerror(e);
|
invocation.return_gerror(e);
|
||||||
return;
|
return;
|
||||||
@ -173,9 +177,9 @@ var GnomeShell = class {
|
|||||||
invocation.return_value(null);
|
invocation.return_value(null);
|
||||||
}
|
}
|
||||||
|
|
||||||
GrabAcceleratorAsync(params, invocation) {
|
async GrabAcceleratorAsync(params, invocation) {
|
||||||
try {
|
try {
|
||||||
this._senderChecker.checkInvocation(invocation);
|
await this._senderChecker.checkInvocation(invocation);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
invocation.return_gerror(e);
|
invocation.return_gerror(e);
|
||||||
return;
|
return;
|
||||||
@ -187,9 +191,9 @@ var GnomeShell = class {
|
|||||||
invocation.return_value(GLib.Variant.new('(u)', [bindingAction]));
|
invocation.return_value(GLib.Variant.new('(u)', [bindingAction]));
|
||||||
}
|
}
|
||||||
|
|
||||||
GrabAcceleratorsAsync(params, invocation) {
|
async GrabAcceleratorsAsync(params, invocation) {
|
||||||
try {
|
try {
|
||||||
this._senderChecker.checkInvocation(invocation);
|
await this._senderChecker.checkInvocation(invocation);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
invocation.return_gerror(e);
|
invocation.return_gerror(e);
|
||||||
return;
|
return;
|
||||||
@ -205,9 +209,9 @@ var GnomeShell = class {
|
|||||||
invocation.return_value(GLib.Variant.new('(au)', [bindingActions]));
|
invocation.return_value(GLib.Variant.new('(au)', [bindingActions]));
|
||||||
}
|
}
|
||||||
|
|
||||||
UngrabAcceleratorAsync(params, invocation) {
|
async UngrabAcceleratorAsync(params, invocation) {
|
||||||
try {
|
try {
|
||||||
this._senderChecker.checkInvocation(invocation);
|
await this._senderChecker.checkInvocation(invocation);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
invocation.return_gerror(e);
|
invocation.return_gerror(e);
|
||||||
return;
|
return;
|
||||||
@ -220,9 +224,9 @@ var GnomeShell = class {
|
|||||||
invocation.return_value(GLib.Variant.new('(b)', [ungrabSucceeded]));
|
invocation.return_value(GLib.Variant.new('(b)', [ungrabSucceeded]));
|
||||||
}
|
}
|
||||||
|
|
||||||
UngrabAcceleratorsAsync(params, invocation) {
|
async UngrabAcceleratorsAsync(params, invocation) {
|
||||||
try {
|
try {
|
||||||
this._senderChecker.checkInvocation(invocation);
|
await this._senderChecker.checkInvocation(invocation);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
invocation.return_gerror(e);
|
invocation.return_gerror(e);
|
||||||
return;
|
return;
|
||||||
@ -307,9 +311,9 @@ var GnomeShell = class {
|
|||||||
this._grabbers.delete(name);
|
this._grabbers.delete(name);
|
||||||
}
|
}
|
||||||
|
|
||||||
ShowMonitorLabelsAsync(params, invocation) {
|
async ShowMonitorLabelsAsync(params, invocation) {
|
||||||
try {
|
try {
|
||||||
this._senderChecker.checkInvocation(invocation);
|
await this._senderChecker.checkInvocation(invocation);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
invocation.return_gerror(e);
|
invocation.return_gerror(e);
|
||||||
return;
|
return;
|
||||||
@ -321,9 +325,9 @@ var GnomeShell = class {
|
|||||||
invocation.return_value(null);
|
invocation.return_value(null);
|
||||||
}
|
}
|
||||||
|
|
||||||
HideMonitorLabelsAsync(params, invocation) {
|
async HideMonitorLabelsAsync(params, invocation) {
|
||||||
try {
|
try {
|
||||||
this._senderChecker.checkInvocation(invocation);
|
await this._senderChecker.checkInvocation(invocation);
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
invocation.return_gerror(e);
|
invocation.return_gerror(e);
|
||||||
return;
|
return;
|
||||||
|
Loading…
Reference in New Issue
Block a user