File: ScanningSession.h

package info (click to toggle)
scap-workbench 1.2.1-1
  • links: PTS, VCS
  • area: main
  • in suites: experimental
  • size: 3,292 kB
  • sloc: cpp: 7,519; sh: 205; xml: 38; ansic: 15; makefile: 13
file content (331 lines) | stat: -rw-r--r-- 11,873 bytes parent folder | download
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
/*
 * Copyright 2013 Red Hat Inc., Durham, North Carolina.
 * All Rights Reserved.
 *
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 *
 * Authors:
 *      Martin Preisler <mpreisle@redhat.com>
 */

#ifndef SCAP_WORKBENCH_SCANNING_SESSION_H_
#define SCAP_WORKBENCH_SCANNING_SESSION_H_

#include "ForwardDecls.h"
#include "Utils.h"

#include <QSet>
#include <QDir>
#include <map>

extern "C"
{
#include <xccdf_benchmark.h>
}

/**
 * @brief Encapsulates xccdf_session, tailoring and profile selection
 */
class ScanningSession
{
    public:
        ScanningSession();
        ~ScanningSession();

        /**
         * @brief Sets whether openscap validation should be skipped when loading
         */
        void setSkipValid(bool skipValid);

        /**
         * @brief Retrieves the internal xccdf_session structure
         *
         * @note Use of this method is discouraged.
         */
        struct xccdf_session* getXCCDFSession() const;

        /**
         * @brief Opens a specific file
         *
         * Passed file may be an XCCDF file (any openscap supported version)
         * or source datastream (SDS) file (any openscap supported version)
         */
        void openFile(const QString& path, bool reload = false);

        /**
         * @brief Closes currently opened file (if any)
         *
         * @throws Does not throw exceptions!
         */
        void closeFile();

        /**
         * @brief Retrieves full absolute path of the opened file
         */
        QString getOpenedFilePath() const;

        /**
         * @brief Retrieves full absolute path of the opened file
         */
        QString getOriginalFilePath() const;

        /**
         * @brief Retrives the closure set of the original file
         */
        QSet<QString> getOriginalClosure() const;

        /**
         * @brief A helper method that gets the longest common ancestor dir from a set of paths
         */
        static QDir getCommonAncestorDirectory(const QSet<QString>& paths);

        /**
         * @brief List of all files (paths) necessary to evaluate content that is currently loaded
         *
         * @note This does NOT include the tailoring file, has to be handled separately!
         * Returns XCCDF, OVAL, CPEs, anything that is necessary to evaluate.
         */
        QSet<QString> getOpenedFilesClosure() const;

        static void copyOrReplace(const QString& from, const QString& to);

        /**
         * @brief Saves opened file and its dependencies to given directory
         *
         * @note This method does save the tailoring file if any tailoring has been done
         * @return set of file paths we have saved
         */
        QSet<QString> saveOpenedFilesClosureToDir(const QDir& dir);

        /**
         * @brief Returns true if a file has been opened in this session
         *
         * @note Never throws exceptions!
         */
        bool fileOpened() const;

        /**
         * @brief Returns true if a file is loaded and is a source datastream, false otherwise
         */
        bool isSDS() const;

        /**
         * @brief Sets ID of datastream inside the SDS
         *
         * @par
         * This method will throw an exception if no file is opened or if opened file is
         * not a source datastream.
         */
        void setDatastreamID(const QString& datastreamID);
        QString getDatastreamID() const;

        /**
         * @brief Sets ID of XCCDF component inside the SDS
         *
         * @par
         * This method will throw an exception if no file is opened or if opened file is
         * not a source datastream.
         */
        void setComponentID(const QString& componentID);
        QString getComponentID() const;

        /**
         * @brief Retrieves title of effective benchmark that will be used for evaluation
         *
         * In case just an XCCDF file is loaded the title is of the benchmark in that XCCDF file.
         * In case a SDS is loaded the title of the benchmark in selected datastream and component is returned.
         */
        QString getBenchmarkTitle() const;

        /**
         * @brief Removes all tailoring (including the tailoring loaded from a file!)
         *
         * The result scanning session will scan as if only the input file was loaded.
         */
        void resetTailoring();
        void setTailoringFile(const QString& tailoringFile);
        void setTailoringComponentID(const QString& componentID);

        /**
         * @brief Saves tailoring to given file path
         *
         * @param userFile if true, the path will be kept as a user provided
         * path for the current tailoring file
         *
         * @see getUserTailoringFilePath
         */
        void saveTailoring(const QString& path, bool userFile);

        /**
         * @brief Exports tailoring file to a temporary path and returns the path
         *
         * @par
         * This method ensures that the file resides at the path returned. If no
         * tailoring file has been loaded, this method ensures a new one is created
         * and exported.
         */
        QString getTailoringFilePath();

