<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN"> <html><head><meta http-equiv="Content-Type" content="text/html;charset=iso-8859-1"> <title>policy.c Source File</title> <link href="doxygen.css" rel="stylesheet" type="text/css"> </head><body> <!-- Generated by Doxygen 1.2.15 --> <center> <a class="qindex" href="index.html">Main Page</a> <a class="qindex" href="modules.html">Modules</a> <a class="qindex" href="annotated.html">Data Structures</a> <a class="qindex" href="files.html">File List</a> <a class="qindex" href="functions.html">Data Fields</a> <a class="qindex" href="pages.html">Related Pages</a> </center> <hr><h1>policy.c</h1><div class="fragment"><pre>00001 <font class="comment">/* -*- mode: C; c-file-style: "gnu" -*- */</font> 00002 <font class="comment">/* policy.c Bus security policy</font> 00003 <font class="comment"> *</font> 00004 <font class="comment"> * Copyright (C) 2003 Red Hat, Inc.</font> 00005 <font class="comment"> *</font> 00006 <font class="comment"> * Licensed under the Academic Free License version 1.2</font> 00007 <font class="comment"> * </font> 00008 <font class="comment"> * This program is free software; you can redistribute it and/or modify</font> 00009 <font class="comment"> * it under the terms of the GNU General Public License as published by</font> 00010 <font class="comment"> * the Free Software Foundation; either version 2 of the License, or</font> 00011 <font class="comment"> * (at your option) any later version.</font> 00012 <font class="comment"> *</font> 00013 <font class="comment"> * This program is distributed in the hope that it will be useful,</font> 00014 <font class="comment"> * but WITHOUT ANY WARRANTY; without even the implied warranty of</font> 00015 <font class="comment"> * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the</font> 00016 <font class="comment"> * GNU General Public License for more details.</font> 00017 <font class="comment"> * </font> 00018 <font class="comment"> * You should have received a copy of the GNU General Public License</font> 00019 <font class="comment"> * along with this program; if not, write to the Free Software</font> 00020 <font class="comment"> * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA</font> 00021 <font class="comment"> *</font> 00022 <font class="comment"> */</font> 00023 00024 <font class="preprocessor">#include "policy.h"</font> 00025 <font class="preprocessor">#include "services.h"</font> 00026 <font class="preprocessor">#include "test.h"</font> 00027 <font class="preprocessor">#include "utils.h"</font> 00028 <font class="preprocessor">#include <dbus/dbus-list.h></font> 00029 <font class="preprocessor">#include <dbus/dbus-hash.h></font> 00030 <font class="preprocessor">#include <dbus/dbus-internals.h></font> 00031 00032 BusPolicyRule* 00033 bus_policy_rule_new (BusPolicyRuleType type, 00034 dbus_bool_t allow) 00035 { 00036 BusPolicyRule *rule; 00037 00038 rule = dbus_new0 (BusPolicyRule, 1); 00039 <font class="keywordflow">if</font> (rule == NULL) 00040 <font class="keywordflow">return</font> NULL; 00041 00042 rule->type = type; 00043 rule->refcount = 1; 00044 rule->allow = allow; 00045 00046 <font class="keywordflow">switch</font> (rule->type) 00047 { 00048 <font class="keywordflow">case</font> BUS_POLICY_RULE_USER: 00049 rule->d.user.uid = DBUS_UID_UNSET; 00050 <font class="keywordflow">break</font>; 00051 <font class="keywordflow">case</font> BUS_POLICY_RULE_GROUP: 00052 rule->d.group.gid = DBUS_GID_UNSET; 00053 <font class="keywordflow">break</font>; 00054 <font class="keywordflow">case</font> BUS_POLICY_RULE_SEND: 00055 rule->d.send.message_type = DBUS_MESSAGE_TYPE_INVALID; 00056 <font class="keywordflow">break</font>; 00057 <font class="keywordflow">case</font> BUS_POLICY_RULE_RECEIVE: 00058 rule->d.receive.message_type = DBUS_MESSAGE_TYPE_INVALID; 00059 <font class="keywordflow">break</font>; 00060 <font class="keywordflow">case</font> BUS_POLICY_RULE_OWN: 00061 <font class="keywordflow">break</font>; 00062 } 00063 00064 <font class="keywordflow">return</font> rule; 00065 } 00066 00067 <font class="keywordtype">void</font> 00068 bus_policy_rule_ref (BusPolicyRule *rule) 00069 { 00070 _dbus_assert (rule->refcount > 0); 00071 00072 rule->refcount += 1; 00073 } 00074 00075 <font class="keywordtype">void</font> 00076 bus_policy_rule_unref (BusPolicyRule *rule) 00077 { 00078 _dbus_assert (rule->refcount > 0); 00079 00080 rule->refcount -= 1; 00081 00082 <font class="keywordflow">if</font> (rule->refcount == 0) 00083 { 00084 <font class="keywordflow">switch</font> (rule->type) 00085 { 00086 <font class="keywordflow">case</font> BUS_POLICY_RULE_SEND: 00087 dbus_free (rule->d.send.path); 00088 dbus_free (rule->d.send.interface); 00089 dbus_free (rule->d.send.member); 00090 dbus_free (rule->d.send.error); 00091 dbus_free (rule->d.send.destination); 00092 <font class="keywordflow">break</font>; 00093 <font class="keywordflow">case</font> BUS_POLICY_RULE_RECEIVE: 00094 dbus_free (rule->d.receive.path); 00095 dbus_free (rule->d.receive.interface); 00096 dbus_free (rule->d.receive.member); 00097 dbus_free (rule->d.receive.error); 00098 dbus_free (rule->d.receive.origin); 00099 <font class="keywordflow">break</font>; 00100 <font class="keywordflow">case</font> BUS_POLICY_RULE_OWN: 00101 dbus_free (rule->d.own.service_name); 00102 <font class="keywordflow">break</font>; 00103 <font class="keywordflow">case</font> BUS_POLICY_RULE_USER: 00104 <font class="keywordflow">break</font>; 00105 <font class="keywordflow">case</font> BUS_POLICY_RULE_GROUP: 00106 <font class="keywordflow">break</font>; 00107 } 00108 00109 dbus_free (rule); 00110 } 00111 } 00112 00113 <font class="keyword">struct </font>BusPolicy 00114 { 00115 <font class="keywordtype">int</font> refcount; 00116 00117 <a class="code" href="structDBusList.html">DBusList</a> *default_rules; 00118 <a class="code" href="structDBusList.html">DBusList</a> *mandatory_rules; 00119 <a class="code" href="structDBusHashTable.html">DBusHashTable</a> *rules_by_uid; 00120 <a class="code" href="structDBusHashTable.html">DBusHashTable</a> *rules_by_gid; 00121 }; 00122 00123 <font class="keyword">static</font> <font class="keywordtype">void</font> 00124 free_rule_func (<font class="keywordtype">void</font> *data, 00125 <font class="keywordtype">void</font> *user_data) 00126 { 00127 BusPolicyRule *rule = data; 00128 00129 bus_policy_rule_unref (rule); 00130 } 00131 00132 <font class="keyword">static</font> <font class="keywordtype">void</font> 00133 free_rule_list_func (<font class="keywordtype">void</font> *data) 00134 { 00135 <a class="code" href="structDBusList.html">DBusList</a> **list = data; 00136 00137 <font class="keywordflow">if</font> (list == NULL) <font class="comment">/* DBusHashTable is on crack */</font> 00138 <font class="keywordflow">return</font>; 00139 00140 _dbus_list_foreach (list, free_rule_func, NULL); 00141 00142 _dbus_list_clear (list); 00143 00144 dbus_free (list); 00145 } 00146 00147 BusPolicy* 00148 bus_policy_new (<font class="keywordtype">void</font>) 00149 { 00150 BusPolicy *policy; 00151 00152 policy = dbus_new0 (BusPolicy, 1); 00153 <font class="keywordflow">if</font> (policy == NULL) 00154 <font class="keywordflow">return</font> NULL; 00155 00156 policy->refcount = 1; 00157 00158 policy->rules_by_uid = _dbus_hash_table_new (DBUS_HASH_ULONG, 00159 NULL, 00160 free_rule_list_func); 00161 <font class="keywordflow">if</font> (policy->rules_by_uid == NULL) 00162 <font class="keywordflow">goto</font> failed; 00163 00164 policy->rules_by_gid = _dbus_hash_table_new (DBUS_HASH_ULONG, 00165 NULL, 00166 free_rule_list_func); 00167 <font class="keywordflow">if</font> (policy->rules_by_gid == NULL) 00168 <font class="keywordflow">goto</font> failed; 00169 00170 <font class="keywordflow">return</font> policy; 00171 00172 failed: 00173 bus_policy_unref (policy); 00174 <font class="keywordflow">return</font> NULL; 00175 } 00176 00177 <font class="keywordtype">void</font> 00178 bus_policy_ref (BusPolicy *policy) 00179 { 00180 _dbus_assert (policy->refcount > 0); 00181 00182 policy->refcount += 1; 00183 } 00184 00185 <font class="keywordtype">void</font> 00186 bus_policy_unref (BusPolicy *policy) 00187 { 00188 _dbus_assert (policy->refcount > 0); 00189 00190 policy->refcount -= 1; 00191 00192 <font class="keywordflow">if</font> (policy->refcount == 0) 00193 { 00194 _dbus_list_foreach (&policy->default_rules, free_rule_func, NULL); 00195 _dbus_list_clear (&policy->default_rules); 00196 00197 _dbus_list_foreach (&policy->mandatory_rules, free_rule_func, NULL); 00198 _dbus_list_clear (&policy->mandatory_rules); 00199 00200 <font class="keywordflow">if</font> (policy->rules_by_uid) 00201 { 00202 _dbus_hash_table_unref (policy->rules_by_uid); 00203 policy->rules_by_uid = NULL; 00204 } 00205 00206 <font class="keywordflow">if</font> (policy->rules_by_gid) 00207 { 00208 _dbus_hash_table_unref (policy->rules_by_gid); 00209 policy->rules_by_gid = NULL; 00210 } 00211 00212 dbus_free (policy); 00213 } 00214 } 00215 00216 <font class="keyword">static</font> dbus_bool_t 00217 add_list_to_client (<a class="code" href="structDBusList.html">DBusList</a> **list, 00218 BusClientPolicy *client) 00219 { 00220 <a class="code" href="structDBusList.html">DBusList</a> *link; 00221 00222 link = _dbus_list_get_first_link (list); 00223 <font class="keywordflow">while</font> (link != NULL) 00224 { 00225 BusPolicyRule *rule = link-><a class="code" href="structDBusList.html#m2">data</a>; 00226 link = _dbus_list_get_next_link (list, link); 00227 00228 <font class="keywordflow">switch</font> (rule->type) 00229 { 00230 <font class="keywordflow">case</font> BUS_POLICY_RULE_USER: 00231 <font class="keywordflow">case</font> BUS_POLICY_RULE_GROUP: 00232 <font class="comment">/* These aren't per-connection policies */</font> 00233 <font class="keywordflow">break</font>; 00234 00235 <font class="keywordflow">case</font> BUS_POLICY_RULE_OWN: 00236 <font class="keywordflow">case</font> BUS_POLICY_RULE_SEND: 00237 <font class="keywordflow">case</font> BUS_POLICY_RULE_RECEIVE: 00238 <font class="comment">/* These are per-connection */</font> 00239 <font class="keywordflow">if</font> (!bus_client_policy_append_rule (client, rule)) 00240 <font class="keywordflow">return</font> FALSE; 00241 <font class="keywordflow">break</font>; 00242 } 00243 } 00244 00245 <font class="keywordflow">return</font> TRUE; 00246 } 00247 00248 BusClientPolicy* 00249 bus_policy_create_client_policy (BusPolicy *policy, 00250 <a class="code" href="structDBusConnection.html">DBusConnection</a> *connection, 00251 <a class="code" href="structDBusError.html">DBusError</a> *error) 00252 { 00253 BusClientPolicy *client; 00254 <font class="keywordtype">unsigned</font> <font class="keywordtype">long</font> uid; 00255 00256 _dbus_assert (dbus_connection_get_is_authenticated (connection)); 00257 _DBUS_ASSERT_ERROR_IS_CLEAR (error); 00258 00259 client = bus_client_policy_new (); 00260 <font class="keywordflow">if</font> (client == NULL) 00261 <font class="keywordflow">goto</font> nomem; 00262 00263 <font class="keywordflow">if</font> (!add_list_to_client (&policy->default_rules, 00264 client)) 00265 <font class="keywordflow">goto</font> nomem; 00266 00267 <font class="comment">/* we avoid the overhead of looking up user's groups</font> 00268 <font class="comment"> * if we don't have any group rules anyway</font> 00269 <font class="comment"> */</font> 00270 <font class="keywordflow">if</font> (_dbus_hash_table_get_n_entries (policy->rules_by_gid) > 0) 00271 { 00272 <font class="keywordtype">unsigned</font> <font class="keywordtype">long</font> *groups; 00273 <font class="keywordtype">int</font> n_groups; 00274 <font class="keywordtype">int</font> i; 00275 00276 <font class="keywordflow">if</font> (!bus_connection_get_groups (connection, &groups, &n_groups, error)) 00277 <font class="keywordflow">goto</font> failed; 00278 00279 i = 0; 00280 <font class="keywordflow">while</font> (i < n_groups) 00281 { 00282 <a class="code" href="structDBusList.html">DBusList</a> **list; 00283 00284 list = _dbus_hash_table_lookup_ulong (policy->rules_by_gid, 00285 groups[i]); 00286 00287 <font class="keywordflow">if</font> (list != NULL) 00288 { 00289 <font class="keywordflow">if</font> (!add_list_to_client (list, client)) 00290 { 00291 dbus_free (groups); 00292 <font class="keywordflow">goto</font> nomem; 00293 } 00294 } 00295 00296 ++i; 00297 } 00298 00299 dbus_free (groups); 00300 } 00301 00302 <font class="keywordflow">if</font> (!dbus_connection_get_unix_user (connection, &uid)) 00303 { 00304 dbus_set_error (error, DBUS_ERROR_FAILED, 00305 <font class="stringliteral">"No user ID known for connection, cannot determine security policy\n"</font>); 00306 <font class="keywordflow">goto</font> failed; 00307 } 00308 00309 <font class="keywordflow">if</font> (_dbus_hash_table_get_n_entries (policy->rules_by_uid) > 0) 00310 { 00311 <a class="code" href="structDBusList.html">DBusList</a> **list; 00312 00313 list = _dbus_hash_table_lookup_ulong (policy->rules_by_uid, 00314 uid); 00315 00316 <font class="keywordflow">if</font> (list != NULL) 00317 { 00318 <font class="keywordflow">if</font> (!add_list_to_client (list, client)) 00319 <font class="keywordflow">goto</font> nomem; 00320 } 00321 } 00322 00323 <font class="keywordflow">if</font> (!add_list_to_client (&policy->mandatory_rules, 00324 client)) 00325 <font class="keywordflow">goto</font> nomem; 00326 00327 bus_client_policy_optimize (client); 00328 00329 <font class="keywordflow">return</font> client; 00330 00331 nomem: 00332 BUS_SET_OOM (error); 00333 failed: 00334 _DBUS_ASSERT_ERROR_IS_SET (error); 00335 <font class="keywordflow">if</font> (client) 00336 bus_client_policy_unref (client); 00337 <font class="keywordflow">return</font> NULL; 00338 } 00339 00340 <font class="keyword">static</font> dbus_bool_t 00341 list_allows_user (dbus_bool_t def, 00342 <a class="code" href="structDBusList.html">DBusList</a> **list, 00343 <font class="keywordtype">unsigned</font> <font class="keywordtype">long</font> uid, 00344 <font class="keyword">const</font> <font class="keywordtype">unsigned</font> <font class="keywordtype">long</font> *group_ids, 00345 <font class="keywordtype">int</font> n_group_ids) 00346 { 00347 <a class="code" href="structDBusList.html">DBusList</a> *link; 00348 dbus_bool_t allowed; 00349 00350 allowed = def; 00351 00352 link = _dbus_list_get_first_link (list); 00353 <font class="keywordflow">while</font> (link != NULL) 00354 { 00355 BusPolicyRule *rule = link-><a class="code" href="structDBusList.html#m2">data</a>; 00356 link = _dbus_list_get_next_link (list, link); 00357 00358 <font class="keywordflow">if</font> (rule->type == BUS_POLICY_RULE_USER) 00359 { 00360 _dbus_verbose (<font class="stringliteral">"List %p user rule uid="</font>DBUS_UID_FORMAT<font class="stringliteral">"\n"</font>, 00361 list, rule->d.user.uid); 00362 00363 <font class="keywordflow">if</font> (rule->d.user.uid == DBUS_UID_UNSET) 00364 ; <font class="comment">/* '*' wildcard */</font> 00365 <font class="keywordflow">else</font> <font class="keywordflow">if</font> (rule->d.user.uid != uid) 00366 <font class="keywordflow">continue</font>; 00367 } 00368 <font class="keywordflow">else</font> <font class="keywordflow">if</font> (rule->type == BUS_POLICY_RULE_GROUP) 00369 { 00370 _dbus_verbose (<font class="stringliteral">"List %p group rule uid="</font>DBUS_UID_FORMAT<font class="stringliteral">"\n"</font>, 00371 list, rule->d.user.uid); 00372 00373 <font class="keywordflow">if</font> (rule->d.group.gid == DBUS_GID_UNSET) 00374 ; <font class="comment">/* '*' wildcard */</font> 00375 <font class="keywordflow">else</font> 00376 { 00377 <font class="keywordtype">int</font> i; 00378 00379 i = 0; 00380 <font class="keywordflow">while</font> (i < n_group_ids) 00381 { 00382 <font class="keywordflow">if</font> (rule->d.group.gid == group_ids[i]) 00383 <font class="keywordflow">break</font>; 00384 ++i; 00385 } 00386 00387 <font class="keywordflow">if</font> (i == n_group_ids) 00388 <font class="keywordflow">continue</font>; 00389 } 00390 } 00391 <font class="keywordflow">else</font> 00392 <font class="keywordflow">continue</font>; 00393 00394 allowed = rule->allow; 00395 } 00396 00397 <font class="keywordflow">return</font> allowed; 00398 } 00399 00400 dbus_bool_t 00401 bus_policy_allow_user (BusPolicy *policy, 00402 <a class="code" href="structDBusUserDatabase.html">DBusUserDatabase</a> *user_database, 00403 <font class="keywordtype">unsigned</font> <font class="keywordtype">long</font> uid) 00404 { 00405 dbus_bool_t allowed; 00406 <font class="keywordtype">unsigned</font> <font class="keywordtype">long</font> *group_ids; 00407 <font class="keywordtype">int</font> n_group_ids; 00408 00409 <font class="comment">/* On OOM or error we always reject the user */</font> 00410 <font class="keywordflow">if</font> (!_dbus_user_database_get_groups (user_database, 00411 uid, &group_ids, &n_group_ids, NULL)) 00412 { 00413 _dbus_verbose (<font class="stringliteral">"Did not get any groups for UID %lu\n"</font>, 00414 uid); 00415 <font class="keywordflow">return</font> FALSE; 00416 } 00417 00418 allowed = FALSE; 00419 00420 allowed = list_allows_user (allowed, 00421 &policy->default_rules, 00422 uid, 00423 group_ids, n_group_ids); 00424 00425 allowed = list_allows_user (allowed, 00426 &policy->mandatory_rules, 00427 uid, 00428 group_ids, n_group_ids); 00429 00430 dbus_free (group_ids); 00431 00432 _dbus_verbose (<font class="stringliteral">"UID %lu allowed = %d\n"</font>, uid, allowed); 00433 00434 <font class="keywordflow">return</font> allowed; 00435 } 00436 00437 dbus_bool_t 00438 bus_policy_append_default_rule (BusPolicy *policy, 00439 BusPolicyRule *rule) 00440 { 00441 <font class="keywordflow">if</font> (!_dbus_list_append (&policy->default_rules, rule)) 00442 <font class="keywordflow">return</font> FALSE; 00443 00444 bus_policy_rule_ref (rule); 00445 00446 <font class="keywordflow">return</font> TRUE; 00447 } 00448 00449 dbus_bool_t 00450 bus_policy_append_mandatory_rule (BusPolicy *policy, 00451 BusPolicyRule *rule) 00452 { 00453 <font class="keywordflow">if</font> (!_dbus_list_append (&policy->mandatory_rules, rule)) 00454 <font class="keywordflow">return</font> FALSE; 00455 00456 bus_policy_rule_ref (rule); 00457 00458 <font class="keywordflow">return</font> TRUE; 00459 } 00460 00461 <font class="keyword">static</font> <a class="code" href="structDBusList.html">DBusList</a>** 00462 get_list (<a class="code" href="structDBusHashTable.html">DBusHashTable</a> *hash, 00463 <font class="keywordtype">unsigned</font> <font class="keywordtype">long</font> key) 00464 { 00465 <a class="code" href="structDBusList.html">DBusList</a> **list; 00466 00467 list = _dbus_hash_table_lookup_ulong (hash, key); 00468 00469 <font class="keywordflow">if</font> (list == NULL) 00470 { 00471 list = dbus_new0 (<a class="code" href="structDBusList.html">DBusList</a>*, 1); 00472 <font class="keywordflow">if</font> (list == NULL) 00473 <font class="keywordflow">return</font> NULL; 00474 00475 <font class="keywordflow">if</font> (!_dbus_hash_table_insert_ulong (hash, key, list)) 00476 { 00477 dbus_free (list); 00478 <font class="keywordflow">return</font> NULL; 00479 } 00480 } 00481 00482 <font class="keywordflow">return</font> list; 00483 } 00484 00485 dbus_bool_t 00486 bus_policy_append_user_rule (BusPolicy *policy, 00487 dbus_uid_t uid, 00488 BusPolicyRule *rule) 00489 { 00490 <a class="code" href="structDBusList.html">DBusList</a> **list; 00491 00492 list = get_list (policy->rules_by_uid, uid); 00493 00494 <font class="keywordflow">if</font> (list == NULL) 00495 <font class="keywordflow">return</font> FALSE; 00496 00497 <font class="keywordflow">if</font> (!_dbus_list_append (list, rule)) 00498 <font class="keywordflow">return</font> FALSE; 00499 00500 bus_policy_rule_ref (rule); 00501 00502 <font class="keywordflow">return</font> TRUE; 00503 } 00504 00505 dbus_bool_t 00506 bus_policy_append_group_rule (BusPolicy *policy, 00507 dbus_gid_t gid, 00508 BusPolicyRule *rule) 00509 { 00510 <a class="code" href="structDBusList.html">DBusList</a> **list; 00511 00512 list = get_list (policy->rules_by_gid, gid); 00513 00514 <font class="keywordflow">if</font> (list == NULL) 00515 <font class="keywordflow">return</font> FALSE; 00516 00517 <font class="keywordflow">if</font> (!_dbus_list_append (list, rule)) 00518 <font class="keywordflow">return</font> FALSE; 00519 00520 bus_policy_rule_ref (rule); 00521 00522 <font class="keywordflow">return</font> TRUE; 00523 } 00524 00525 <font class="keyword">static</font> dbus_bool_t 00526 append_copy_of_policy_list (<a class="code" href="structDBusList.html">DBusList</a> **list, 00527 <a class="code" href="structDBusList.html">DBusList</a> **to_append) 00528 { 00529 <a class="code" href="structDBusList.html">DBusList</a> *link; 00530 <a class="code" href="structDBusList.html">DBusList</a> *tmp_list; 00531 00532 tmp_list = NULL; 00533 00534 <font class="comment">/* Preallocate all our links */</font> 00535 link = _dbus_list_get_first_link (to_append); 00536 <font class="keywordflow">while</font> (link != NULL) 00537 { 00538 <font class="keywordflow">if</font> (!_dbus_list_append (&tmp_list, link-><a class="code" href="structDBusList.html#m2">data</a>)) 00539 { 00540 _dbus_list_clear (&tmp_list); 00541 <font class="keywordflow">return</font> FALSE; 00542 } 00543 00544 link = _dbus_list_get_next_link (to_append, link); 00545 } 00546 00547 <font class="comment">/* Now append them */</font> 00548 <font class="keywordflow">while</font> ((link = _dbus_list_pop_first_link (&tmp_list))) 00549 { 00550 bus_policy_rule_ref (link-><a class="code" href="structDBusList.html#m2">data</a>); 00551 _dbus_list_append_link (list, link); 00552 } 00553 00554 <font class="keywordflow">return</font> TRUE; 00555 } 00556 00557 <font class="keyword">static</font> dbus_bool_t 00558 merge_id_hash (<a class="code" href="structDBusHashTable.html">DBusHashTable</a> *dest, 00559 <a class="code" href="structDBusHashTable.html">DBusHashTable</a> *to_absorb) 00560 { 00561 <a class="code" href="structDBusHashIter.html">DBusHashIter</a> iter; 00562 00563 _dbus_hash_iter_init (to_absorb, &iter); 00564 <font class="keywordflow">while</font> (_dbus_hash_iter_next (&iter)) 00565 { 00566 <font class="keywordtype">unsigned</font> <font class="keywordtype">long</font> id = _dbus_hash_iter_get_ulong_key (&iter); 00567 <a class="code" href="structDBusList.html">DBusList</a> **list = _dbus_hash_iter_get_value (&iter); 00568 <a class="code" href="structDBusList.html">DBusList</a> **target = get_list (dest, id); 00569 00570 <font class="keywordflow">if</font> (target == NULL) 00571 <font class="keywordflow">return</font> FALSE; 00572 00573 <font class="keywordflow">if</font> (!append_copy_of_policy_list (target, list)) 00574 <font class="keywordflow">return</font> FALSE; 00575 } 00576 00577 <font class="keywordflow">return</font> TRUE; 00578 } 00579 00580 dbus_bool_t 00581 bus_policy_merge (BusPolicy *policy, 00582 BusPolicy *to_absorb) 00583 { 00584 <font class="comment">/* Not properly atomic, but as used for configuration files</font> 00585 <font class="comment"> * we don't rely on it.</font> 00586 <font class="comment"> */</font> 00587 <font class="keywordflow">if</font> (!append_copy_of_policy_list (&policy->default_rules, 00588 &to_absorb->default_rules)) 00589 <font class="keywordflow">return</font> FALSE; 00590 00591 <font class="keywordflow">if</font> (!append_copy_of_policy_list (&policy->mandatory_rules, 00592 &to_absorb->mandatory_rules)) 00593 <font class="keywordflow">return</font> FALSE; 00594 00595 <font class="keywordflow">if</font> (!merge_id_hash (policy->rules_by_uid, 00596 to_absorb->rules_by_uid)) 00597 <font class="keywordflow">return</font> FALSE; 00598 00599 <font class="keywordflow">if</font> (!merge_id_hash (policy->rules_by_gid, 00600 to_absorb->rules_by_gid)) 00601 <font class="keywordflow">return</font> FALSE; 00602 00603 <font class="keywordflow">return</font> TRUE; 00604 } 00605 00606 <font class="keyword">struct </font>BusClientPolicy 00607 { 00608 <font class="keywordtype">int</font> refcount; 00609 00610 <a class="code" href="structDBusList.html">DBusList</a> *rules; 00611 }; 00612 00613 BusClientPolicy* 00614 bus_client_policy_new (<font class="keywordtype">void</font>) 00615 { 00616 BusClientPolicy *policy; 00617 00618 policy = dbus_new0 (BusClientPolicy, 1); 00619 <font class="keywordflow">if</font> (policy == NULL) 00620 <font class="keywordflow">return</font> NULL; 00621 00622 policy->refcount = 1; 00623 00624 <font class="keywordflow">return</font> policy; 00625 } 00626 00627 <font class="keywordtype">void</font> 00628 bus_client_policy_ref (BusClientPolicy *policy) 00629 { 00630 _dbus_assert (policy->refcount > 0); 00631 00632 policy->refcount += 1; 00633 } 00634 00635 <font class="keyword">static</font> <font class="keywordtype">void</font> 00636 rule_unref_foreach (<font class="keywordtype">void</font> *data, 00637 <font class="keywordtype">void</font> *user_data) 00638 { 00639 BusPolicyRule *rule = data; 00640 00641 bus_policy_rule_unref (rule); 00642 } 00643 00644 <font class="keywordtype">void</font> 00645 bus_client_policy_unref (BusClientPolicy *policy) 00646 { 00647 _dbus_assert (policy->refcount > 0); 00648 00649 policy->refcount -= 1; 00650 00651 <font class="keywordflow">if</font> (policy->refcount == 0) 00652 { 00653 _dbus_list_foreach (&policy->rules, 00654 rule_unref_foreach, 00655 NULL); 00656 00657 _dbus_list_clear (&policy->rules); 00658 00659 dbus_free (policy); 00660 } 00661 } 00662 00663 <font class="keyword">static</font> <font class="keywordtype">void</font> 00664 remove_rules_by_type_up_to (BusClientPolicy *policy, 00665 BusPolicyRuleType type, 00666 <a class="code" href="structDBusList.html">DBusList</a> *up_to) 00667 { 00668 <a class="code" href="structDBusList.html">DBusList</a> *link; 00669 00670 link = _dbus_list_get_first_link (&policy->rules); 00671 <font class="keywordflow">while</font> (link != up_to) 00672 { 00673 BusPolicyRule *rule = link-><a class="code" href="structDBusList.html#m2">data</a>; 00674 <a class="code" href="structDBusList.html">DBusList</a> *next = _dbus_list_get_next_link (&policy->rules, link); 00675 00676 <font class="keywordflow">if</font> (rule->type == type) 00677 { 00678 _dbus_list_remove_link (&policy->rules, link); 00679 bus_policy_rule_unref (rule); 00680 } 00681 00682 link = next; 00683 } 00684 } 00685 00686 <font class="keywordtype">void</font> 00687 bus_client_policy_optimize (BusClientPolicy *policy) 00688 { 00689 <a class="code" href="structDBusList.html">DBusList</a> *link; 00690 00691 <font class="comment">/* The idea here is that if we have:</font> 00692 <font class="comment"> * </font> 00693 <font class="comment"> * <allow send_interface="foo.bar"/></font> 00694 <font class="comment"> * <deny send_interface="*"/></font> 00695 <font class="comment"> *</font> 00696 <font class="comment"> * (for example) the deny will always override the allow. So we</font> 00697 <font class="comment"> * delete the allow. Ditto for deny followed by allow, etc. This is</font> 00698 <font class="comment"> * a dumb thing to put in a config file, but the <include> feature</font> 00699 <font class="comment"> * of files allows for an "inheritance and override" pattern where</font> 00700 <font class="comment"> * it could make sense. If an included file wants to "start over"</font> 00701 <font class="comment"> * with a blanket deny, no point keeping the rules from the parent</font> 00702 <font class="comment"> * file.</font> 00703 <font class="comment"> */</font> 00704 00705 _dbus_verbose (<font class="stringliteral">"Optimizing policy with %d rules\n"</font>, 00706 _dbus_list_get_length (&policy->rules)); 00707 00708 link = _dbus_list_get_first_link (&policy->rules); 00709 <font class="keywordflow">while</font> (link != NULL) 00710 { 00711 BusPolicyRule *rule; 00712 <a class="code" href="structDBusList.html">DBusList</a> *next; 00713 dbus_bool_t remove_preceding; 00714 00715 next = _dbus_list_get_next_link (&policy->rules, link); 00716 rule = link-><a class="code" href="structDBusList.html#m2">data</a>; 00717 00718 remove_preceding = FALSE; 00719 00720 _dbus_assert (rule != NULL); 00721 00722 <font class="keywordflow">switch</font> (rule->type) 00723 { 00724 <font class="keywordflow">case</font> BUS_POLICY_RULE_SEND: 00725 remove_preceding = 00726 rule->d.send.message_type == DBUS_MESSAGE_TYPE_INVALID && 00727 rule->d.send.path == NULL && 00728 rule->d.send.interface == NULL && 00729 rule->d.send.member == NULL && 00730 rule->d.send.error == NULL && 00731 rule->d.send.destination == NULL; 00732 <font class="keywordflow">break</font>; 00733 <font class="keywordflow">case</font> BUS_POLICY_RULE_RECEIVE: 00734 remove_preceding = 00735 rule->d.receive.message_type == DBUS_MESSAGE_TYPE_INVALID && 00736 rule->d.receive.path == NULL && 00737 rule->d.receive.interface == NULL && 00738 rule->d.receive.member == NULL && 00739 rule->d.receive.error == NULL && 00740 rule->d.receive.origin == NULL; 00741 <font class="keywordflow">break</font>; 00742 <font class="keywordflow">case</font> BUS_POLICY_RULE_OWN: 00743 remove_preceding = 00744 rule->d.own.service_name == NULL; 00745 <font class="keywordflow">break</font>; 00746 <font class="keywordflow">case</font> BUS_POLICY_RULE_USER: 00747 <font class="keywordflow">case</font> BUS_POLICY_RULE_GROUP: 00748 _dbus_assert_not_reached (<font class="stringliteral">"invalid rule"</font>); 00749 <font class="keywordflow">break</font>; 00750 } 00751 00752 <font class="keywordflow">if</font> (remove_preceding) 00753 remove_rules_by_type_up_to (policy, rule->type, 00754 link); 00755 00756 link = next; 00757 } 00758 00759 _dbus_verbose (<font class="stringliteral">"After optimization, policy has %d rules\n"</font>, 00760 _dbus_list_get_length (&policy->rules)); 00761 } 00762 00763 dbus_bool_t 00764 bus_client_policy_append_rule (BusClientPolicy *policy, 00765 BusPolicyRule *rule) 00766 { 00767 _dbus_verbose (<font class="stringliteral">"Appending rule %p with type %d to policy %p\n"</font>, 00768 rule, rule->type, policy); 00769 00770 <font class="keywordflow">if</font> (!_dbus_list_append (&policy->rules, rule)) 00771 <font class="keywordflow">return</font> FALSE; 00772 00773 bus_policy_rule_ref (rule); 00774 00775 <font class="keywordflow">return</font> TRUE; 00776 } 00777 00778 dbus_bool_t 00779 bus_client_policy_check_can_send (BusClientPolicy *policy, 00780 BusRegistry *registry, 00781 <a class="code" href="structDBusConnection.html">DBusConnection</a> *receiver, 00782 <a class="code" href="structDBusMessage.html">DBusMessage</a> *message) 00783 { 00784 <a class="code" href="structDBusList.html">DBusList</a> *link; 00785 dbus_bool_t allowed; 00786 00787 <font class="comment">/* policy->rules is in the order the rules appeared</font> 00788 <font class="comment"> * in the config file, i.e. last rule that applies wins</font> 00789 <font class="comment"> */</font> 00790 00791 _dbus_verbose (<font class="stringliteral">" (policy) checking send rules\n"</font>); 00792 00793 allowed = FALSE; 00794 link = _dbus_list_get_first_link (&policy->rules); 00795 <font class="keywordflow">while</font> (link != NULL) 00796 { 00797 BusPolicyRule *rule = link-><a class="code" href="structDBusList.html#m2">data</a>; 00798 00799 link = _dbus_list_get_next_link (&policy->rules, link); 00800 00801 <font class="comment">/* Rule is skipped if it specifies a different</font> 00802 <font class="comment"> * message name from the message, or a different</font> 00803 <font class="comment"> * destination from the message</font> 00804 <font class="comment"> */</font> 00805 00806 <font class="keywordflow">if</font> (rule->type != BUS_POLICY_RULE_SEND) 00807 { 00808 _dbus_verbose (<font class="stringliteral">" (policy) skipping non-send rule\n"</font>); 00809 <font class="keywordflow">continue</font>; 00810 } 00811 00812 <font class="keywordflow">if</font> (rule->d.send.message_type != DBUS_MESSAGE_TYPE_INVALID) 00813 { 00814 <font class="keywordflow">if</font> (dbus_message_get_type (message) != rule->d.send.message_type) 00815 { 00816 _dbus_verbose (<font class="stringliteral">" (policy) skipping rule for different message type\n"</font>); 00817 <font class="keywordflow">continue</font>; 00818 } 00819 } 00820 00821 <font class="keywordflow">if</font> (rule->d.send.path != NULL) 00822 { 00823 <font class="keywordflow">if</font> (dbus_message_get_path (message) != NULL && 00824 strcmp (dbus_message_get_path (message), 00825 rule->d.send.path) != 0) 00826 { 00827 _dbus_verbose (<font class="stringliteral">" (policy) skipping rule for different path\n"</font>); 00828 <font class="keywordflow">continue</font>; 00829 } 00830 } 00831 00832 <font class="keywordflow">if</font> (rule->d.send.interface != NULL) 00833 { 00834 <font class="keywordflow">if</font> (dbus_message_get_interface (message) != NULL && 00835 strcmp (dbus_message_get_interface (message), 00836 rule->d.send.interface) != 0) 00837 { 00838 _dbus_verbose (<font class="stringliteral">" (policy) skipping rule for different interface\n"</font>); 00839 <font class="keywordflow">continue</font>; 00840 } 00841 } 00842 00843 <font class="keywordflow">if</font> (rule->d.send.member != NULL) 00844 { 00845 <font class="keywordflow">if</font> (dbus_message_get_member (message) != NULL && 00846 strcmp (dbus_message_get_member (message), 00847 rule->d.send.member) != 0) 00848 { 00849 _dbus_verbose (<font class="stringliteral">" (policy) skipping rule for different member\n"</font>); 00850 <font class="keywordflow">continue</font>; 00851 } 00852 } 00853 00854 <font class="keywordflow">if</font> (rule->d.send.error != NULL) 00855 { 00856 <font class="keywordflow">if</font> (dbus_message_get_error_name (message) != NULL && 00857 strcmp (dbus_message_get_error_name (message), 00858 rule->d.send.error) != 0) 00859 { 00860 _dbus_verbose (<font class="stringliteral">" (policy) skipping rule for different error name\n"</font>); 00861 <font class="keywordflow">continue</font>; 00862 } 00863 } 00864 00865 <font class="keywordflow">if</font> (rule->d.send.destination != NULL) 00866 { 00867 <font class="comment">/* receiver can be NULL for messages that are sent to the</font> 00868 <font class="comment"> * message bus itself, we check the strings in that case as</font> 00869 <font class="comment"> * built-in services don't have a DBusConnection but messages</font> 00870 <font class="comment"> * to them have a destination service name.</font> 00871 <font class="comment"> */</font> 00872 <font class="keywordflow">if</font> (receiver == NULL) 00873 { 00874 <font class="keywordflow">if</font> (!dbus_message_has_destination (message, 00875 rule->d.send.destination)) 00876 { 00877 _dbus_verbose (<font class="stringliteral">" (policy) skipping rule because message dest is not %s\n"</font>, 00878 rule->d.send.destination); 00879 <font class="keywordflow">continue</font>; 00880 } 00881 } 00882 <font class="keywordflow">else</font> 00883 { 00884 <a class="code" href="structDBusString.html">DBusString</a> str; 00885 BusService *service; 00886 00887 _dbus_string_init_const (&str, rule->d.send.destination); 00888 00889 service = bus_registry_lookup (registry, &str); 00890 <font class="keywordflow">if</font> (service == NULL) 00891 { 00892 _dbus_verbose (<font class="stringliteral">" (policy) skipping rule because dest %s doesn't exist\n"</font>, 00893 rule->d.send.destination); 00894 <font class="keywordflow">continue</font>; 00895 } 00896 00897 <font class="keywordflow">if</font> (!bus_service_has_owner (service, receiver)) 00898 { 00899 _dbus_verbose (<font class="stringliteral">" (policy) skipping rule because dest %s isn't owned by receiver\n"</font>, 00900 rule->d.send.destination); 00901 <font class="keywordflow">continue</font>; 00902 } 00903 } 00904 } 00905 00906 <font class="comment">/* Use this rule */</font> 00907 allowed = rule->allow; 00908 00909 _dbus_verbose (<font class="stringliteral">" (policy) used rule, allow now = %d\n"</font>, 00910 allowed); 00911 } 00912 00913 <font class="keywordflow">return</font> allowed; 00914 } 00915 00916 dbus_bool_t 00917 bus_client_policy_check_can_receive (BusClientPolicy *policy, 00918 BusRegistry *registry, 00919 <a class="code" href="structDBusConnection.html">DBusConnection</a> *sender, 00920 <a class="code" href="structDBusConnection.html">DBusConnection</a> *addressed_recipient, 00921 <a class="code" href="structDBusConnection.html">DBusConnection</a> *proposed_recipient, 00922 <a class="code" href="structDBusMessage.html">DBusMessage</a> *message) 00923 { 00924 <a class="code" href="structDBusList.html">DBusList</a> *link; 00925 dbus_bool_t allowed; 00926 dbus_bool_t eavesdropping; 00927 00928 <font class="comment">/* NULL sender, proposed_recipient means the bus driver. NULL</font> 00929 <font class="comment"> * addressed_recipient means the message didn't specify an explicit</font> 00930 <font class="comment"> * target. If proposed_recipient is NULL, then addressed_recipient</font> 00931 <font class="comment"> * is also NULL but is implicitly the bus driver.</font> 00932 <font class="comment"> */</font> 00933 00934 _dbus_assert (proposed_recipient == NULL || 00935 (dbus_message_get_destination (message) == NULL || 00936 addressed_recipient != NULL)); 00937 00938 eavesdropping = 00939 (proposed_recipient == NULL || <font class="comment">/* explicitly to bus driver */</font> 00940 (addressed_recipient && addressed_recipient != proposed_recipient)); <font class="comment">/* explicitly to a different recipient */</font> 00941 00942 <font class="comment">/* policy->rules is in the order the rules appeared</font> 00943 <font class="comment"> * in the config file, i.e. last rule that applies wins</font> 00944 <font class="comment"> */</font> 00945 00946 _dbus_verbose (<font class="stringliteral">" (policy) checking receive rules, eavesdropping = %d\n"</font>, eavesdropping); 00947 00948 allowed = FALSE; 00949 link = _dbus_list_get_first_link (&policy->rules); 00950 <font class="keywordflow">while</font> (link != NULL) 00951 { 00952 BusPolicyRule *rule = link-><a class="code" href="structDBusList.html#m2">data</a>; 00953 00954 link = _dbus_list_get_next_link (&policy->rules, link); 00955 00956 <font class="keywordflow">if</font> (rule->type != BUS_POLICY_RULE_RECEIVE) 00957 { 00958 _dbus_verbose (<font class="stringliteral">" (policy) skipping non-receive rule\n"</font>); 00959 <font class="keywordflow">continue</font>; 00960 } 00961 00962 <font class="keywordflow">if</font> (rule->d.receive.message_type != DBUS_MESSAGE_TYPE_INVALID) 00963 { 00964 <font class="keywordflow">if</font> (dbus_message_get_type (message) != rule->d.receive.message_type) 00965 { 00966 _dbus_verbose (<font class="stringliteral">" (policy) skipping rule for different message type\n"</font>); 00967 <font class="keywordflow">continue</font>; 00968 } 00969 } 00970 00971 <font class="comment">/* for allow, eavesdrop=false means the rule doesn't apply when</font> 00972 <font class="comment"> * eavesdropping. eavesdrop=true means always allow.</font> 00973 <font class="comment"> */</font> 00974 <font class="keywordflow">if</font> (eavesdropping && rule->allow && !rule->d.receive.eavesdrop) 00975 { 00976 _dbus_verbose (<font class="stringliteral">" (policy) skipping allow rule since it doesn't apply to eavesdropping\n"</font>); 00977 <font class="keywordflow">continue</font>; 00978 } 00979 00980 <font class="comment">/* for deny, eavesdrop=true means the rule applies only when</font> 00981 <font class="comment"> * eavesdropping; eavesdrop=false means always deny.</font> 00982 <font class="comment"> */</font> 00983 <font class="keywordflow">if</font> (!eavesdropping && !rule->allow && rule->d.receive.eavesdrop) 00984 { 00985 _dbus_verbose (<font class="stringliteral">" (policy) skipping deny rule since it only applies to eavesdropping\n"</font>); 00986 <font class="keywordflow">continue</font>; 00987 } 00988 00989 <font class="keywordflow">if</font> (rule->d.receive.path != NULL) 00990 { 00991 <font class="keywordflow">if</font> (dbus_message_get_path (message) != NULL && 00992 strcmp (dbus_message_get_path (message), 00993 rule->d.receive.path) != 0) 00994 { 00995 _dbus_verbose (<font class="stringliteral">" (policy) skipping rule for different path\n"</font>); 00996 <font class="keywordflow">continue</font>; 00997 } 00998 } 00999 01000 <font class="keywordflow">if</font> (rule->d.receive.interface != NULL) 01001 { 01002 <font class="keywordflow">if</font> (dbus_message_get_interface (message) != NULL && 01003 strcmp (dbus_message_get_interface (message), 01004 rule->d.receive.interface) != 0) 01005 { 01006 _dbus_verbose (<font class="stringliteral">" (policy) skipping rule for different interface\n"</font>); 01007 <font class="keywordflow">continue</font>; 01008 } 01009 } 01010 01011 <font class="keywordflow">if</font> (rule->d.receive.member != NULL) 01012 { 01013 <font class="keywordflow">if</font> (dbus_message_get_member (message) != NULL && 01014 strcmp (dbus_message_get_member (message), 01015 rule->d.receive.member) != 0) 01016 { 01017 _dbus_verbose (<font class="stringliteral">" (policy) skipping rule for different member\n"</font>); 01018 <font class="keywordflow">continue</font>; 01019 } 01020 } 01021 01022 <font class="keywordflow">if</font> (rule->d.receive.error != NULL) 01023 { 01024 <font class="keywordflow">if</font> (dbus_message_get_error_name (message) != NULL && 01025 strcmp (dbus_message_get_error_name (message), 01026 rule->d.receive.error) != 0) 01027 { 01028 _dbus_verbose (<font class="stringliteral">" (policy) skipping rule for different error name\n"</font>); 01029 <font class="keywordflow">continue</font>; 01030 } 01031 } 01032 01033 <font class="keywordflow">if</font> (rule->d.receive.origin != NULL) 01034 { 01035 <font class="comment">/* sender can be NULL for messages that originate from the</font> 01036 <font class="comment"> * message bus itself, we check the strings in that case as</font> 01037 <font class="comment"> * built-in services don't have a DBusConnection but will</font> 01038 <font class="comment"> * still set the sender on their messages.</font> 01039 <font class="comment"> */</font> 01040 <font class="keywordflow">if</font> (sender == NULL) 01041 { 01042 <font class="keywordflow">if</font> (!dbus_message_has_sender (message, 01043 rule->d.receive.origin)) 01044 { 01045 _dbus_verbose (<font class="stringliteral">" (policy) skipping rule because message sender is not %s\n"</font>, 01046 rule->d.receive.origin); 01047 <font class="keywordflow">continue</font>; 01048 } 01049 } 01050 <font class="keywordflow">else</font> 01051 { 01052 BusService *service; 01053 <a class="code" href="structDBusString.html">DBusString</a> str; 01054 01055 _dbus_string_init_const (&str, rule->d.receive.origin); 01056 01057 service = bus_registry_lookup (registry, &str); 01058 01059 <font class="keywordflow">if</font> (service == NULL) 01060 { 01061 _dbus_verbose (<font class="stringliteral">" (policy) skipping rule because origin %s doesn't exist\n"</font>, 01062 rule->d.receive.origin); 01063 <font class="keywordflow">continue</font>; 01064 } 01065 01066 <font class="keywordflow">if</font> (!bus_service_has_owner (service, sender)) 01067 { 01068 _dbus_verbose (<font class="stringliteral">" (policy) skipping rule because origin %s isn't owned by sender\n"</font>, 01069 rule->d.receive.origin); 01070 <font class="keywordflow">continue</font>; 01071 } 01072 } 01073 } 01074 01075 <font class="comment">/* Use this rule */</font> 01076 allowed = rule->allow; 01077 01078 _dbus_verbose (<font class="stringliteral">" (policy) used rule, allow now = %d\n"</font>, 01079 allowed); 01080 } 01081 01082 <font class="keywordflow">return</font> allowed; 01083 } 01084 01085 dbus_bool_t 01086 bus_client_policy_check_can_own (BusClientPolicy *policy, 01087 <a class="code" href="structDBusConnection.html">DBusConnection</a> *connection, 01088 <font class="keyword">const</font> <a class="code" href="structDBusString.html">DBusString</a> *service_name) 01089 { 01090 <a class="code" href="structDBusList.html">DBusList</a> *link; 01091 dbus_bool_t allowed; 01092 01093 <font class="comment">/* policy->rules is in the order the rules appeared</font> 01094 <font class="comment"> * in the config file, i.e. last rule that applies wins</font> 01095 <font class="comment"> */</font> 01096 01097 allowed = FALSE; 01098 link = _dbus_list_get_first_link (&policy->rules); 01099 <font class="keywordflow">while</font> (link != NULL) 01100 { 01101 BusPolicyRule *rule = link-><a class="code" href="structDBusList.html#m2">data</a>; 01102 01103 link = _dbus_list_get_next_link (&policy->rules, link); 01104 01105 <font class="comment">/* Rule is skipped if it specifies a different service name from</font> 01106 <font class="comment"> * the desired one.</font> 01107 <font class="comment"> */</font> 01108 01109 <font class="keywordflow">if</font> (rule->type != BUS_POLICY_RULE_OWN) 01110 <font class="keywordflow">continue</font>; 01111 01112 <font class="keywordflow">if</font> (rule->d.own.service_name != NULL) 01113 { 01114 <font class="keywordflow">if</font> (!_dbus_string_equal_c_str (service_name, 01115 rule->d.own.service_name)) 01116 <font class="keywordflow">continue</font>; 01117 } 01118 01119 <font class="comment">/* Use this rule */</font> 01120 allowed = rule->allow; 01121 } 01122 01123 <font class="keywordflow">return</font> allowed; 01124 } 01125 01126 <font class="preprocessor">#ifdef DBUS_BUILD_TESTS</font> 01127 <font class="preprocessor"></font> 01128 dbus_bool_t 01129 bus_policy_test (<font class="keyword">const</font> <a class="code" href="structDBusString.html">DBusString</a> *test_data_dir) 01130 { 01131 <font class="comment">/* This doesn't do anything for now because I decided to do it in</font> 01132 <font class="comment"> * dispatch.c instead by having some of the clients in dispatch.c</font> 01133 <font class="comment"> * have particular policies applied to them.</font> 01134 <font class="comment"> */</font> 01135 01136 <font class="keywordflow">return</font> TRUE; 01137 } 01138 01139 <font class="preprocessor">#endif </font><font class="comment">/* DBUS_BUILD_TESTS */</font> </pre></div><hr><address align="right"><small>Generated on Mon Sep 29 21:31:02 2003 for D-BUS by <a href="http://www.doxygen.org/index.html"> <img src="doxygen.png" alt="doxygen" align="middle" border=0 width=110 height=53></a>1.2.15 </small></address> </body> </html>