xref: /aosp_15_r20/external/pytorch/caffe2/serialize/versions.h (revision da0073e96a02ea20f0ac840b70461e3646d07c45)
1*da0073e9SAndroid Build Coastguard Worker #pragma once
2*da0073e9SAndroid Build Coastguard Worker #include <cstdint>
3*da0073e9SAndroid Build Coastguard Worker 
4*da0073e9SAndroid Build Coastguard Worker namespace caffe2 {
5*da0073e9SAndroid Build Coastguard Worker namespace serialize {
6*da0073e9SAndroid Build Coastguard Worker 
7*da0073e9SAndroid Build Coastguard Worker constexpr uint64_t kMinSupportedFileFormatVersion = 0x1L;
8*da0073e9SAndroid Build Coastguard Worker 
9*da0073e9SAndroid Build Coastguard Worker constexpr uint64_t kMaxSupportedFileFormatVersion = 0xAL;
10*da0073e9SAndroid Build Coastguard Worker 
11*da0073e9SAndroid Build Coastguard Worker // Versions (i.e. why was the version number bumped?)
12*da0073e9SAndroid Build Coastguard Worker 
13*da0073e9SAndroid Build Coastguard Worker // Note [Dynamic Versions and torch.jit.save vs. torch.save]
14*da0073e9SAndroid Build Coastguard Worker //
15*da0073e9SAndroid Build Coastguard Worker // Our versioning scheme has a "produced file format version" which
16*da0073e9SAndroid Build Coastguard Worker // describes how an archive is to be read. The version written in an archive
17*da0073e9SAndroid Build Coastguard Worker // is at least this current produced file format version, but may be greater
18*da0073e9SAndroid Build Coastguard Worker // if it includes certain symbols. We refer to these conditional versions
19*da0073e9SAndroid Build Coastguard Worker // as "dynamic," since they are identified at runtime.
20*da0073e9SAndroid Build Coastguard Worker //
21*da0073e9SAndroid Build Coastguard Worker // Dynamic versioning is useful when an operator's semantics are updated.
22*da0073e9SAndroid Build Coastguard Worker // When using torch.jit.save we want those semantics to be preserved. If
23*da0073e9SAndroid Build Coastguard Worker // we bumped the produced file format version on every change, however,
24*da0073e9SAndroid Build Coastguard Worker // then older versions of PyTorch couldn't read even simple archives, like
25*da0073e9SAndroid Build Coastguard Worker // a single tensor, from newer versions of PyTorch. Instead, we
26*da0073e9SAndroid Build Coastguard Worker // assign dynamic versions to these changes that override the
27*da0073e9SAndroid Build Coastguard Worker // produced file format version as needed. That is, when the semantics
28*da0073e9SAndroid Build Coastguard Worker // of torch.div changed it was assigned dynamic version 4, and when
29*da0073e9SAndroid Build Coastguard Worker // torch.jit.saving modules that use torch.div those archives also have
30*da0073e9SAndroid Build Coastguard Worker // (at least) version 4. This prevents earlier versions of PyTorch
31*da0073e9SAndroid Build Coastguard Worker // from accidentally performing the wrong kind of division. Modules
32*da0073e9SAndroid Build Coastguard Worker // that don't use torch.div or other operators with dynamic versions
33*da0073e9SAndroid Build Coastguard Worker // can write the produced file format version, and these programs will
34*da0073e9SAndroid Build Coastguard Worker // run as expected on earlier versions of PyTorch.
35*da0073e9SAndroid Build Coastguard Worker //
36*da0073e9SAndroid Build Coastguard Worker // While torch.jit.save attempts to preserve operator semantics,
37*da0073e9SAndroid Build Coastguard Worker // torch.save does not. torch.save is analogous to pickling Python, so
38*da0073e9SAndroid Build Coastguard Worker // a function that uses torch.div will have different behavior if torch.saved
39*da0073e9SAndroid Build Coastguard Worker // and torch.loaded across PyTorch versions. From a technical perspective,
40*da0073e9SAndroid Build Coastguard Worker // torch.save ignores dynamic versioning.
41*da0073e9SAndroid Build Coastguard Worker 
42*da0073e9SAndroid Build Coastguard Worker // 1. Initial version
43*da0073e9SAndroid Build Coastguard Worker // 2. Removed op_version_set version numbers
44*da0073e9SAndroid Build Coastguard Worker // 3. Added type tags to pickle serialization of container types
45*da0073e9SAndroid Build Coastguard Worker // 4. (Dynamic) Stopped integer division using torch.div
46*da0073e9SAndroid Build Coastguard Worker //      (a versioned symbol preserves the historic behavior of versions 1--3)
47*da0073e9SAndroid Build Coastguard Worker // 5. (Dynamic) Stops torch.full inferring a floating point dtype
48*da0073e9SAndroid Build Coastguard Worker //      when given bool or integer fill values.
49*da0073e9SAndroid Build Coastguard Worker // 6. Write version string to `./data/version` instead of `version`.
50*da0073e9SAndroid Build Coastguard Worker 
51*da0073e9SAndroid Build Coastguard Worker // [12/15/2021]
52*da0073e9SAndroid Build Coastguard Worker // kProducedFileFormatVersion is set to 7 from 3 due to a different
53*da0073e9SAndroid Build Coastguard Worker // interpretation of what file format version is.
54*da0073e9SAndroid Build Coastguard Worker // Whenever there is new upgrader introduced,
55*da0073e9SAndroid Build Coastguard Worker // this number should be bumped.
56*da0073e9SAndroid Build Coastguard Worker // The reasons that version is bumped in the past:
57*da0073e9SAndroid Build Coastguard Worker //     1. aten::div is changed at version 4
58*da0073e9SAndroid Build Coastguard Worker //     2. aten::full is changed at version 5
59*da0073e9SAndroid Build Coastguard Worker //     3. torch.package uses version 6
60*da0073e9SAndroid Build Coastguard Worker //     4. Introduce new upgrader design and set the version number to 7
61*da0073e9SAndroid Build Coastguard Worker //        mark this change
62*da0073e9SAndroid Build Coastguard Worker // --------------------------------------------------
63*da0073e9SAndroid Build Coastguard Worker // We describe new operator version bump reasons here:
64*da0073e9SAndroid Build Coastguard Worker // 1) [01/24/2022]
65*da0073e9SAndroid Build Coastguard Worker //     We bump the version number to 8 to update aten::linspace
66*da0073e9SAndroid Build Coastguard Worker //     and aten::linspace.out to error out when steps is not
67*da0073e9SAndroid Build Coastguard Worker //     provided. (see: https://github.com/pytorch/pytorch/issues/55951)
68*da0073e9SAndroid Build Coastguard Worker // 2) [01/30/2022]
69*da0073e9SAndroid Build Coastguard Worker //     Bump the version number to 9 to update aten::logspace and
70*da0073e9SAndroid Build Coastguard Worker //     and aten::logspace.out to error out when steps is not
71*da0073e9SAndroid Build Coastguard Worker //     provided. (see: https://github.com/pytorch/pytorch/issues/55951)
72*da0073e9SAndroid Build Coastguard Worker // 3) [02/11/2022]
73*da0073e9SAndroid Build Coastguard Worker //     Bump the version number to 10 to update aten::gelu and
74*da0073e9SAndroid Build Coastguard Worker //     and aten::gelu.out to support the new approximate kwarg.
75*da0073e9SAndroid Build Coastguard Worker //     (see: https://github.com/pytorch/pytorch/pull/61439)
76*da0073e9SAndroid Build Coastguard Worker constexpr uint64_t kProducedFileFormatVersion = 0xAL;
77*da0073e9SAndroid Build Coastguard Worker 
78*da0073e9SAndroid Build Coastguard Worker // Absolute minimum version we will write packages. This
79*da0073e9SAndroid Build Coastguard Worker // means that every package from now on will always be
80*da0073e9SAndroid Build Coastguard Worker // greater than this number.
81*da0073e9SAndroid Build Coastguard Worker constexpr uint64_t kMinProducedFileFormatVersion = 0x3L;
82*da0073e9SAndroid Build Coastguard Worker 
83*da0073e9SAndroid Build Coastguard Worker // The version we write when the archive contains bytecode.
84*da0073e9SAndroid Build Coastguard Worker // It must be higher or eq to kProducedFileFormatVersion.
85*da0073e9SAndroid Build Coastguard Worker // Because torchscript changes is likely introduce bytecode change.
86*da0073e9SAndroid Build Coastguard Worker // If kProducedFileFormatVersion is increased, kProducedBytecodeVersion
87*da0073e9SAndroid Build Coastguard Worker // should be increased too. The relationship is:
88*da0073e9SAndroid Build Coastguard Worker // kMaxSupportedFileFormatVersion >= (most likely ==) kProducedBytecodeVersion
89*da0073e9SAndroid Build Coastguard Worker //   >= kProducedFileFormatVersion
90*da0073e9SAndroid Build Coastguard Worker // If a format change is forward compatible (still readable by older
91*da0073e9SAndroid Build Coastguard Worker // executables), we will not increment the version number, to minimize the
92*da0073e9SAndroid Build Coastguard Worker // risk of breaking existing clients. TODO: A better way would be to allow
93*da0073e9SAndroid Build Coastguard Worker // the caller that creates a model to specify a maximum version that its
94*da0073e9SAndroid Build Coastguard Worker // clients can accept.
95*da0073e9SAndroid Build Coastguard Worker // Versions:
96*da0073e9SAndroid Build Coastguard Worker //  0x1L: Initial version
97*da0073e9SAndroid Build Coastguard Worker //  0x2L: (Comment missing)
98*da0073e9SAndroid Build Coastguard Worker //  0x3L: (Comment missing)
99*da0073e9SAndroid Build Coastguard Worker //  0x4L: (update) Added schema to function tuple. Forward-compatible change.
100*da0073e9SAndroid Build Coastguard Worker //  0x5L: (update) Update bytecode is sharing constant tensor files from
101*da0073e9SAndroid Build Coastguard Worker //  torchscript, and only serialize extra tensors that are not in the
102*da0073e9SAndroid Build Coastguard Worker //  torchscript constant table. Also update tensor storage schema adapting to
103*da0073e9SAndroid Build Coastguard Worker //  the unify format, the root key of tensor storage is updated from {index} to
104*da0073e9SAndroid Build Coastguard Worker //  {the_pointer_value_the_tensor.storage}, for example:
105*da0073e9SAndroid Build Coastguard Worker //  `140245072983168.storage` Forward-compatibility change.
106*da0073e9SAndroid Build Coastguard Worker //  0x6L: Implicit opereator versioning using number of specified argument.
107*da0073e9SAndroid Build Coastguard Worker //  Refer to the summary of https://github.com/pytorch/pytorch/pull/56845 for
108*da0073e9SAndroid Build Coastguard Worker //  details.
109*da0073e9SAndroid Build Coastguard Worker //  0x7L: Enable support for operators with default arguments plus out
110*da0073e9SAndroid Build Coastguard Worker //  arguments. Refer. See https://github.com/pytorch/pytorch/pull/63651 for
111*da0073e9SAndroid Build Coastguard Worker //  details.
112*da0073e9SAndroid Build Coastguard Worker //  0x8L: Emit promoted operators as instructions. See
113*da0073e9SAndroid Build Coastguard Worker //  https://github.com/pytorch/pytorch/pull/71662 for details.
114*da0073e9SAndroid Build Coastguard Worker //  0x9L: Change serialization format from pickle to format This version is to
115*da0073e9SAndroid Build Coastguard Worker //  serve migration. v8 pickle and v9 flatbuffer are the same. Refer to the
116*da0073e9SAndroid Build Coastguard Worker //  summary of https://github.com/pytorch/pytorch/pull/75201 for more details.
117*da0073e9SAndroid Build Coastguard Worker constexpr uint64_t kProducedBytecodeVersion = 0x8L;
118*da0073e9SAndroid Build Coastguard Worker 
119*da0073e9SAndroid Build Coastguard Worker // static_assert(
120*da0073e9SAndroid Build Coastguard Worker //     kProducedBytecodeVersion >= kProducedFileFormatVersion,
121*da0073e9SAndroid Build Coastguard Worker //     "kProducedBytecodeVersion must be higher or equal to
122*da0073e9SAndroid Build Coastguard Worker //     kProducedFileFormatVersion.");
123*da0073e9SAndroid Build Coastguard Worker 
124*da0073e9SAndroid Build Coastguard Worker // Introduce kMinSupportedBytecodeVersion and kMaxSupportedBytecodeVersion
125*da0073e9SAndroid Build Coastguard Worker // for limited backward/forward compatibility support of bytecode. If
126*da0073e9SAndroid Build Coastguard Worker // kMinSupportedBytecodeVersion <= model_version <= kMaxSupportedBytecodeVersion
127*da0073e9SAndroid Build Coastguard Worker // (in loader), we should support this model_version. For example, we provide a
128*da0073e9SAndroid Build Coastguard Worker // wrapper to handle an updated operator.
129*da0073e9SAndroid Build Coastguard Worker constexpr uint64_t kMinSupportedBytecodeVersion = 0x4L;
130*da0073e9SAndroid Build Coastguard Worker constexpr uint64_t kMaxSupportedBytecodeVersion = 0x9L;
131*da0073e9SAndroid Build Coastguard Worker 
132*da0073e9SAndroid Build Coastguard Worker } // namespace serialize
133*da0073e9SAndroid Build Coastguard Worker } // namespace caffe2
134