        /**
         * @brief Returns the path of tailoring file most suitable for user presentation
         *
         * @par
         * This method returns the most friendly path for the user.
         * If a tailoring file has been loaded or saved by user, its path will be returned.
         * If a profile has been tailored but not saved yet, a temporary path is returned.
         * If there is no tailoring, an empty string is returned.
         */
        QString getUserTailoringFilePath();

        /**
         * @brief Generates guide and saves it to supplied path
         */
        void generateGuide(const QString& path);

        /**
         * @brief Exports guide to a temporary path and returns the path
         *
         * If called multiple times the temporary file is overwritten, at most
         * one temporary file will be created by this method. The file is destroyed
         * when ScanningSession is destroyed.
         */
        QString getGuideFilePath();

        /**
         * @brief Returns true if tailoring has been created and is valid
         *
         * @note A tailoring with 0 profiles isn't valid, the method will return false in that case
         * @note Can be caused by user changes or getTailoringFilePath called
         */
        bool hasTailoring() const;

        /**
         * @brief Returns a map of profile IDs that are available for selection
         *
         * IDs are mapped to respective profiles.
         *
         * Changing component ID and/or tailoring does invalidate the map. Available
         * profiles will change if tailoring or benchmark changes.
         *
         * @see setProfile
         */
        std::map<QString, struct xccdf_profile*> getAvailableProfiles();

        /**
         * @brief Sets which profile to use for scanning
         *
         * Will throw an exception if profile selection fails.
         *
         * @see getAvailableProfiles
         */
        void setProfile(const QString& profileID);

        /**
         * @brief Retrieves currently selected profile for scanning
         *
         * @see setProfile
         */
        QString getProfile() const;

        /**
         * @brief Checks whether a profile is selected
         *
         * (default) profile doesn't count as a profile in this method. This method
         * checks whether a profile other than (default) profile is selected.
         */
        bool profileSelected() const;

        /**
         * @brief Checks whether currently selected profile is a tailoring profile
         *
         * Tailoring profile comes from a tailoring file. It can either have ID of
         * a normal profile (thus shadowing it) or a completely different ID.
         *
         * A profile that is not a tailoring profile comes in the input file.
         */
        bool isSelectedProfileTailoring() const;

        /**
         * @brief Reloads the session if needed, datastream split is potentially done again
         *
         * @param forceReload if true, the reload is forced no matter what mSessionDirty is
         *
         * The main purpose of this method is to allow to reload the session when
         * parameters that affect "loading" of the session change. These parameters
         * are mainly datastream ID and component ID.
         *
         * mSessionDirty is automatically set to true whenever crucial parameters of
         * the session change. reloadSession will early out if reload is not necessary.
         */
        void reloadSession(bool forceReload = false) const;

        /**
         * @brief Creates a new profile, makes it inherit current profile
         *
         * @param shadowed if true the new profile will have the same ID
         * @param newIdBase ID of the new profile, only applicable if @a shadowed is false
         * @return created profile (can be passed to TailoringWindow for further tailoring)
         */
        struct xccdf_profile* tailorCurrentProfile(bool shadowed, const QString& newIdBase);

        const struct xccdf_version_info* getXCCDFVersionInfo();

    private:
        struct xccdf_benchmark* getXCCDFInputBenchmark();
        void ensureTailoringExists();

        /// This is our central point of interaction with openscap
        struct xccdf_session* mSession;
        /// Our own tailoring that may or may not initially be loaded from a file
        mutable struct xccdf_tailoring* mTailoring;

        /// Temporary copy of opened DS or XCCDF file
        SpacelessQTemporaryDir* mTempOpenDir;
        /// Path to temporary DS or XCCDF file
        QString mTempOpenPath;
        /// Path to original DS or XCCDF file
        QString mOriginalOpenPath;
        /// Closure of original DS or XCCDF file
        QSet<QString> mClosureOfOriginalFile;

        /// Temporary file provides auto deletion and a valid temp file path
        SpacelessQTemporaryFile mTailoringFile;
        /// Temporary file provides auto deletion and a valid temp file path
        SpacelessQTemporaryFile mGuideFile;

        /// Whether or not validation should be skipped
        bool mSkipValid;

        /// If true, the session will be reloaded
        mutable bool mSessionDirty;
        /// If true, we no longer allow changing tailoring entirely
        /// (loading new file, setting it to load from datastream, ...)
        /// user changes to the tailoring would be lost if we reloaded.
        bool mTailoringUserChanges;

        QString mUserTailoringFile;
        QString mUserTailoringCID;

        /// Gets the dependency closure of the specified file.
        void updateDependencyClosureOfFile(const QString& filePath, QSet<QString>& targetSet) const;

        /// Clones openFile(path) to a Temporary File
        void cloneToTemporaryFile(const QString& path);
        /// Closes mOpenFile if it is open
        void cleanTmpDir();
        /// Copies all files from the path into the temporary location
        void copyTempFiles(QString path, QString baseDirectory, const QFileInfo pathInfo);
};

#endif