summaryrefslogtreecommitdiff
path: root/source/slang/slang-serialize-container.h
blob: 4b35e931f3dd530725963522c31654f54ae3735e (plain)
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
// slang-serialize-container.h
#ifndef SLANG_SERIALIZE_CONTAINER_H
#define SLANG_SERIALIZE_CONTAINER_H

#include "../core/slang-riff.h"
#include "slang-serialize-types.h"
#include "slang-ir-insts.h"
#include "slang-profile.h"

namespace Slang {

class EndToEndCompileRequest;

/* The binary representation actually held in riff/file format*/
struct SerialContainerBinary
{
    struct Target
    {
        uint32_t target;
        uint32_t flags;
        uint32_t profile;
        uint32_t floatingPointMode;
    };

    struct EntryPoint
    {
        uint32_t name;
        uint32_t profile;
        uint32_t mangledName;
    };
};

struct SerialContainerDataModule
{
    RefPtr<IRModule> irModule;              ///< The IR for the module
    RefPtr<ASTBuilder> astBuilder;          ///< The astBuilder that owns the astRootNode
    NodeBase* astRootNode = nullptr;        ///< The module decl
    List<String> dependentFiles;
    SHA1::Digest digest;
};

/* Struct that holds all the data that can be held in a 'container' */
struct SerialContainerData
{
    struct Target
    {
        CodeGenTarget       codeGenTarget = CodeGenTarget::Unknown;
        SlangTargetFlags    flags = kDefaultTargetFlags;
        Profile             profile;
        FloatingPointMode   floatingPointMode = FloatingPointMode::Default;
    };
    
    struct TargetComponent
    {
        // IR module for a specific compilation target
        Target target;
        RefPtr<IRModule> irModule;
    };

    typedef SerialContainerDataModule Module;

    struct EntryPoint
    {
        Name* name = nullptr;
        Profile profile;
        String mangledName;
    };

    void clear()
    {
        entryPoints.clear();
        modules.clear();
        targetComponents.clear();
    }

    List<Module> modules;
    List<TargetComponent> targetComponents;
    List<EntryPoint> entryPoints;
};

struct SerialContainerUtil
{
    struct WriteOptions
    {
        SerialCompressionType compressionType = SerialCompressionType::VariableByteLite;                ///< If compression is used what type to use (only some parts can be compressed)
        SerialOptionFlags optionFlags = SerialOptionFlag::ASTModule | SerialOptionFlag::IRModule;       ///< Flags controlling what is written
        SourceManager* sourceManager = nullptr;                                                         ///< The source manager used for the SourceLoc in the input
    };

    struct ReadOptions
    {
        Session* session = nullptr;
        SourceManager* sourceManager = nullptr;
        NamePool* namePool = nullptr;
        SharedASTBuilder* sharedASTBuilder = nullptr;
        ASTBuilder* astBuilder = nullptr; // Optional. If not provided will create one in SerialContainerData.
        Linkage* linkage = nullptr;
        DiagnosticSink* sink = nullptr;
        bool readHeaderOnly = false;
        String modulePath;
    };

        /// Add module to outData
    static SlangResult addModuleToData(Module* module, const WriteOptions& options, SerialContainerData& outData);

        /// Get the serializable contents of the request as data
    static SlangResult addEndToEndRequestToData(EndToEndCompileRequest* request, const WriteOptions& options, SerialContainerData& outData);

        /// Convert front end request into something serializable
    static SlangResult addFrontEndRequestToData(FrontEndCompileRequest* request, const WriteOptions& options, SerialContainerData& outData);

        /// Write the data into the container
    static SlangResult write(const SerialContainerData& data, const WriteOptions& options, RiffContainer* container);

        /// Read the container into outData
    static SlangResult read(RiffContainer* container, const ReadOptions& options, const LoadedModuleDictionary* additionalLoadedModules, SerialContainerData& outData);

        /// Verify IR serialization
    static SlangResult verifyIRSerialize(IRModule* module, Session* session, const WriteOptions& options);

        /// Write the request to the stream
    static SlangResult write(FrontEndCompileRequest* frontEndReq, const WriteOptions& options, Stream* stream);
    static SlangResult write(EndToEndCompileRequest* request, const WriteOptions& options, Stream* stream);
    static SlangResult write(Module* module, const WriteOptions& options, Stream* stream);

};

} // namespace Slang

#endif