QueryData genOSXPlist(QueryContext& context) { QueryData results; // Resolve file paths for EQUALS and LIKE operations. auto paths = context.constraints["path"].getAll(EQUALS); context.expandConstraints( "path", LIKE, paths, ([&](const std::string& pattern, std::set<std::string>& out) { std::vector<std::string> patterns; auto status = resolveFilePattern(pattern, patterns, GLOB_ALL | GLOB_NO_CANON); if (status.ok()) { for (const auto& resolved : patterns) { out.insert(resolved); } } return status; })); for (const auto& path : paths) { if (!pathExists(path).ok() || !isReadable(path).ok()) { VLOG(1) << "Cannot find/read defaults plist from path: " + path; continue; } pt::ptree tree; if (!osquery::parsePlist(path, tree).ok()) { VLOG(1) << "Could not parse plist: " + path; continue; } for (const auto& item : tree) { Row r; r["path"] = path; r["key"] = item.first; r["subkey"] = ""; genOSXPlistPrefValue(item.second, r, 0, results); } } return results; }
void expandFSPathConstraints(QueryContext& context, const std::string& path_column_name, std::set<std::string>& paths) { context.expandConstraints( path_column_name, LIKE, paths, ([&](const std::string& pattern, std::set<std::string>& out) { std::vector<std::string> patterns; auto status = resolveFilePattern(pattern, patterns, GLOB_ALL | GLOB_NO_CANON); if (status.ok()) { for (const auto& resolved : patterns) { out.insert(resolved); } } return status; })); }
QueryData genFile(QueryContext& context) { QueryData results; // Resolve file paths for EQUALS and LIKE operations. auto paths = context.constraints["path"].getAll(EQUALS); context.expandConstraints( "path", LIKE, paths, ([&](const std::string& pattern, std::set<std::string>& out) { std::vector<std::string> patterns; auto status = resolveFilePattern(pattern, patterns, GLOB_ALL | GLOB_NO_CANON); if (status.ok()) { for (const auto& resolved : patterns) { out.insert(resolved); } } return status; })); // Iterate through each of the resolved/supplied paths. for (const auto& path_string : paths) { fs::path path = path_string; genFileInfo(path, path.parent_path(), "", results); } // Resolve directories for EQUALS and LIKE operations. auto directories = context.constraints["directory"].getAll(EQUALS); context.expandConstraints( "directory", LIKE, directories, ([&](const std::string& pattern, std::set<std::string>& out) { std::vector<std::string> patterns; auto status = resolveFilePattern(pattern, patterns, GLOB_FOLDERS | GLOB_NO_CANON); if (status.ok()) { for (const auto& resolved : patterns) { out.insert(resolved); } } return status; })); // Now loop through constraints using the directory column constraint. for (const auto& directory_string : directories) { if (!isReadable(directory_string) || !isDirectory(directory_string)) { continue; } try { // Iterate over the directory and generate info for each regular file. fs::directory_iterator begin(directory_string), end; for (; begin != end; ++begin) { genFileInfo(begin->path(), directory_string, "", results); } } catch (const fs::filesystem_error& e) { continue; } } return results; }
QueryData genHash(QueryContext& context) { QueryData results; boost::system::error_code ec; // The query must provide a predicate with constraints including path or // directory. We search for the parsed predicate constraints with the equals // operator. auto paths = context.constraints["path"].getAll(EQUALS); context.expandConstraints( "path", LIKE, paths, ([&](const std::string& pattern, std::set<std::string>& out) { std::vector<std::string> patterns; auto status = resolveFilePattern(pattern, patterns, GLOB_ALL | GLOB_NO_CANON); if (status.ok()) { for (const auto& resolved : patterns) { out.insert(resolved); } } return status; })); // Iterate through the file paths, adding the hash results for (const auto& path_string : paths) { boost::filesystem::path path = path_string; if (!boost::filesystem::is_regular_file(path, ec)) { continue; } genHashForFile(path_string, path.parent_path().string(), context, results); } // Now loop through constraints using the directory column constraint. auto directories = context.constraints["directory"].getAll(EQUALS); context.expandConstraints( "directory", LIKE, directories, ([&](const std::string& pattern, std::set<std::string>& out) { std::vector<std::string> patterns; auto status = resolveFilePattern(pattern, patterns, GLOB_FOLDERS | GLOB_NO_CANON); if (status.ok()) { for (const auto& resolved : patterns) { out.insert(resolved); } } return status; })); // Iterate over the directory paths for (const auto& directory_string : directories) { boost::filesystem::path directory = directory_string; if (!boost::filesystem::is_directory(directory, ec)) { continue; } // Iterate over the directory files and generate a hash for each regular // file. boost::filesystem::directory_iterator begin(directory), end; for (; begin != end; ++begin) { if (boost::filesystem::is_regular_file(begin->path(), ec)) { genHashForFile( begin->path().string(), directory_string, context, results); } } } return results; }