Generic solution for onlycap issues
[platform/core/test/security-tests.git] / src / cynara-tests / test_cases_helpers.cpp
1 /*
2  * Copyright (c) 2015-2019 Samsung Electronics Co., Ltd All Rights Reserved
3  *
4  *    Licensed under the Apache License, Version 2.0 (the "License");
5  *    you may not use this file except in compliance with the License.
6  *    You may obtain a copy of the License at
7  *
8  *        http://www.apache.org/licenses/LICENSE-2.0
9  *
10  *    Unless required by applicable law or agreed to in writing, software
11  *    distributed under the License is distributed on an "AS IS" BASIS,
12  *    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  *    See the License for the specific language governing permissions and
14  *    limitations under the License.
15  */
16 /**
17  * @file        test_cases_helpers.cpp
18  * @author      Aleksander Zdyb <a.zdyb@samsung.com>
19  * @version     1.0
20  * @brief       Tests for cynara-helper-credentials-socket and cynara-helper-credentials-dbus
21  */
22
23 #include <cstdlib>
24 #include <functional>
25 #include <string>
26 #include <sys/types.h>
27 #include <sys/un.h>
28 #include <unistd.h>
29 #include <utility>
30
31 #include <dbus/dbus.h>
32 #include <glib-object.h>
33 #include <gio/gio.h>
34 #include <systemd/sd-bus.h>
35
36 #include <tests_common.h>
37 #include <access_provider.h>
38 #include <dpl/test/test_runner.h>
39 #include <memory.h>
40 #include <synchronization_pipe.h>
41 #include <tests_common.h>
42 #include <uds.h>
43 #include <passwd_access.h>
44 #include <cynara_helpers_creds.h>
45 #include <cynara_helpers_dbus.h>
46
47 #include <cynara-creds-gdbus.h>
48 #include <cynara-creds-self.h>
49 #include <scoped_process_label.h>
50
51 class ProcessCredentials {
52 public:
53     ProcessCredentials() {}
54
55     const std::string &label(void) const {
56         return m_label;
57     }
58
59     uid_t uid(void) const {
60         return PasswdAccess::uid(APP_USER);
61     }
62
63     gid_t gid(void) const {
64         return PasswdAccess::gid("users");
65     }
66
67 private:
68     std::string m_label = "cynara_helpers";
69 };
70
71 cynara_client_creds getClientDefaultMethod() {
72     cynara_client_creds def;
73     int ret = cynara_creds_get_default_client_method(&def);
74     RUNNER_ASSERT_MSG(ret == CYNARA_API_SUCCESS,
75                       "cynara_creds_get_default_client_method failed with " << ret);
76     return def;
77 }
78
79 cynara_user_creds getUserDefaultMethod() {
80     cynara_user_creds def;
81     int ret = cynara_creds_get_default_user_method(&def);
82     RUNNER_ASSERT_MSG(ret == CYNARA_API_SUCCESS,
83                       "cynara_creds_get_default_user_method failed with " << ret);
84     return def;
85 }
86
87
88 void udsServer(SynchronizationPipe &pipe, const struct sockaddr_un &sockaddr,
89                const struct ProcessCredentials &peerCredentials) {
90     SecurityServer::AccessProvider ap(peerCredentials.label());
91     ap.applyAndSwithToUser(peerCredentials.uid(), peerCredentials.gid());
92     pipe.claimChildEp();
93
94     int sock = UDSHelpers::createServer(&sockaddr);
95     SockUniquePtr sockPtr(&sock);
96     pipe.post();
97     int clientSock = UDSHelpers::acceptClient(sock);
98
99     UDSHelpers::waitForDisconnect(clientSock);
100 }
101
102 typedef std::function<void(int sock, pid_t pid,
103         const ProcessCredentials &peerCredentials)> SocketAssertionFn;
104
105 void socketTestTemplate(SocketAssertionFn assertion, const std::string &scope) {
106     const auto sockaddr = UDSHelpers::makeAbstractAddress("helper_" + scope + ".socket");
107     const ProcessCredentials peerCredentials;
108
109     SynchronizationPipe pipe;
110
111     pid_t pid = runInChild(std::bind(udsServer, std::ref(pipe), std::cref(sockaddr),
112                            std::cref(peerCredentials)));
113
114     pipe.claimParentEp();
115     pipe.wait();
116     int sock = UDSHelpers::createClient(&sockaddr);
117     SockUniquePtr sockPtr(&sock);
118
119     assertion(sock, pid, peerCredentials);
120 }
121
122 RUNNER_TEST_GROUP_INIT(cynara_creds_socket)
123
124 void testSocketClientSmack(cynara_client_creds method = CLIENT_METHOD_SMACK) {
125     socketTestTemplate([method] (int sock, pid_t, const ProcessCredentials &peerCredentials) {
126         CStringPtr label(CynaraHelperCredentials::socketGetClient(sock, method));
127         RUNNER_ASSERT_MSG(peerCredentials.label() == label.get(),
128                           "Labels don't match ret = " << label.get()
129                           << "; expected = " << peerCredentials.label());
130     }, "tccs01");
131 }
132
133 void testSocketClientPid(cynara_client_creds method = CLIENT_METHOD_PID) {
134     socketTestTemplate([method] (int sock, pid_t pid, const ProcessCredentials &) {
135         CStringPtr clientPidStr(CynaraHelperCredentials::socketGetClient(sock, method));
136         pid_t clientPid = std::stoi(clientPidStr.get());
137         RUNNER_ASSERT_MSG(pid == clientPid, "PIDs don't match ret = " << clientPid
138                           << "; expected = " << pid);
139     }, "tccs02");
140 }
141
142 RUNNER_MULTIPROCESS_TEST_SMACK(tccs01_socket_credentials_client_smack)
143 {
144     testSocketClientSmack();
145 }
146
147 RUNNER_MULTIPROCESS_TEST(tccs02_socket_credentials_client_pid)
148 {
149     testSocketClientPid();
150 }
151
152 RUNNER_MULTIPROCESS_TEST_SMACK(tccs03_socket_credentials_client_default)
153 {
154     auto method = getClientDefaultMethod();
155     switch(method) {
156     case CLIENT_METHOD_SMACK:
157         testSocketClientSmack(CLIENT_METHOD_DEFAULT);
158         break;
159     case CLIENT_METHOD_PID:
160         testSocketClientPid(CLIENT_METHOD_DEFAULT);
161         break;
162     default:
163         RUNNER_FAIL_MSG("cynara_creds_get_default_client_method returned unexpected value "
164                         << method);
165     }
166 }
167
168 void testSocketUserUid(cynara_user_creds method = USER_METHOD_UID) {
169     socketTestTemplate([method] (int sock, pid_t, const ProcessCredentials &peerCredentials) {
170         CStringPtr uidStr(CynaraHelperCredentials::socketGetUser(sock, method));
171         uid_t uid = std::stoul(uidStr.get());
172         RUNNER_ASSERT_MSG(peerCredentials.uid() == uid, "UIDs don't match ret = " << uid
173                           << "; expected = "<< peerCredentials.uid());
174     }, "tccs04");
175 }
176
177 void testSocketUserGid(cynara_user_creds method = USER_METHOD_GID) {
178     socketTestTemplate([method] (int sock, pid_t, const ProcessCredentials &peerCredentials) {
179         CStringPtr gidStr(CynaraHelperCredentials::socketGetUser(sock, method));
180         gid_t gid = std::stoul(gidStr.get());
181         RUNNER_ASSERT_MSG(peerCredentials.gid() == gid, "GIDs don't match ret = " << gid
182                           << "; expected = "<< peerCredentials.gid());
183     }, "tccs05");
184 }
185
186 RUNNER_MULTIPROCESS_TEST(tccs04_socket_credentials_user_uid)
187 {
188     testSocketUserUid();
189 }
190
191 RUNNER_MULTIPROCESS_TEST(tccs05_socket_credentials_user_gid)
192 {
193     testSocketUserGid();
194 }
195
196 RUNNER_MULTIPROCESS_TEST(tccs06_socket_credentials_user_default)
197 {
198     auto method = getUserDefaultMethod();
199     switch(method) {
200     case USER_METHOD_UID:
201         testSocketUserUid(USER_METHOD_DEFAULT);
202         break;
203     case USER_METHOD_GID:
204         testSocketUserGid(USER_METHOD_DEFAULT);
205         break;
206     default:
207         RUNNER_FAIL_MSG("cynara_creds_get_default_user_method returned unexpected value "
208                  << method);
209     }
210 }
211
212 RUNNER_MULTIPROCESS_TEST(tccs07_socket_credentials_pid)
213 {
214     socketTestTemplate([] (int sock, pid_t expectedPid, const ProcessCredentials &) {
215         pid_t peerPid(CynaraHelperCredentials::socketGetPid(sock));
216         RUNNER_ASSERT_MSG(peerPid == expectedPid, "Pids don't match ret = " << peerPid
217                           << "; expected = "<< expectedPid);
218     }, "tccs05");
219 }
220
221 // TODO: Create utility namespace for DBus, maybe?
222 DBusConnectionPtr createDBusConnection(const std::string &name) {
223     DBusError err;
224
225     dbus_error_init(&err);
226     DBusConnection *conn = dbus_bus_get_private(DBUS_BUS_SYSTEM, &err);
227     RUNNER_ASSERT_MSG(dbus_error_is_set(&err) != 1, "Error in dbus_bus_get: " << err.message);
228     dbus_connection_set_exit_on_disconnect(conn, FALSE);
229
230     DBusConnectionPtr ret(conn, [] (DBusConnection *conn) {
231         dbus_connection_close(conn);
232         dbus_connection_unref(conn);
233     });
234
235     if (name.empty() == false) {
236         dbus_bus_request_name(conn, name.c_str(), DBUS_NAME_FLAG_REPLACE_EXISTING , &err);
237         RUNNER_ASSERT_MSG(dbus_error_is_set(&err) != TRUE,
238                           "Error in dbus_bus_request_name: " << err.message);
239     }
240
241     return ret;
242 }
243
244 void dbusServer(SynchronizationPipe &pipe, const std::string &requestedName,
245                 const ProcessCredentials &peerCredentials) {
246     // for DBus connection, System must have access to our peer creds as well.
247     SecurityServer::AccessProvider systemAp("System");
248     systemAp.addObjectRule(peerCredentials.label(), "rwx");
249     systemAp.apply();
250
251     SecurityServer::AccessProvider ap(peerCredentials.label());
252     ap.addObjectRule("System", "w");
253     ap.addObjectRule("System::Run", "x");
254     ap.addObjectRule("System::Shared", "rwx"); // for GDB
255     ap.addSubjectRule("System::Privileged", "rwx"); // for piping
256     ap.addObjectRule("System::Privileged", "rwx"); // for GDB and piping
257     ap.addObjectRule("User", "r"); // for /usr/lib/debug access
258     ap.applyAndSwithToUser(peerCredentials.uid(), peerCredentials.gid());
259     pipe.claimChildEp();
260
261     auto conn = createDBusConnection(requestedName);
262     pipe.post();
263     pipe.wait();
264 }
265
266 typedef std::function<void(DBusConnectionPtr conn, pid_t pid,
267                            const std::string &requestedName,
268                            const ProcessCredentials &peerCredentials)> DBusAssertionFn;
269
270 void dbusTestTemplate(DBusAssertionFn assertion, const std::string &/*scope*/) {
271     std::string requestedName = "tests.dbus.cynara";
272     const ProcessCredentials peerCredentials;
273
274     SynchronizationPipe pipe;
275     pid_t pid = runInChild(std::bind(dbusServer, std::ref(pipe), std::cref(requestedName),
276                            std::cref(peerCredentials)));
277
278     pipe.claimParentEp();
279     pipe.wait();
280
281     auto conn = createDBusConnection("");
282     assertion(std::move(conn), pid, requestedName, peerCredentials);
283     pipe.post();
284 }
285
286 RUNNER_TEST_GROUP_INIT(cynara_creds_dbus)
287
288 void testDbusClientPid(cynara_client_creds method = CLIENT_METHOD_PID) {
289     dbusTestTemplate([method] (DBusConnectionPtr conn, pid_t pid, const std::string &requestedName,
290                          const ProcessCredentials &) {
291         CStringPtr clientPidStr(CynaraHelperCredentials::dbusGetClient(std::move(conn),
292             requestedName.c_str(), method, CYNARA_API_SUCCESS));
293         pid_t clientPid = std::stoi(clientPidStr.get());
294         RUNNER_ASSERT_MSG(pid == clientPid, "PIDs don't match ret = " << clientPid
295                           << "; expected = " << pid);
296     }, "tccd01");
297 }
298
299 void testDbusClientSmack(cynara_client_creds method = CLIENT_METHOD_SMACK) {
300     dbusTestTemplate([method] (DBusConnectionPtr conn, pid_t, const std::string &requestedName,
301                          const ProcessCredentials &peerCredentials) {
302         CStringPtr label(CynaraHelperCredentials::dbusGetClient(std::move(conn),
303             requestedName.c_str(), method, CYNARA_API_SUCCESS));
304         RUNNER_ASSERT_MSG(peerCredentials.label() == label.get(),
305                           "Labels don't match ret = " << label.get()
306                           << "; expected = " << peerCredentials.label());
307     }, "tccd02");
308 }
309
310 RUNNER_MULTIPROCESS_TEST(tccd01_dbus_credentials_client_pid)
311 {
312     testDbusClientPid();
313 }
314
315 RUNNER_MULTIPROCESS_TEST_SMACK(tccd02_dbus_credentials_client_smack)
316 {
317     testDbusClientSmack();
318 }
319
320 RUNNER_MULTIPROCESS_TEST_SMACK(tccd03_dbus_credentials_client_default)
321 {
322     auto method = getClientDefaultMethod();
323     switch(method) {
324     case CLIENT_METHOD_SMACK:
325         testDbusClientSmack(CLIENT_METHOD_DEFAULT);
326         break;
327     case CLIENT_METHOD_PID:
328         testDbusClientPid(CLIENT_METHOD_DEFAULT);
329         break;
330     default:
331         RUNNER_FAIL_MSG("cynara_creds_get_default_client_method returned unexpected value "
332                         << method);
333     }
334 }
335
336 void testDbusUserUid(cynara_user_creds method = USER_METHOD_UID) {
337     dbusTestTemplate([method] (DBusConnectionPtr conn, pid_t, const std::string &requestedName,
338                          const ProcessCredentials &peerCredentials) {
339         CStringPtr uidStr(CynaraHelperCredentials::dbusGetUser(std::move(conn),
340             requestedName.c_str(), method, CYNARA_API_SUCCESS));
341         uid_t uid = std::stoul(uidStr.get());
342         RUNNER_ASSERT_MSG(peerCredentials.uid() == uid, "UIDs don't match ret = " << uid
343                           << "; expected = "<< peerCredentials.uid());
344     }, "tccd04");
345 }
346
347 void testDbusUserGid(cynara_user_creds method = USER_METHOD_GID) {
348     // Acquiring gid from dbus connection is not yet implemented for cynara helpers
349     dbusTestTemplate([method] (DBusConnectionPtr conn, pid_t, const std::string &requestedName,
350                          const ProcessCredentials &) {
351         CStringPtr gidStr(CynaraHelperCredentials::dbusGetUser(std::move(conn),
352             requestedName.c_str(), method, CYNARA_API_METHOD_NOT_SUPPORTED));
353     }, "tccd04");
354 }
355
356 RUNNER_MULTIPROCESS_TEST(tccd04_dbus_credentials_user_uid)
357 {
358     testDbusUserUid();
359 }
360
361 RUNNER_MULTIPROCESS_TEST(tccd05_dbus_credentials_user_gid)
362 {
363     testDbusUserGid();
364 }
365
366 RUNNER_MULTIPROCESS_TEST(tccd06_dbus_credentials_user_default) {
367     auto method = getUserDefaultMethod();
368     switch(method) {
369     case USER_METHOD_UID:
370         testDbusUserUid(USER_METHOD_DEFAULT);
371         break;
372     case USER_METHOD_GID:
373         testDbusUserGid(USER_METHOD_DEFAULT);
374         break;
375     default:
376         RUNNER_FAIL_MSG("cynara_creds_get_default_user_method returned unexpected value "
377                         << method);
378     }
379 }
380
381 RUNNER_TEST_SMACK(tccd06_dbus_credentials_pid) {
382     dbusTestTemplate([] (DBusConnectionPtr conn, pid_t expectedPid,
383                          const std::string &requestedName, const ProcessCredentials &) {
384         auto helperPid = CynaraHelperCredentials::dbusGetPid(std::move(conn),
385             requestedName.c_str(), CYNARA_API_SUCCESS);
386         RUNNER_ASSERT_MSG(helperPid == expectedPid, "PIDs don't match ret = " << helperPid
387                           << "; expected = " << expectedPid);
388     }, "tccd06");
389 }
390
391 GDBusConnectionPtr createGDBusConnection() {
392     GDBusConnection *conn = g_bus_get_sync(G_BUS_TYPE_SYSTEM, NULL, NULL);
393
394     return GDBusConnectionPtr(conn, [] (GDBusConnection *conn) {
395         g_object_unref(G_OBJECT(conn));
396     });
397 }
398
399
400 typedef std::function<void(GDBusConnectionPtr conn, pid_t pid,
401                            const std::string &requestedName,
402                            const ProcessCredentials &peerCredentials)> GDBusAssertionFn;
403
404 void gdbusTestTemplate(GDBusAssertionFn assertion, const std::string &/*scope*/) {
405     std::string requestedName = "tests.dbus.cynara";
406     const ProcessCredentials peerCredentials;
407
408     SynchronizationPipe pipe;
409     pid_t pid = runInChild(std::bind(dbusServer, std::ref(pipe), std::cref(requestedName),
410                            std::cref(peerCredentials)));
411
412     pipe.claimParentEp();
413     pipe.wait();
414
415     auto conn = createGDBusConnection();
416     assertion(std::move(conn), pid, requestedName, peerCredentials);
417     pipe.post();
418 }
419
420
421 RUNNER_TEST_GROUP_INIT(cynara_creds_gdbus)
422
423 void testGdbusClientPid(cynara_client_creds method = CLIENT_METHOD_PID) {
424     gdbusTestTemplate([method] (GDBusConnectionPtr conn, pid_t pid,
425                                 const std::string &requestedName,
426                                 const ProcessCredentials &) {
427         GStringPtr clientPidStr(CynaraHelperCredentials::gdbusGetClient(std::move(conn),
428                                 requestedName.c_str(), method));
429         pid_t clientPid = std::stoi(clientPidStr.get());
430         RUNNER_ASSERT_MSG(pid == clientPid, "PIDs don't match ret = " << clientPid
431                           << "; expected = " << pid);
432     }, "tccgd01");
433 }
434
435 void testGdbusClientSmack(cynara_client_creds method = CLIENT_METHOD_SMACK) {
436     gdbusTestTemplate([method] (GDBusConnectionPtr conn, pid_t,
437                                 const std::string &requestedName,
438                                 const ProcessCredentials &peerCredentials) {
439         GStringPtr label(CynaraHelperCredentials::gdbusGetClient(std::move(conn),
440                          requestedName.c_str(), method));
441         RUNNER_ASSERT_MSG(peerCredentials.label() == label.get(),
442                           "Labels don't match ret = " << label.get()
443                           << "; expected = " << peerCredentials.label());
444     }, "tccgd02");
445 }
446
447 RUNNER_MULTIPROCESS_TEST(tccgd01_gdbus_credentials_client_pid)
448 {
449     testGdbusClientPid();
450 }
451
452 RUNNER_MULTIPROCESS_TEST_SMACK(tccgd02_gdbus_credentials_client_smack)
453 {
454     testGdbusClientSmack();
455 }
456
457 RUNNER_MULTIPROCESS_TEST_SMACK(tccgd03_gdbus_credentials_client_default)
458 {
459     auto method = getClientDefaultMethod();
460     switch(method) {
461     case CLIENT_METHOD_SMACK:
462         testGdbusClientSmack(CLIENT_METHOD_DEFAULT);
463         break;
464     case CLIENT_METHOD_PID:
465         testGdbusClientPid(CLIENT_METHOD_DEFAULT);
466         break;
467     default:
468         RUNNER_FAIL_MSG("cynara_creds_get_default_client_method returned unexpected value "
469                         << method);
470     }
471 }
472
473 void testGdbusUserUid(cynara_user_creds method = USER_METHOD_UID) {
474     gdbusTestTemplate([method] (GDBusConnectionPtr conn, pid_t,
475                                 const std::string &requestedName,
476                                 const ProcessCredentials &peerCredentials) {
477         GStringPtr uidStr(CynaraHelperCredentials::gdbusGetUser(std::move(conn),
478                           requestedName.c_str(), method));
479         uid_t uid = std::stoul(uidStr.get());
480         RUNNER_ASSERT_MSG(peerCredentials.uid() == uid, "UIDs don't match ret = " << uid
481                           << "; expected = "<< peerCredentials.uid());
482     }, "tccgd04");
483 }
484
485 void testGdbusUserGid(cynara_user_creds method = USER_METHOD_GID) {
486     // Getting gid for gdbus connection is not yet implemented in cynara helpers
487     gdbusTestTemplate([method] (GDBusConnectionPtr conn, pid_t,
488                                 const std::string &requestedName,
489                                 const ProcessCredentials &) {
490         GStringPtr gidStr(CynaraHelperCredentials::gdbusGetUser(std::move(conn),
491                           requestedName.c_str(), method, CYNARA_API_METHOD_NOT_SUPPORTED));
492     }, "tccgd04");
493 }
494
495 RUNNER_MULTIPROCESS_TEST(tccgd04_gdbus_credentials_user_uid)
496 {
497     testGdbusUserUid();
498 }
499
500 RUNNER_MULTIPROCESS_TEST(tccgd05_gdbus_credentials_user_gid)
501 {
502     testGdbusUserGid();
503 }
504
505 RUNNER_MULTIPROCESS_TEST(tccgd06_gdbus_credentials_user_default) {
506     auto method = getUserDefaultMethod();
507     switch(method) {
508     case USER_METHOD_UID:
509         testGdbusUserUid(USER_METHOD_DEFAULT);
510         break;
511     case USER_METHOD_GID:
512         testGdbusUserGid(USER_METHOD_DEFAULT);
513         break;
514     default:
515         RUNNER_FAIL_MSG("cynara_creds_get_default_user_method returned unexpected value "
516                         << method);
517     }
518 }
519
520 RUNNER_MULTIPROCESS_TEST(tccgd06_gdbus_credentials_pid) {
521     gdbusTestTemplate([] (GDBusConnectionPtr conn, pid_t expectedPid,
522                           const std::string &requestedName, const ProcessCredentials &) {
523         auto helperPid = CynaraHelperCredentials::gdbusGetPid(std::move(conn),
524                          requestedName.c_str());
525         RUNNER_ASSERT_MSG(helperPid == expectedPid, "PIDs don't match ret = " << helperPid
526                           << "; expected = " << expectedPid);
527     }, "tccgd06");
528 }
529
530
531 SdBusConnectionPtr createSdBusConnection(const std::string &requestedName) {
532     sd_bus *bus = NULL;
533
534     int r = sd_bus_default_system(&bus);
535     RUNNER_ASSERT_MSG(r >= 0, "Failed to connect do system bus: %s" << strerror(-r));
536
537     if (requestedName.empty() == false) {
538         r = sd_bus_request_name(bus, requestedName.c_str(), SD_BUS_NAME_REPLACE_EXISTING);
539         RUNNER_ASSERT_MSG(r >= 0, "Error in sd_bus_request_name");
540     }
541
542     SdBusConnectionPtr ret(bus, [] (sd_bus *busConnection) {
543         sd_bus_unref(busConnection);
544     });
545
546     return ret;
547 }
548
549 typedef std::function<void(SdBusConnectionPtr conn, pid_t pid, const std::string &requestedName,
550                            const ProcessCredentials &peerCredentials)> SdBusAssertionFn;
551
552 void sdBusTestTemplate(SdBusAssertionFn assertion) {
553     std::string requestedName = "tests.dbus.cynara";
554     const ProcessCredentials peerCredentials;
555
556     SynchronizationPipe pipe;
557     pid_t pid = runInChild(std::bind(dbusServer, std::ref(pipe), std::cref(requestedName),
558                            std::cref(peerCredentials)));
559
560     pipe.claimParentEp();
561     pipe.wait();
562
563     auto conn = createSdBusConnection("");
564     assertion(std::move(conn), pid, requestedName, peerCredentials);
565     pipe.post();
566 }
567
568
569 RUNNER_TEST_GROUP_INIT(cynara_creds_sd_bus)
570
571 void testSdBusClientPid(cynara_client_creds method = CLIENT_METHOD_PID) {
572     sdBusTestTemplate([method] (SdBusConnectionPtr conn, pid_t pid,
573                         const std::string &requestedName,
574                         const ProcessCredentials &) {
575         CStringPtr clientPidStr(CynaraHelperCredentials::sdBusGetClient(std::move(conn),
576                                 requestedName.c_str(), method, CYNARA_API_SUCCESS));
577         pid_t clientPid = std::stoi(clientPidStr.get());
578         RUNNER_ASSERT_MSG(pid == clientPid, "PIDs don't match ret = " << clientPid
579                           << "; expected = " << pid);
580     });
581 }
582
583 void testSdBusClientSmack(cynara_client_creds method = CLIENT_METHOD_SMACK) {
584     sdBusTestTemplate([method] (SdBusConnectionPtr conn, pid_t,
585                         const std::string &requestedName,
586                         const ProcessCredentials &peerCredentials) {
587         CStringPtr label(CynaraHelperCredentials::sdBusGetClient(std::move(conn),
588                          requestedName.c_str(), method, CYNARA_API_SUCCESS));
589         RUNNER_ASSERT_MSG(peerCredentials.label() == label.get(),
590                           "Labels don't match ret = " << label.get()
591                           << "; expected = " << peerCredentials.label());
592     });
593 }
594
595 RUNNER_MULTIPROCESS_TEST(tccsd01_sd_bus_credentials_client_pid)
596 {
597     testSdBusClientPid();
598 }
599
600 RUNNER_MULTIPROCESS_TEST_SMACK(tccsd02_sd_bus_credentials_client_smack)
601 {
602     testSdBusClientSmack();
603 }
604
605 RUNNER_MULTIPROCESS_TEST_SMACK(tccsd03_sd_bus_credentials_client_default)
606 {
607     auto method = getClientDefaultMethod();
608     switch(method) {
609     case CLIENT_METHOD_SMACK:
610         testSdBusClientSmack(CLIENT_METHOD_DEFAULT);
611         break;
612     case CLIENT_METHOD_PID:
613         testSdBusClientPid(CLIENT_METHOD_DEFAULT);
614         break;
615     default:
616         RUNNER_FAIL_MSG("cynara_creds_get_default_client_method returned unexpected value "
617                         << method);
618     }
619 }
620
621 void testSdBusUserUid(cynara_user_creds method = USER_METHOD_UID) {
622     sdBusTestTemplate([method] (SdBusConnectionPtr conn, pid_t,
623                         const std::string &requestedName,
624                         const ProcessCredentials &peerCredentials) {
625         CStringPtr uidStr(CynaraHelperCredentials::sdBusGetUser(std::move(conn),
626                           requestedName.c_str(), method, CYNARA_API_SUCCESS));
627         uid_t uid = std::stoul(uidStr.get());
628         RUNNER_ASSERT_MSG(peerCredentials.uid() == uid, "UIDs don't match ret = " << uid
629                           << "; expected = "<< peerCredentials.uid());
630     });
631 }
632
633 void testSdBusUserGid(cynara_user_creds method = USER_METHOD_GID) {
634     sdBusTestTemplate([method] (SdBusConnectionPtr conn, pid_t,
635                         const std::string &requestedName,
636                         const ProcessCredentials &peerCredentials) {
637         CStringPtr gidStr(CynaraHelperCredentials::sdBusGetUser(std::move(conn),
638                           requestedName.c_str(), method, CYNARA_API_SUCCESS));
639         gid_t gid = std::stoul(gidStr.get());
640         RUNNER_ASSERT_MSG(peerCredentials.gid() == gid, "GIDs don't match ret = " << gid
641                           << "; expected = "<< peerCredentials.gid());
642     });
643 }
644
645 RUNNER_MULTIPROCESS_TEST(tccsd04_sd_bus_credentials_user_uid)
646 {
647     testSdBusUserUid();
648 }
649
650 RUNNER_MULTIPROCESS_TEST(tccsd05_sd_bus_credentials_user_gid)
651 {
652     testSdBusUserGid();
653 }
654
655 RUNNER_MULTIPROCESS_TEST(tccsd06_sd_bus_credentials_user_default)
656 {
657     auto method = getUserDefaultMethod();
658     switch(method) {
659     case USER_METHOD_UID:
660         testSdBusUserUid(USER_METHOD_DEFAULT);
661         break;
662     case USER_METHOD_GID:
663         testSdBusUserGid(USER_METHOD_DEFAULT);
664         break;
665     default:
666         RUNNER_FAIL_MSG("cynara_creds_get_default_user_method returned unexpected value "
667                         << method);
668     }
669 }
670
671 RUNNER_TEST_SMACK(tccd07_sd_bus_credentials_pid) {
672     sdBusTestTemplate([] (SdBusConnectionPtr conn, pid_t expectedPid,
673                           const std::string &requestedName, const ProcessCredentials &) {
674         auto helperPid = CynaraHelperCredentials::sdBusGetPid(std::move(conn),
675                          requestedName.c_str(), CYNARA_API_SUCCESS);
676         RUNNER_ASSERT_MSG(helperPid == expectedPid, "PIDs don't match ret = " << helperPid
677                           << "; expected = " << expectedPid);
678     });
679 }
680
681
682 RUNNER_TEST_GROUP_INIT(cynara_creds_self)
683
684 void testCredsClientSelf(cynara_client_creds method, const std::string &expected) {
685     char *client;
686     int ret = cynara_creds_self_get_client(method, &client);
687     CStringPtr clientPtr(client);
688     RUNNER_ASSERT_MSG(ret == CYNARA_API_SUCCESS, "cynara_creds_self_get_client failed with " << ret);
689     RUNNER_ASSERT_MSG(expected == client, "expected client doesn't match, expected: " << expected
690                                           << ", got : " << client);
691 }
692
693 void testCredsUserSelf(cynara_user_creds method, const std::string &expected) {
694     char *user;
695     int ret = cynara_creds_self_get_user(method, &user);
696     CStringPtr clientPtr(user);
697     RUNNER_ASSERT_MSG(ret == CYNARA_API_SUCCESS, "cynara_creds_self_get_user failed with " << ret);
698     RUNNER_ASSERT_MSG(expected == user, "expected user doesn't match, expected: " << expected
699                                           << ", got : " << user);
700 }
701
702 void testSelfClientSmack(cynara_client_creds method = CLIENT_METHOD_SMACK) {
703     std::string label = "test-label";
704     ScopedProcessLabel spl(label, false);
705     testCredsClientSelf(method, label);
706 }
707
708 void testSelfClientPid(cynara_client_creds method = CLIENT_METHOD_PID) {
709     pid_t pid = getpid();
710     testCredsClientSelf(method, std::to_string(pid));
711 }
712
713 void testSelfUserUid(cynara_user_creds method = USER_METHOD_UID) {
714     uid_t uid = getuid();
715     testCredsUserSelf(method, std::to_string(uid));
716 }
717
718 void testSelfUserGid(cynara_user_creds method = USER_METHOD_GID) {
719     gid_t gid = getgid();
720     testCredsUserSelf(method, std::to_string(gid));
721 }
722
723 RUNNER_CHILD_TEST_SMACK(tccsl01_self_credentials_client_smack) {
724     testSelfClientSmack();
725 }
726
727 RUNNER_CHILD_TEST_SMACK(tccsl02_self_credentials_client_pid) {
728     testSelfClientPid();
729 }
730
731 RUNNER_CHILD_TEST_SMACK(tccsl03_self_credentials_user_uid) {
732     testSelfUserUid();
733 }
734
735 RUNNER_CHILD_TEST_SMACK(tccsl04_self_credentials_user_gid) {
736     testSelfUserGid();
737 }
738
739 RUNNER_CHILD_TEST_SMACK(tccsl05_self_credentials_client_default) {
740     auto method = getClientDefaultMethod();
741     switch(method) {
742     case CLIENT_METHOD_SMACK:
743         testSelfClientSmack(CLIENT_METHOD_DEFAULT);
744         break;
745     case CLIENT_METHOD_PID:
746         testSelfClientPid(CLIENT_METHOD_DEFAULT);
747         break;
748     default:
749         RUNNER_FAIL_MSG("cynara_creds_get_default_client_method returned unexpected value " << method);
750     }
751 }
752
753 RUNNER_CHILD_TEST_SMACK(tccsl06_self_credentials_user_default) {
754     auto method = getUserDefaultMethod();
755     switch(method) {
756     case USER_METHOD_UID:
757         testSelfUserUid(USER_METHOD_DEFAULT);
758         break;
759     case USER_METHOD_GID:
760         testSelfUserGid(USER_METHOD_DEFAULT);
761         break;
762     default:
763         RUNNER_FAIL_MSG("cynara_creds_get_default_user_method returned unexpected value " << method);
764     }
765 }