1/* 2 * Copyright 2001-2006 Ingo Weinhold, bonefish@cs.tu-berlin.de 3 * Copyright 2013 Haiku Inc. All rights reserved. 4 * Distributed under the terms of the MIT License. 5 * 6 * Authors: 7 * John Scipione, jscipione@gmail.com 8 * Ingo Weinhold, bonefish@users.sf.net 9 * 10 * Corresponds to: 11 * headers/os/storage/Resources.h hrev45283 12 * src/kits/storage/Resources.cpp hrev45283 13 */ 14 15 16/*! 17 \file Resources.h 18 \ingroup storage 19 \ingroup libbe 20 \brief Provides the BResources class. 21*/ 22 23 24/*! 25 \class BResources 26 \ingroup storage 27 \ingroup libbe 28 \brief Provides an interface for accessing and manipulating file 29 resources. 30 31 BResources delegates most of the work to ResourcesContainer and 32 ResourceFile. The former manages a collections of ResourceItem objects's 33 (the actual resources) whereas the latter provides the file I/O 34 functionality. 35 36 An InitCheck() method is not needed, since a BResources object will 37 never be invalid. It always serves as a resources container, even if 38 it is not associated with a file. It is always possible to WriteTo() 39 the resources BResources contains to a file (a valid one of course). 40*/ 41 42 43/*! 44 \fn BResources::BResources() 45 \brief Creates an uninitialized BResources object. 46 47 \see SetTo() 48*/ 49 50 51/*! 52 \fn BResources::BResources(const BFile* file, bool clobber) 53 \brief Creates a BResources object that represents the resources of the 54 supplied \a file. 55 56 If the \a clobber argument is \c true, the data of the file are erased 57 and it is turned into an empty resource file. Otherwise \a file 58 must refer either to a resource file or to an executable (ELF or PEF 59 binary). If the file has been opened \c B_READ_ONLY, only read access 60 to its resources is possible. 61 62 The BResources object makes a copy of \a file, that is the caller remains 63 owner of the BFile object. 64 65 \param file The file to create a BResource object from. 66 \param clobber If \c true, the data of the file are erased. 67*/ 68 69 70/*! 71 \fn BResources::BResources(const char* path, bool clobber) 72 \brief Creates a BResources object that represents the resources of the 73 file referenced by the supplied \a path. 74 75 If the \a clobber argument is \c true, the data of the file are erased 76 and it is turned into an empty resource file. Otherwise \a path 77 must refer either to a resource file or to an executable (ELF or PEF 78 binary). 79 80 \param path A path referring to the file to create a BResource object 81 from. 82 \param clobber If \c true, the data of the file are erased. 83*/ 84 85 86/*! 87 \fn BResources::BResources(const entry_ref* ref, bool clobber) 88 \brief Creates a BResources object that represents the resources of the 89 file referenced by the supplied \a ref. 90 91 If the \a clobber argument is \c true, the data of the file are erased 92 and it is turned into an empty resource file. Otherwise \a ref 93 must refer either to a resource file or to an executable (ELF or PEF 94 binary). 95 96 \param ref An entry_ref referring to the file to create a BResource object 97 from. 98 \param clobber If \c true, the data of the file are erased. 99*/ 100 101 102/*! 103 \fn BResources::~BResources() 104 \brief Destroys the BResources object and frees any associated resources. 105 106 Sync() is first called to make sure that the changes are written back to 107 the file. 108*/ 109 110 111/*! 112 \name SetTo methods 113 114 What happens, if \a clobber is \c true, depends on the type of the file. 115 If the file is capable of containing resources, that is, is a resource 116 file or an executable (ELF or PEF), its resources are removed. Otherwise 117 the file's data are erased and it is turned into an empty resource file. 118 If \a clobber is \c false, \a file must refer to a file that is capable 119 of containing resources. 120 121 If the file has been opened \c B_READ_ONLY, only read access 122 to its resources is possible. 123 124 The BResources object makes a copy of \a file, that is the caller remains 125 owner of the BFile object. 126*/ 127 128 129//! @{ 130 131 132/*! 133 \fn status_t BResources::SetTo(const BFile* file, bool clobber) 134 \brief Initializes the BResources object to represent the resources of 135 the supplied file. 136 137 \param file The file to initialize the BResources object from. 138 \param clobber If \c true, the data of the file are erased. 139 140 \returns A status code. 141 \retval B_OK Everything went fine. 142 \retval B_BAD_VALUE \a file was \c NULL or uninitialized. 143 \retval B_ERROR Failed to initialize the object. 144*/ 145 146 147/*! 148 \fn status_t BResources::SetTo(const char* path, bool clobber) 149 \brief Initialized the BResources object to represent the resources of 150 the file referred to by the supplied \a path. 151 152 \param path A path referring to the file to create a BResource object 153 from. 154 \param clobber If \c true, the data of the file are erased. 155 156 \returns A status code. 157 \retval B_OK Everything went fine. 158 \retval B_BAD_VALUE \a path was \c NULL. 159 \retval B_ENTRY_NOT_FOUND The file referenced by \a path couldn't be found. 160 \retval B_ERROR Failed to initialize the object. 161*/ 162 163 164/*! 165 \fn status_t BResources::SetTo(const entry_ref* ref, bool clobber) 166 \brief Initialized the BResources object to represent the resources of the 167 file referenced by the supplied \a ref. 168 169 \param ref An entry_ref referring to the file to create a BResource object 170 from. 171 \param clobber If \c true, the data of the file are erased. 172 173 \returns A status code. 174 \retval B_OK Everything went fine. 175 \retval B_BAD_VALUE \a ref was \c NULL. 176 \retval B_ENTRY_NOT_FOUND The file referenced by \a ref couldn't be found. 177 \retval B_ERROR Failed to initialize the object. 178*/ 179 180 181/*! 182 \fn status_t BResources::SetToImage(image_id image, bool clobber) 183 \brief Initialized the BResources object to represent the resources of 184 the file from which the specified \a image has been loaded. 185 186 If \a clobber is \c true, the file's resources are removed. 187 188 \param image ID of a loaded image. 189 \param clobber If \c true, the data of the file are erased. 190 191 \returns A status code. 192 \retval B_OK Everything went fine. 193 \retval B_ENTRY_NOT_FOUND The file referenced by \a ref couldn't be found. 194 \retval B_ERROR Failed to initialize the object. 195*/ 196 197 198/*! 199 \fn status_t BResources::SetToImage(const void* codeOrDataPointer, 200 bool clobber) 201 \brief Initialized the BResources object to represent the resources of 202 the file from which the specified pointer has been loaded. 203 204 The image belongs to the current team and is identified by a pointer into 205 it's code (aka text) or data segment, i.e. any pointer to a function or a 206 static (or global) variable will do. 207 208 If \a clobber is \c true, the file's resources are removed. 209 210 \param codeOrDataPointer Pointer to the text or data segment of the image. 211 \param clobber If \c true, the data of the file are erased. 212 213 \returns A status code. 214 \retval B_OK Everything went fine. 215 \retval B_BAD_VALUE \a codeOrDataPointer was \c NULL. 216 \retval B_ENTRY_NOT_FOUND The image or the file couldn't be found. 217 \retval B_ERROR Failed to initialize the object. 218*/ 219 220 221//! @} 222 223 224/*! 225 \name Constructor helper methods 226*/ 227 228 229//! @{ 230 231 232/*! 233 \fn void BResources::Unset() 234 \brief Returns the BResources object to an uninitialized state. 235 236 If the object represented resources that had been modified, the data are 237 written back to the file. 238 239 \note This method is not found in BeOS R5. 240*/ 241 242 243/*! 244 \fn status_t BResources::InitCheck() const 245 \brief Gets the initialization status of the object. 246 247 Unlike other Storage Kit classes a BResources object is always properly 248 initialized, unless it couldn't allocate memory for some important 249 internal structures. Thus even after a call to SetTo() that reported an 250 error, InitCheck() is likely to return \c B_OK. 251 252 \note This method is not found in BeOS R5. 253 254 \return \c B_OK if the objects is properly initialized, 255 \c B_NO_MEMORY otherwise. 256*/ 257 258 259//! @} 260 261 262/*! 263 \name LoadResources methods 264 265 A resource is loaded into memory only once. A second call with the same 266 parameters will result in the same pointer. The BResources object is the 267 owner of the allocated memory and the pointer to it will be valid until 268 the object is destroyed or the resource is removed or modified. 269*/ 270 271 272//! @{ 273 274 275/*! 276 \fn const void* BResources::LoadResource(type_code type, int32 id, 277 size_t* _size) 278 \brief Loads a resource identified by \a type and \a id into memory. 279 280 \param type The type of the resource to be loaded. 281 \param id The ID of the resource to be loaded. 282 \param _size A pointer to a variable into which the size of the resource 283 shall be written. 284 285 \return A pointer to the resource data if everything went fine, or 286 \c NULL if the file does not have a resource that matches the 287 parameters or an error occurred. 288*/ 289 290 291/*! 292 \fn const void* BResources::LoadResource(type_code type, const char* name, 293 size_t* _size) 294 \brief Loads a resource identified by \a type and \a name into memory. 295 296 \note Since a type and name pair may not identify a resource uniquely, 297 this method always returns the first resource that matches the 298 parameters, that is the one with the smallest index. 299 300 \param type The type of the resource to be loaded. 301 \param name The name of the resource to be loaded. 302 \param _size A pointer to a variable into which the size of the resource 303 shall be written. 304 305 \return A pointer to the resource data if everything went fine, or 306 \c NULL if the file does not have a resource that matches the 307 parameters or an error occurred. 308*/ 309 310 311/*! 312 \fn status_t BResources::PreloadResourceType(type_code type) 313 \brief Loads all resources of the specified \a type into memory. 314 315 If \a type is 0, all resources are loaded. This might be useful for 316 performance reasons. 317 318 \param type The type of resources to be loaded. 319 320 \returns One of the following status codes or the negation of the number 321 of errors that occurred. 322 \retval B_OK Everything went fine. 323 \retval B_BAD_FILE The resource map is empty??? 324*/ 325 326 327//! @} 328 329 330/*! 331 \fn const BFile& BResources::File() const 332 \brief Gets a reference to the internal BFile object. 333 334 \return A reference to the internal BFile object. 335*/ 336 337 338/*! 339 \fn status_t BResources::Sync() 340 \brief Writes all changes to the resources to the file. 341 342 Since AddResource() and RemoveResource() may change the resources only in 343 memory, this method can be used to make sure, that all changes are 344 actually written to the file. 345 346 The BResources object's destructor calls Sync() before cleaning up. 347 348 \note When a resource is written to the file its data is converted 349 to the endianness of the file. When reading a resource the 350 data is converted to the endianness of the host. This of course 351 only works for known types, i.e. those that swap_data() is able to 352 understand. 353 354 \returns A status code. 355 \retval B_OK Everything went fine. 356 \retval B_BAD_FILE The resource map is empty??? 357 \retval B_FILE_ERROR A file error occurred. 358 \retval B_IO_ERROR An error occurred while writing the resources. 359 \retval B_NOT_ALLOWED The file was opened read only. 360*/ 361 362 363/*! 364 \fn status_t BResources::MergeFrom(BFile* fromFile) 365 \brief Adds the resources of \a fromFile to the internal file of the 366 BResources object. 367 368 \param fromFile The file whose resources are to be be copied from. 369 370 \returns A status code. 371 \retval B_OK Everything went fine. 372 \retval B_BAD_FILE The resource map is empty??? 373 \retval B_BAD_VALUE \a fromFile was \c NULL. 374 \retval B_FILE_ERROR A file error occurred. 375 \retval B_IO_ERROR An error occurred while writing the resources. 376*/ 377 378 379/*! 380 \fn status_t BResources::WriteTo(BFile* file) 381 \brief Writes the resources to a new file. 382 383 The resources formerly contained in the target file (if any) are erased. 384 When the method returns, the BResources object refers to the new file. 385 386 \warning If the resources have been modified, but Sync() has not been 387 called, the old file remains unmodified. 388 389 \param file The file that the resources shall be written to. 390 391 \return \c B_OK if everything went fine or an error code otherwise. 392*/ 393 394 395/*! 396 \fn status_t BResources::AddResource(type_code type, int32 id, 397 const void* data, size_t length, const char* name) 398 \brief Adds a new resource to the file. 399 400 If a resource already exists with the same \a type and \a id it is 401 replaced. The caller keeps the ownership of the supplied chunk of memory 402 containing the resource data. 403 404 Supplying an empty \a name (\c "") is equivalent to supplying a \c NULL 405 \a name. 406 407 \param type The type of the resource. 408 \param id The ID of the resource. 409 \param data The resource data. 410 \param length The size of the data in bytes. 411 \param name The name of the resource (may be empty or \c NULL). 412 413 \returns A status code. 414 \retval B_OK Everything went fine. 415 \retval B_BAD_VALUE \a data was \c NULL. 416 \retval B_FILE_ERROR A file error occurred. 417 \retval B_NO_MEMORY Not enough memory for the operation. 418 \retval B_NOT_ALLOWED The file was opened read only. 419*/ 420 421 422/*! 423 \fn bool BResources::HasResource(type_code type, int32 id) 424 \brief Returns whether the file contains a resource with the specified 425 \a type and \a id. 426 427 \param type The resource type to check. 428 \param id The ID of the resource to check. 429 430 \return \c true if the file contains a matching resource, 431 \c false otherwise. 432*/ 433 434 435/*! 436 \fn bool BResources::HasResource(type_code type, const char* name) 437 \brief Returns whether the file contains a resource with the specified 438 \a type and \a name. 439 440 \param type The resource type to check. 441 \param name The name of the resource to check. 442 443 \return \c true, if the file contains a matching resource, 444 \c false otherwise. 445*/ 446 447 448/*! 449 \fn bool BResources::GetResourceInfo(int32 byIndex, type_code* typeFound, 450 int32* idFound, const char** nameFound, size_t* lengthFound) 451 \brief Gets information about a resource identified by \a byindex. 452 453 \param byIndex The index of the resource in the file. 454 \param typeFound A pointer to a variable the type of the found resource 455 shall be written into. 456 \param idFound A pointer to a variable the ID of the found resource 457 shall be written into. 458 \param nameFound A pointer to a variable the name pointer of the found 459 resource shall be written into. 460 \param lengthFound A pointer to a variable the data size of the found 461 resource shall be written into. 462 463 \return \c true, if a matching resource could be found, 464 \c false otherwise. 465*/ 466 467 468/*! 469 \fn bool BResources::GetResourceInfo(type_code byType, int32 andIndex, 470 int32* idFound, const char** nameFound, size_t* lengthFound) 471 \brief Gets information about a resource identified by \a byType and 472 \a andIndex. 473 474 \param byType The resource type. 475 \param andIndex The index into a array of resources of type \a byType. 476 \param idFound A pointer to a variable the ID of the found resource 477 shall be written into. 478 \param nameFound A pointer to a variable the name pointer of the found 479 resource shall be written into. 480 \param lengthFound A pointer to a variable the data size of the found 481 resource shall be written into. 482 483 \return \c true, if a matching resource could be found, 484 \c false otherwise. 485*/ 486 487 488/*! 489 \fn bool BResources::GetResourceInfo(type_code byType, int32 andID, 490 const char** nameFound, size_t* lengthFound) 491 \brief Gets information about a resource identified by \a byType and 492 \a andID. 493 494 \param byType The resource type. 495 \param andID The resource ID. 496 \param nameFound A pointer to a variable the name pointer of the found 497 resource shall be written into. 498 \param lengthFound A pointer to a variable the data size of the found 499 resource shall be written into. 500 501 \return \c true, if a matching resource could be found, 502 \c false otherwise. 503*/ 504 505 506/*! 507 \fn bool BResources::GetResourceInfo(type_code byType, const char* andName, 508 int32* idFound, size_t* lengthFound) 509 \brief Gets information about a resource identified by \a byType and 510 \a andName. 511 512 \param byType The resource type. 513 \param andName The resource name. 514 \param idFound A pointer to a variable the ID of the found resource 515 shall be written into. 516 \param lengthFound A pointer to a variable the data size of the found 517 resource shall be written into. 518 519 \return \c true, if a matching resource could be found, 520 \c false otherwise. 521*/ 522 523 524/*! 525 \fn bool BResources::GetResourceInfo(const void* byPointer, 526 type_code* typeFound, int32* idFound, size_t* lengthFound, 527 const char** nameFound) 528 \brief Gets information about a resource identified by \a byPointer. 529 530 \param byPointer The pointer to the resource data (formerly returned by 531 LoadResource()). 532 \param typeFound A pointer to a variable the type of the found resource 533 shall be written into. 534 \param idFound A pointer to a variable the ID of the found resource 535 shall be written into. 536 \param lengthFound A pointer to a variable the data size of the found 537 resource shall be written into. 538 \param nameFound A pointer to a variable the name pointer of the found 539 resource shall be written into. 540 541 \return \c true, if a matching resource could be found, 542 \c false otherwise. 543*/ 544 545 546/*! 547 \fn status_t BResources::RemoveResource(const void* resource) 548 \brief Removes a resource identified by \a resource. 549 550 \param resource The pointer to the resource data (formerly returned by 551 LoadResource()). 552 553 \return A status code. 554 \retval B_OK Everything went fine. 555 \retval B_BAD_VALUE \a resource was \c NULL or invalid (didn't point to 556 any resource data of this file). 557 \retval B_ERROR An error occurred while removing the resource. 558 \retval B_FILE_ERROR A file error occurred. 559 \retval B_NOT_ALLOWED The file was opened read only. 560*/ 561 562 563/*! 564 \fn status_t BResources::RemoveResource(type_code type, int32 id) 565 \brief Removes a resource identified by \a type and \a id. 566 567 \param type The type of the resource to remove. 568 \param id The ID of the resource to remove. 569 570 \return A status code. 571 \retval B_OK Everything went fine. 572 \retval B_BAD_VALUE No such resource was found. 573 \retval B_ERROR An error occurred while removing the resource. 574 \retval B_FILE_ERROR A file error occurred. 575 \retval B_NOT_ALLOWED The file was opened read only. 576*/ 577 578 579/*! 580 \name Deprecated methods 581 582 These methods are deprecated and should not be used as there is a better 583 method. See the method description for the replacement method to use. 584*/ 585 586 587//! @{ 588 589 590/*! 591 \fn status_t BResources::WriteResource(type_code type, int32 id, 592 const void* data, off_t offset, size_t length) 593 \brief Writes data into an existing resource. 594 (deprecated, use AddResource() instead) 595 596 \deprecated Use AddResource() instead. 597 598 If writing the data would exceed the bounds of the resource, it is 599 enlarged respectively. If \a offset is past the end of the resource, 600 padding with unspecified data is inserted. 601 602 \param type The type of the resource to write data to. 603 \param id The ID of the resource to write data to. 604 \param data The data to be written. 605 \param offset The byte offset relative to the beginning of the resource at 606 which the data shall be written. 607 \param length The size of the data to be written. 608 609 \return A status code. 610 \retval B_OK Everything went fine. 611 \retval B_BAD_VALUE \a data was \c NULL or \a type and \a id did not 612 identify an existing resource. 613 \retval B_ERROR Error writing data. 614 \retval B_NO_MEMORY Not enough memory for this operation. 615*/ 616 617 618/*! 619 \fn status_t BResources::ReadResource(type_code type, int32 id, 620 void* data, off_t offset, size_t length) 621 \brief Reads data from an existing resource. 622 (deprecated, use LoadResource() instead) 623 624 \deprecated Use LoadResource() instead. 625 626 If more data than existing are requested, this method does not fail. It 627 will then read only the existing data. As a consequence an offset past 628 the end of the resource will not cause the method to fail, but no data 629 will be read at all. 630 631 \param type The type of the resource to be read. 632 \param id The ID of the resource to be read. 633 \param data A pointer to a buffer into which the data shall be read 634 \param offset The byte offset relative to the beginning of the resource 635 from which the data shall be read. 636 \param length The size of the data to be read. 637 638 \return A status code. 639 \retval B_OK Everything went fine. 640 \retval B_BAD_VALUE \a data was \c NULL or \a type and \a id did not 641 identify an existing resource. 642 \retval B_ERROR Error reading data. 643 \retval B_NO_MEMORY Not enough memory for this operation. 644*/ 645 646 647/*! 648 \fn void* BResources::FindResource(type_code type, int32 id, 649 size_t* lengthFound) 650 \brief Finds a resource by \a type and \a id and returns a pointer to a 651 copy of its data. (deprecated, use LoadResource() instead) 652 653 \deprecated Use LoadResource() instead. 654 655 \warning The caller is responsible for calling free() to release the 656 memory used by the returned data. 657 658 \param type The type of the resource to find. 659 \param id The ID of the resource to find. 660 \param lengthFound A pointer to a variable into which the size of the 661 resource data shall be written. 662 663 \return A pointer to the resource data if everything went fine or \c NULL 664 if an error occurred. 665*/ 666 667 668/*! 669 \fn void* BResources::FindResource(type_code type, const char* name, 670 size_t* lengthFound) 671 \brief Finds a resource by \a type and \a name and returns a pointer to a 672 copy of its data. (deprecated, use LoadResource() instead) 673 674 \deprecated Use LoadResource() instead. 675 676 \warning The caller is responsible for calling free() to release the 677 memory used by the returned data. 678 679 \param type The type of the resource to find. 680 \param name The name of the resource to find. 681 \param lengthFound A pointer to a variable into which the size of the 682 resource data shall be written. 683 684 \return A pointer to the resource data if everything went fine or \c NULL 685 if an error occurred. 686*/ 687 688 689//! @} 690