--- /dev/null
+/*
+ * Copyright (c) 2014-2016 Samsung Electronics Co., Ltd All Rights Reserved
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+#pragma once
+
+#include <unistd.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+#include <sys/smack.h>
+
+#include <string>
+
+
+struct AppInstallHelper {
+ AppInstallHelper(const std::string &name)
+ : m_name(name)
+ {}
+
+ std::string getInstallDir() {
+ return "/usr/apps/" + getPkgId();
+ }
+
+ std::string getTrustedDir(int i = 0) {
+ return getInstallDir() + "/trustedDir" + std::to_string(i);
+ }
+
+ std::string getAppId() {
+ return m_name + "_app_id";
+ }
+
+ std::string getPkgId() {
+ return m_name + "_pkg_id";
+ }
+
+ void createInstallDir() {
+ mkdir(getInstallDir().c_str(), 0777);
+ }
+
+ void createTrustedDir(int i = 0) {
+ mkdir(getTrustedDir(i).c_str(), 0777);
+ }
+
+ void revokeRules() {
+ RUNNER_ASSERT_MSG(
+ 0 == smack_revoke_subject(generateAppLabel().c_str()),
+ "Revoking smack subject failed");
+ RUNNER_ASSERT_MSG(
+ 0 == smack_revoke_subject(generatePkgLabel().c_str()),
+ "Revoking smack subject failed");
+ }
+
+ std::string generateAppLabel() {
+ return "User::App::" + getAppId();
+ }
+
+ std::string generatePkgLabel() {
+ return "User::Pkg::" + getPkgId();
+ }
+
+ virtual ~AppInstallHelper() {
+ // TODO we should also remove trusted dirs created with custom params
+ rmdir(getTrustedDir().c_str());
+ rmdir(getInstallDir().c_str());
+ }
+
+protected:
+ std::string m_name;
+};
+
#include <sys/types.h>
#include <sys/un.h>
#include <sys/wait.h>
+#include <sys/smack.h>
#include <algorithm>
#include <fstream>
#include <sm_db.h>
#include <sm_request.h>
#include <sm_user_request.h>
+#include <app_install_helper.h>
#include <temp_test_user.h>
#include <cynara_test_client.h>
#include <cynara_test_admin.h>
static const char *const SM_RW_PATH = "/usr/apps/sm_test_02_pkg_id_full/app_dir";
static const char *const SM_DENIED_PATH = "/usr/apps/non_app_dir";
+static const char *const SM_TRUSTED_PATH = "/usr/apps/sm_test_02_pkg_id_full/app_dir_trusted";
static const char *const ANY_USER_REPRESENTATION = "anyuser";/*this may be actually any string*/
static const std::string EXEC_FILE("exec");
return pw;
};
+void check_exact_access(const std::string& subject, const std::string& object, const std::string& access)
+{
+ // check access
+ if (!access.empty()) {
+ int result = smack_have_access(subject.c_str(), object.c_str(), access.c_str());
+ RUNNER_ASSERT_MSG(result >= 0, "smack_have_access failed");
+ RUNNER_ASSERT_MSG(result == 1,
+ "No smack access: " << subject << " " << object << " " << access);
+ }
+ // check excessive access
+ auto foundInAccess = [&access](std::string::value_type c) {
+ return access.find(c) != std::string::npos; };
+
+ std::string negative = "rwxatl";
+ auto end = std::remove_if(negative.begin(), negative.end(), foundInAccess);
+ negative.erase(end, negative.end());
+
+ for(const auto& c : negative) {
+ int result = smack_have_access(subject.c_str(), object.c_str(), std::string(1, c).c_str());
+ RUNNER_ASSERT_MSG(result >= 0, "smack_have_access failed");
+ RUNNER_ASSERT_MSG(result == 0,
+ "Unexpected smack access: " << subject << " " << object << " " << c);
+ }
+}
+
RUNNER_TEST_GROUP_INIT(SECURITY_MANAGER)
};
}
-RUNNER_TEST(security_manager_27a_set_wrong_author_id)
+RUNNER_TEST(security_manager_40_set_wrong_author_id)
{
InstallRequest requestInst;
requestInst.setAuthorId(NULL, SECURITY_MANAGER_ERROR_INPUT_PARAM);
requestInst.setAuthorId("", SECURITY_MANAGER_ERROR_INPUT_PARAM);
}
-RUNNER_TEST(security_manager_27b_set_author_id_multiple_times)
+RUNNER_TEST(security_manager_41_set_author_id_multiple_times)
{
for(unsigned int i=0; i<10; ++i) {
std::string authorId = "some-author-id" + std::to_string(i);
}
}
+RUNNER_TEST(security_manager_43_app_install_with_trusted_path)
+{
+ std::vector<AppInstallHelper> helper {{"app43a"}, {"app43b"}, {"app43c"}};
+ auto &provider = helper[0];
+ auto &user = helper[1];
+ auto &untrusted = helper[2];
+
+ TestSecurityManagerDatabase dbtest;
+ const char *author_id = "custom_author_id_test 41";
+
+ const char *const trusted_access = "rwxatl";
+ const char *const system_access = "rwxatl";
+
+ int result;
+
+ // cleanup
+ for (auto &e : helper) {
+ e.revokeRules();
+ e.createInstallDir();
+ e.createTrustedDir();
+ }
+
+ result = nftw(provider.getInstallDir().c_str(), &nftw_remove_labels, FTW_MAX_FDS, FTW_PHYS);
+ RUNNER_ASSERT_MSG(result == 0, "Unable to set Smack labels in " << SM_TRUSTED_PATH);
+
+ // install app with shared/trusted dir
+ InstallRequest trustingApp;
+ trustingApp.setAppId(provider.getAppId().c_str());
+ trustingApp.setPkgId(provider.getPkgId().c_str());
+ trustingApp.setAuthorId("author id to be overwritten");
+ trustingApp.setAuthorId(author_id);
+ trustingApp.addPath(provider.getTrustedDir().c_str(), SECURITY_MANAGER_PATH_TRUSTED_RW);
+ Api::install(trustingApp);
+
+ int64_t authorDb = dbtest.get_author_id(author_id);
+ const std::string trusted_label = std::string("User::Author::") + std::to_string(authorDb);
+
+ // check trusted path label
+ nftw_expected_label = trusted_label;
+ nftw_expected_transmute = true;
+ nftw_expected_exec = false;
+
+ // check labels
+ result = nftw(provider.getTrustedDir().c_str(), &nftw_check_sm_labels, FTW_MAX_FDS, FTW_PHYS);
+ RUNNER_ASSERT_MSG(result == 0, "Unable to check Smack labels for " << SM_TRUSTED_PATH);
+
+ // check rules
+ check_exact_access("System", trusted_label.c_str(), system_access);
+ check_exact_access("User", trusted_label.c_str(), system_access);
+ check_exact_access(generateAppLabel(provider.getAppId().c_str()), trusted_label, trusted_access);
+ check_exact_access(generatePkgLabel(provider.getPkgId().c_str()), trusted_label, "");
+
+ // install trusted app
+ InstallRequest trustedApp;
+ trustedApp.setAppId(user.getAppId().c_str());
+ trustedApp.setPkgId(user.getPkgId().c_str());
+ trustedApp.setAuthorId(author_id);
+ Api::install(trustedApp);
+
+ // check rules
+ check_exact_access(generateAppLabel(user.getAppId().c_str()), trusted_label, trusted_access);
+ check_exact_access(generatePkgLabel(user.getPkgId().c_str()), trusted_label, "");
+
+ // install untrusted app
+ InstallRequest untrustedApp;
+ untrustedApp.setAppId(untrusted.getAppId().c_str());
+ untrustedApp.setPkgId(untrusted.getPkgId().c_str());
+ Api::install(untrustedApp);
+
+ // check rules
+ check_exact_access(generateAppLabel(untrusted.getAppId().c_str()), trusted_label, "");
+ check_exact_access(generatePkgLabel(untrusted.getPkgId().c_str()), trusted_label, "");
+
+ // uninstall trusting app
+ Api::uninstall(trustingApp);
+
+ // there's still one app with author id, rules should be kept
+ check_exact_access("System", trusted_label, system_access);
+ check_exact_access("User", trusted_label, system_access);
+ check_exact_access(generateAppLabel(provider.getAppId().c_str()), trusted_label, "");
+ check_exact_access(generatePkgLabel(provider.getPkgId().c_str()), trusted_label, "");
+ check_exact_access(generateAppLabel(user.getAppId().c_str()), trusted_label, trusted_access);
+ check_exact_access(generatePkgLabel(user.getPkgId().c_str()), trusted_label, "");
+
+ Api::uninstall(trustedApp);
+
+ // no more apps with author id
+ check_exact_access("System", trusted_label, "");
+ check_exact_access("User", trusted_label, "");
+ check_exact_access(generateAppLabel(user.getAppId().c_str()), trusted_label, "");
+ check_exact_access(generatePkgLabel(user.getPkgId().c_str()), trusted_label, "");
+
+ Api::uninstall(untrustedApp);
+}
+
+
+RUNNER_TEST(security_manager_44_app_install_with_trusted_path_no_author_id)
+{
+ AppInstallHelper help("app44");
+ help.createInstallDir();
+ help.createTrustedDir();
+
+ // install app with shared/trusted dir but without authors id
+ InstallRequest app;
+ app.setAppId(help.getAppId().c_str());
+ app.setPkgId(help.getPkgId().c_str());
+ app.addPath(help.getTrustedDir().c_str(),
+ SECURITY_MANAGER_PATH_TRUSTED_RW);
+ Api::install(app, SECURITY_MANAGER_ERROR_INPUT_PARAM);
+}
+
int main(int argc, char *argv[])
{
return DPL::Test::TestRunnerSingleton::Instance().ExecTestRunner(argc, argv);