2 * Copyright (c) 2014 Ian Sutton <ian@kremlin.cc>
4 * Permission to use, copy, modify, and distribute this software for any
5 * purpose with or without fee is hereby granted, provided that the above
6 * copyright notice and this permission notice appear in all copies.
8 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
9 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
10 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
11 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
12 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
13 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
14 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
21 #include <glib/gprintf.h>
22 #include <glib-unix.h>
23 #include <polkit/polkit.h>
27 const gint MAX_TOKENS
= 20;
29 /* return must be g_free()'d */
30 gchar
*config_get(const gchar
*path
, gchar
*key
) {
32 gchar
*content
, **split_content
, *cur
, **cur_split
, *ret
;
35 gboolean breaker
= TRUE
;
37 ret
= (gchar
*) g_malloc0(4096);
39 if(!g_file_get_contents(path
, &content
, NULL
, &err
))
42 split_content
= g_strsplit(content
, "\n", MAX_TOKENS
);
44 while(breaker
&& (cur
= split_content
[incr
]) && (cur_split
= g_strsplit(cur
, "=", 2))) {
46 if(!g_strcmp0(key
, cur_split
[0])) {
48 g_strlcpy(ret
, cur_split
[1], 2048);
53 g_strfreev(cur_split
);
57 g_strfreev(split_content
);
61 return (ret
? ret
: NULL
);
64 gboolean
config_set(const gchar
*path
, gchar
*key
, gchar
*value
) {
66 gchar
*content
, **split_content
, *cur
, **cur_split
, *rewrite
;
67 GError
*err_set
, *err_get
;
70 gboolean breaker
= TRUE
;
72 err_get
= err_set
= NULL
;
74 if(!g_file_get_contents(path
, &content
, NULL
, &err_get
))
77 split_content
= g_strsplit(content
, "\n", MAX_TOKENS
);
79 while(breaker
&& (cur
= split_content
[incr
]) && (cur_split
= g_strsplit(cur
, "=", 2))) {
81 if(!g_strcmp0(key
, cur_split
[0])) {
84 split_content
[incr
] = g_strjoinv("=", cur_split
);
94 rewrite
= g_strjoinv("\n", split_content
);
95 ret
= g_file_set_contents(path
, rewrite
, -1, &err_set
);
100 g_strfreev(cur_split
);
102 g_strfreev(split_content
);
109 static gboolean
is_valid_action(GList
*action_list
, const gchar
*action
) {
111 PolkitActionDescription
*action_descr
;
112 const gchar
*action_descr_id
;
117 cur
= g_list_first(action_list
);
119 while(cur
&& (action_descr
= ((PolkitActionDescription
*)(cur
->data
))) && (action_descr_id
= polkit_action_description_get_action_id(action_descr
))) {
121 if(!g_strcmp0(action
, action_descr_id
)) {
129 g_list_free(action_list
);
134 check_auth_result
polkit_try_auth(const gchar
*bus
, const gchar
*action
, gboolean prompt
) {
136 GList
*valid_actions
;
137 PolkitAuthority
*auth
;
139 PolkitAuthorizationResult
*result
;
140 PolkitCheckAuthorizationFlags prompt_flag
;
141 gboolean authorized
, challenge
;
146 valid_actions
= NULL
;
147 authorized
= challenge
= FALSE
;
148 prompt_flag
= prompt
? POLKIT_CHECK_AUTHORIZATION_FLAGS_ALLOW_USER_INTERACTION
: POLKIT_CHECK_AUTHORIZATION_FLAGS_NONE
;
150 auth
= polkit_authority_get_sync(NULL
, NULL
); /* TODO timeout for this */
151 subj
= polkit_system_bus_name_new(bus
);
152 valid_actions
= polkit_authority_enumerate_actions_sync(auth
, NULL
, NULL
);
154 if(!auth
|| !valid_actions
)
155 return ERROR_GENERIC
; /* extremely unlikely */
158 else if(!is_valid_action(valid_actions
, action
))
159 return ERROR_BADACTION
;
161 if(!(result
= polkit_authority_check_authorization_sync(auth
, subj
, action
, NULL
, prompt_flag
, NULL
, NULL
)))
162 return ERROR_GENERIC
; /* TODO pass, check gerror and return more relevant error */
164 authorized
= polkit_authorization_result_get_is_authorized(result
);
165 challenge
= polkit_authorization_result_get_is_challenge(result
);
167 /* free()'s before return */
169 g_object_unref(auth
);
171 g_object_unref(subj
);
173 g_object_unref(result
);
178 return AUTHORIZED_BY_PROMPT
;
180 return AUTHORIZED_NATIVELY
;
183 return UNAUTHORIZED_FAILED_PROMPT
;
185 return UNAUTHORIZED_NATIVELY
;