KAuth

AuthServicesBackend.cpp
1/*
2 SPDX-FileCopyrightText: 2008 Nicola Gigante <nicola.gigante@gmail.com>
3 SPDX-FileCopyrightText: 2014, 2016 René Bertin <rjvbertin@gmail.com>
4
5 SPDX-License-Identifier: LGPL-2.1-or-later
6*/
7
8#include "AuthServicesBackend.h"
9
10#include <qplugin.h>
11
12#include <QDebug>
13#include <QLoggingCategory>
14
15Q_DECLARE_LOGGING_CATEGORY(KAUTH_OSX)
16// logging category for this backend, default: log stuff >= warning
17Q_LOGGING_CATEGORY(KAUTH_OSX, "kf.auth.apple", QtWarningMsg)
18
19namespace KAuth
20{
21static AuthorizationRef s_authRef = NULL;
22
23AuthorizationRef authRef()
24{
25 if (!s_authRef) {
26 AuthorizationCreate(NULL, kAuthorizationEmptyEnvironment, kAuthorizationFlagDefaults, &s_authRef);
27 }
28
29 return s_authRef;
30}
31
32// GetActionRights return codes:
33// errAuthorizationSuccess = 0,
34// errAuthorizationInvalidSet = -60001, /* The authorization rights are invalid. */
35// errAuthorizationInvalidRef = -60002, /* The authorization reference is invalid. */
36// errAuthorizationInvalidTag = -60003, /* The authorization tag is invalid. */
37// errAuthorizationInvalidPointer = -60004, /* The returned authorization is invalid. */
38// errAuthorizationDenied = -60005, /* The authorization was denied. */
39// errAuthorizationCanceled = -60006, /* The authorization was cancelled by the user. */
40// errAuthorizationInteractionNotAllowed = -60007, /* The authorization was denied since no user interaction was possible. */
41// errAuthorizationInternal = -60008, /* Unable to obtain authorization for this operation. */
42// errAuthorizationExternalizeNotAllowed = -60009, /* The authorization is not allowed to be converted to an external format. */
43// errAuthorizationInternalizeNotAllowed = -60010, /* The authorization is not allowed to be created from an external format. */
44// errAuthorizationInvalidFlags = -60011, /* The provided option flag(s) are invalid for this authorization operation. */
45// errAuthorizationToolExecuteFailure = -60031, /* The specified program could not be executed. */
46// errAuthorizationToolEnvironmentError = -60032, /* An invalid status was returned during execution of a privileged tool. */
47// errAuthorizationBadAddress = -60033, /* The requested socket address is invalid (must be 0-1023 inclusive). */
48static OSStatus GetActionRights(const QString &action, AuthorizationFlags flags, AuthorizationRef auth)
49{
50 AuthorizationItem item;
51 item.name = action.toUtf8().constData();
52 item.valueLength = 0;
53 item.value = NULL;
54 item.flags = 0;
55
56 AuthorizationRights rights;
57 rights.count = 1;
58 rights.items = &item;
59
60 OSStatus result = AuthorizationCopyRights(auth, &rights, kAuthorizationEmptyEnvironment, flags, NULL);
61 return result;
62}
63
64// On OS X we avoid using a helper but grab privilege from here, the client.
65AuthServicesBackend::AuthServicesBackend()
66 : AuthBackend()
67{
68 setCapabilities(AuthorizeFromClientCapability);
69}
70
71AuthServicesBackend::~AuthServicesBackend()
72{
73 if (s_authRef) {
74 OSStatus err = AuthorizationFree(s_authRef, kAuthorizationFlagDefaults);
75 qCDebug(KAUTH_OSX) << "AuthorizationFree(" << s_authRef << ") returned" << err;
76 s_authRef = NULL;
77 }
78}
79
80void AuthServicesBackend::setupAction(const QString &)
81{
82 // Nothing to do here...
83}
84
85Action::AuthStatus AuthServicesBackend::authorizeAction(const QString &action)
86{
87 Action::AuthStatus retval;
88 OSStatus result = GetActionRights(action, kAuthorizationFlagExtendRights | kAuthorizationFlagInteractionAllowed, authRef());
89 qCDebug(KAUTH_OSX) << "AuthServicesBackend::authorizeAction(" << action << ") AuthorizationCopyRights returned" << result;
90 switch (result) {
91 case errAuthorizationSuccess:
92 retval = Action::AuthorizedStatus;
93 break;
94 case errAuthorizationCanceled:
95 retval = Action::UserCancelledStatus;
96 break;
97 case errAuthorizationInteractionNotAllowed:
98 case errAuthorizationDenied:
99 retval = Action::DeniedStatus;
100 break;
101 case errAuthorizationInternal:
102 // does this make sense?
103 retval = Action::AuthRequiredStatus;
104 break;
105 case errAuthorizationExternalizeNotAllowed:
106 case errAuthorizationInternalizeNotAllowed:
107 case errAuthorizationToolExecuteFailure:
108 case errAuthorizationToolEnvironmentError:
109 case errAuthorizationBadAddress:
110 retval = Action::ErrorStatus;
111 break;
112 default:
113 retval = Action::InvalidStatus;
114 break;
115 }
116 return retval;
117}
118
119Action::AuthStatus AuthServicesBackend::actionStatus(const QString &action)
120{
121 Action::AuthStatus retval;
122 OSStatus result = GetActionRights(action, kAuthorizationFlagExtendRights | kAuthorizationFlagPreAuthorize, authRef());
123 qCDebug(KAUTH_OSX) << "AuthServicesBackend::actionStatus(" << action << ") AuthorizationCopyRights returned" << result;
124 // this function has a simpler return code parser:
125 switch (result) {
126 case errAuthorizationSuccess:
127 retval = Action::AuthorizedStatus;
128 break;
129 case errAuthorizationCanceled:
130 retval = Action::UserCancelledStatus;
131 break;
132 case errAuthorizationInteractionNotAllowed:
133 retval = Action::AuthRequiredStatus;
134 break;
135 default:
136 retval = Action::DeniedStatus;
137 break;
138 }
139 return retval;
140}
141
142QByteArray AuthServicesBackend::callerID() const
143{
144 AuthorizationExternalForm ext;
145 AuthorizationMakeExternalForm(authRef(), &ext);
146 QByteArray id((const char *)&ext, sizeof(ext));
147
148 return id;
149}
150
151bool AuthServicesBackend::isCallerAuthorized(const QString &action, const QByteArray &callerID, const QVariantMap &details)
152{
153 Q_UNUSED(details);
154
155 AuthorizationExternalForm ext;
156 memcpy(&ext, callerID.data(), sizeof(ext));
157
158 AuthorizationRef auth;
159
160 if (AuthorizationCreateFromExternalForm(&ext, &auth) != noErr) {
161 qCWarning(KAUTH_OSX()) << "AuthorizationCreateFromExternalForm(" << action << "," << callerID.constData() << ") failed";
162 return false;
163 }
164
165 OSStatus result = GetActionRights(action, kAuthorizationFlagExtendRights | kAuthorizationFlagInteractionAllowed, auth);
166
167 AuthorizationFree(auth, kAuthorizationFlagDefaults);
168 qCDebug(KAUTH_OSX) << "AuthServicesBackend::isCallerAuthorized(" << action << "," << callerID.constData() << ") AuthorizationCopyRights returned" << result;
169
170 return result == errAuthorizationSuccess;
171}
172
173}; // namespace KAuth
174
175#include "moc_AuthServicesBackend.cpp"
const char * constData() const const
char * data()
QByteArray toUtf8() const const
This file is part of the KDE documentation.
Documentation copyright © 1996-2024 The KDE developers.
Generated on Tue Mar 26 2024 11:13:10 by doxygen 1.10.0 written by Dimitri van Heesch, © 1997-2006

KDE's Doxygen guidelines are available online.