1 // Copyright (c) 2016 The WebM project authors. All Rights Reserved. 2 // 3 // Use of this source code is governed by a BSD-style license 4 // that can be found in the LICENSE file in the root of the source 5 // tree. An additional intellectual property rights grant can be found 6 // in the file PATENTS. All contributing project authors may 7 // be found in the AUTHORS file in the root of the source tree. 8 #ifndef INCLUDE_WEBM_CALLBACK_H_ 9 #define INCLUDE_WEBM_CALLBACK_H_ 10 11 #include <cstdint> 12 13 #include "./dom_types.h" 14 #include "./reader.h" 15 #include "./status.h" 16 17 /** 18 \file 19 The main callback type that receives parsing events. 20 */ 21 22 namespace webm { 23 24 /** 25 \addtogroup PUBLIC_API 26 @{ 27 */ 28 29 /** 30 The action to be performed when parsing an element. 31 */ 32 enum class Action { 33 /** 34 Read and parse the element. 35 */ 36 kRead, 37 38 /** 39 Skip the element. Skipped elements are not parsed or stored, and the callback 40 is not given any further notifications regarding the element. 41 */ 42 kSkip, 43 }; 44 45 /** 46 A callback that receives parsing events. 47 48 Every method that returns a `Status` should return `Status::kOkCompleted` when 49 the method has completed and parsing should continue. Returning any other value 50 will cause parsing to stop. Parsing may be resumed if the returned status was 51 not a parsing error (see `Status::is_parsing_error()`). When parsing is 52 resumed, the same `Callback` method will be called again. 53 54 Methods that take a `Reader` expect the implementation to consume (either via 55 `Reader::Read()` or `Reader::Skip()`) the specified number of bytes before 56 returning `Status::kOkCompleted`. Default implementations will call 57 `Reader::Skip()` to skip the specified number of bytes and the resulting 58 `Status` will be returned (unless it's `Status::kOkPartial`, in which case 59 `Reader::Skip()` will be called again to skip more data). 60 61 Throwing an exception from the member functions is permitted, though if the 62 exception will be caught and parsing resumed, then the reader should not 63 advance its position (for methods that take a `Reader`) before the exception is 64 thrown. When parsing is resumed, the same `Callback` method will be called 65 again. 66 67 Users should derive from this class and override member methods as needed. 68 */ 69 class Callback { 70 public: 71 virtual ~Callback() = default; 72 73 /** 74 Called when the parser starts a new element. This is called after the 75 elements ID and size has been parsed, but before any of its body has been 76 read (or validated). 77 78 Defaults to `Action::kRead` and returning `Status::kOkCompleted`. 79 80 \param metadata Metadata about the element that has just been encountered. 81 \param[out] action The action that should be taken when handling this 82 element. Will not be null. 83 */ 84 virtual Status OnElementBegin(const ElementMetadata& metadata, 85 Action* action); 86 87 /** 88 Called when the parser encounters an unknown element. 89 90 Defaults to calling (and returning the result of) `Reader::Skip()`. 91 92 \param metadata Metadata about the element. 93 \param reader The reader that should be used to consume data. Will not be 94 null. 95 \param[in,out] bytes_remaining The number of remaining bytes that need to be 96 consumed for the element. Will not be null. 97 \return `Status::kOkCompleted` when the element has been fully consumed and 98 `bytes_remaining` is now zero. 99 */ 100 virtual Status OnUnknownElement(const ElementMetadata& metadata, 101 Reader* reader, 102 std::uint64_t* bytes_remaining); 103 104 /** 105 Called when the parser encounters an `Id::kEbml` element and it has been 106 fully parsed. 107 108 Defaults to returning `Status::kOkCompleted`. 109 110 \param metadata Metadata about the element. 111 \param ebml The parsed element. 112 */ 113 virtual Status OnEbml(const ElementMetadata& metadata, const Ebml& ebml); 114 115 /** 116 Called when the parser encounters an Id::kVoid element. 117 118 Defaults to calling (and returning the result of) Reader::Skip. 119 120 \param metadata Metadata about the element. 121 \param reader The reader that should be used to consume data. Will not be 122 null. 123 \param[in,out] bytes_remaining The number of remaining bytes that need to be 124 consumed for the element. Will not be null. 125 \return `Status::kOkCompleted` when the element has been fully consumed and 126 `bytes_remaining` is now zero. 127 */ 128 virtual Status OnVoid(const ElementMetadata& metadata, Reader* reader, 129 std::uint64_t* bytes_remaining); 130 131 /** 132 Called when the parser starts an `Id::kSegment` element. 133 134 Defaults to `Action::kRead` and returning `Status::kOkCompleted`. 135 136 \param metadata Metadata about the element that has just been encountered. 137 \param[out] action The action that should be taken when handling this 138 element. Will not be null. 139 */ 140 virtual Status OnSegmentBegin(const ElementMetadata& metadata, 141 Action* action); 142 143 /** 144 Called when the parser encounters an `Id::kSeek` element and it has been 145 fully parsed. 146 147 Defaults to returning `Status::kOkCompleted`. 148 149 \param metadata Metadata about the element. 150 \param seek The parsed element. 151 */ 152 virtual Status OnSeek(const ElementMetadata& metadata, const Seek& seek); 153 154 /** 155 Called when the parser encounters an `Id::kInfo` element and it has been 156 fully parsed. 157 158 Defaults to returning `Status::kOkCompleted`. 159 160 \param metadata Metadata about the element. 161 \param info The parsed element. 162 */ 163 virtual Status OnInfo(const ElementMetadata& metadata, const Info& info); 164 165 /** 166 Called when the parser starts an `Id::kCluster` element. 167 168 Because Cluster elements should start with a Timecode (and optionally 169 PrevSize) child, this method is not invoked until a child BlockGroup or 170 SimpleBlock element is encountered (or the Cluster ends if no such child 171 exists). 172 173 Defaults to `Action::kRead` and returning `Status::kOkCompleted`. 174 175 \param metadata Metadata about the element. 176 \param cluster The element, as it has currently been parsed. 177 \param[out] action The action that should be taken when handling this 178 element. Will not be null. 179 */ 180 virtual Status OnClusterBegin(const ElementMetadata& metadata, 181 const Cluster& cluster, Action* action); 182 183 /** 184 Called when the parser starts an `Id::kSimpleBlock` element. 185 186 Defaults to `Action::kRead` and returning `Status::kOkCompleted`. 187 188 \param metadata Metadata about the element. 189 \param simple_block The parsed SimpleBlock header. 190 \param[out] action The action that should be taken when handling this 191 element. Will not be null. 192 */ 193 virtual Status OnSimpleBlockBegin(const ElementMetadata& metadata, 194 const SimpleBlock& simple_block, 195 Action* action); 196 197 /** 198 Called when the parser finishes an `Id::kSimpleBlock` element. 199 200 Defaults to returning `Status::kOkCompleted`. 201 202 \param metadata Metadata about the element. 203 \param simple_block The parsed SimpleBlock header. 204 */ 205 virtual Status OnSimpleBlockEnd(const ElementMetadata& metadata, 206 const SimpleBlock& simple_block); 207 208 /** 209 Called when the parser starts an `Id::kBlockGroup` element. 210 211 Defaults to `Action::kRead` and returning `Status::kOkCompleted`. 212 213 \param metadata Metadata about the element. 214 \param[out] action The action that should be taken when handling this 215 element. Will not be null. 216 */ 217 virtual Status OnBlockGroupBegin(const ElementMetadata& metadata, 218 Action* action); 219 220 /** 221 Called when the parser starts an `Id::kBlock` element. 222 223 Defaults to `Action::kRead` and returning `Status::kOkCompleted`. 224 225 \param metadata Metadata about the element. 226 \param block The parsed Block header. 227 \param[out] action The action that should be taken when handling this 228 element. Will not be null. 229 */ 230 virtual Status OnBlockBegin(const ElementMetadata& metadata, 231 const Block& block, Action* action); 232 233 /** 234 Called when the parser finishes an `Id::Block` element. 235 236 Defaults to returning `Status::kOkCompleted`. 237 238 \param metadata Metadata about the element. 239 \param block The parsed Block header. 240 */ 241 virtual Status OnBlockEnd(const ElementMetadata& metadata, 242 const Block& block); 243 244 /** 245 Called when the parser finishes an `Id::kBlockGroup` element. 246 247 Defaults to returning `Status::kOkCompleted`. 248 249 \param metadata Metadata about the element. 250 \param block_group The parsed element. 251 */ 252 virtual Status OnBlockGroupEnd(const ElementMetadata& metadata, 253 const BlockGroup& block_group); 254 255 /** 256 Called when the parser encounters a frame within a `Id::kBlock` or 257 `Id::kSimpleBlock` element. 258 259 Defaults to calling (and returning the result of) `Reader::Skip`. 260 261 \param metadata Metadata about the frame. 262 \param reader The reader that should be used to consume data. Will not be 263 null. 264 \param[in,out] bytes_remaining The number of remaining bytes that need to be 265 consumed for the frame. Will not be null. 266 \return `Status::kOkCompleted` when the frame has been fully consumed and 267 `bytes_remaining` is now zero. 268 */ 269 virtual Status OnFrame(const FrameMetadata& metadata, Reader* reader, 270 std::uint64_t* bytes_remaining); 271 272 /** 273 Called when the parser finishes an `Id::kCluster` element. 274 275 Defaults to returning `Status::kOkCompleted`. 276 277 \param metadata Metadata about the element. 278 \param cluster The parsed element. 279 */ 280 virtual Status OnClusterEnd(const ElementMetadata& metadata, 281 const Cluster& cluster); 282 283 /** 284 Called when the parser starts an `Id::kTrackEntry` element. 285 286 Defaults to returning `Status::kOkCompleted`. 287 288 \param metadata Metadata about the element. 289 \param track_entry The parsed element. 290 */ 291 virtual Status OnTrackEntry(const ElementMetadata& metadata, 292 const TrackEntry& track_entry); 293 294 /** 295 Called when the parser encounters an `Id::kCuePoint` element and it has been 296 fully parsed. 297 298 Defaults to returning `Status::kOkCompleted`. 299 300 \param metadata Metadata about the element. 301 \param cue_point The parsed element. 302 */ 303 virtual Status OnCuePoint(const ElementMetadata& metadata, 304 const CuePoint& cue_point); 305 306 /** 307 Called when the parser encounters an `Id::kEditionEntry` element and it has 308 been fully parsed. 309 310 Defaults to returning `Status::kOkCompleted`. 311 312 \param metadata Metadata about the element. 313 \param edition_entry The parsed element. 314 */ 315 virtual Status OnEditionEntry(const ElementMetadata& metadata, 316 const EditionEntry& edition_entry); 317 318 /** 319 Called when the parser encounters an `Id::kTag` element and it has been fully 320 parsed. 321 322 Defaults to returning `Status::kOkCompleted`. 323 324 \param metadata Metadata about the element. 325 \param tag The parsed element. 326 */ 327 virtual Status OnTag(const ElementMetadata& metadata, const Tag& tag); 328 329 /** 330 Called when the parser finishes an `Id::kSegment` element. 331 332 Defaults to returning `Status::kOkCompleted`. 333 334 \param metadata Metadata about the element. 335 */ 336 virtual Status OnSegmentEnd(const ElementMetadata& metadata); 337 338 protected: 339 /** 340 Calls (and returns the result of) `Reader::Skip()`, skipping (up to) the 341 requested number of bytes. 342 343 Unlike `Reader::Skip()`, this method may be called with `*bytes_remaining == 344 0`, which will result in `Status::kOkCompleted`. `Reader::Skip()` will be 345 called multiple times if it returns `Status::kOkPartial` until it returns a 346 different status (indicating the requested number of bytes has been fully 347 skipped or some error occurred). 348 349 \param reader The reader that should be used to skip data. Must not be null. 350 \param[in,out] bytes_remaining The number of remaining bytes that need to be 351 skipped. Must not be null. May be zero. 352 \return The result of `Reader::Skip()`. 353 */ 354 static Status Skip(Reader* reader, std::uint64_t* bytes_remaining); 355 }; 356 357 /** 358 @} 359 */ 360 361 } // namespace webm 362 363 #endif // INCLUDE_WEBM_CALLBACK_H_ 364