1 // ---------------------------------------------------------------------- 2 // This software is part of the OpenBeOS distribution and is covered 3 // by the OpenBeOS license. 4 // 5 // File Name: Volume.cpp 6 // 7 // Description: BVolume class 8 // ---------------------------------------------------------------------- 9 /*! 10 \file Volume.h 11 BVolume implementation. 12 */ 13 14 #include <errno.h> 15 16 #include <Bitmap.h> 17 #include <Directory.h> 18 #include <fs_info.h> 19 #include <kernel_interface.h> 20 #include <Node.h> 21 #include <Volume.h> 22 23 24 #ifdef USE_OPENBEOS_NAMESPACE 25 namespace OpenBeOS { 26 #endif 27 28 /*! 29 \class BVolume 30 \brief Represents a disk volume 31 32 Provides an interface for querying information about a volume. 33 34 The class is a simple wrapper for a \c dev_t and the function 35 fs_stat_dev. The only exception is the method is SetName(), which 36 sets the name of the volume. 37 38 \author Vincent Dominguez 39 \author <a href='mailto:bonefish@users.sf.net'>Ingo Weinhold</a> 40 41 \version 0.0.0 42 */ 43 44 /*! \var dev_t BVolume::fDevice 45 \brief The volume's device ID. 46 */ 47 48 /*! \var dev_t BVolume::fCStatus 49 \brief The object's initialization status. 50 */ 51 52 // constructor 53 /*! \brief Creates an uninitialized BVolume. 54 55 InitCheck() will return \c B_NO_INIT. 56 */ 57 BVolume::BVolume() 58 : fDevice(-1), 59 fCStatus(B_NO_INIT) 60 { 61 } 62 63 // constructor 64 /*! \brief Creates a BVolume and initializes it to the volume specified 65 by the supplied device ID. 66 67 InitCheck() should be called to check whether the initialization was 68 successful. 69 70 \param device The device ID of the volume. 71 */ 72 BVolume::BVolume(dev_t device) 73 : fDevice(-1), 74 fCStatus(B_NO_INIT) 75 { 76 SetTo(device); 77 } 78 79 // copy constructor 80 /*! \brief Creates a BVolume and makes it a clone of the supplied one. 81 82 Afterwards the object refers to the same device the supplied object 83 does. If the latter is not properly initialized, this object isn't 84 either. 85 86 \param volume The volume object to be cloned. 87 */ 88 BVolume::BVolume(const BVolume &volume) 89 : fDevice(volume.fDevice), 90 fCStatus(volume.fCStatus) 91 { 92 } 93 94 // destructor 95 /*! \brief Frees all resources associated with the object. 96 97 Does nothing. 98 */ 99 BVolume::~BVolume() 100 { 101 } 102 103 // InitCheck 104 /*! \brief Returns the result of the last initialization. 105 \return 106 - \c B_OK: The object is properly initialized. 107 - an error code otherwise 108 */ 109 status_t 110 BVolume::InitCheck(void) const 111 { 112 return fCStatus; 113 } 114 115 // SetTo 116 /*! \brief Re-initializes the object to refer to the volume specified by 117 the supplied device ID. 118 \param device The device ID of the volume. 119 \param 120 - \c B_OK: Everything went fine. 121 - an error code otherwise 122 */ 123 status_t 124 BVolume::SetTo(dev_t device) 125 { 126 // uninitialize 127 Unset(); 128 // check the parameter 129 status_t error = (device >= 0 ? B_OK : B_BAD_VALUE); 130 if (error == B_OK) { 131 fs_info info; 132 if (fs_stat_dev(device, &info) != 0) 133 error = errno; 134 } 135 // set the new value 136 if (error == B_OK) 137 fDevice = device; 138 // set the init status variable 139 fCStatus = error; 140 return fCStatus; 141 } 142 143 // Unset 144 /*! \brief Uninitialized the BVolume. 145 */ 146 void 147 BVolume::Unset() 148 { 149 fDevice = -1; 150 fCStatus = B_NO_INIT; 151 } 152 153 // Device 154 /*! \brief Returns the device ID of the volume the object refers to. 155 \return Returns the device ID of the volume the object refers to 156 or -1, if the object is not properly initialized. 157 */ 158 dev_t 159 BVolume::Device() const 160 { 161 return fDevice; 162 } 163 164 // GetRootDirectory 165 /*! \brief Returns the root directory of the volume referred to by the object. 166 \param directory A pointer to a pre-allocated BDirectory to be initialized 167 to the volume's root directory. 168 \return 169 - \c B_OK: Everything went fine. 170 - \c B_BAD_VALUE: \c NULL \a directory or the object is not properly 171 initialized. 172 - another error code 173 */ 174 status_t 175 BVolume::GetRootDirectory(BDirectory *directory) const 176 { 177 // check parameter and initialization 178 status_t error = (directory && InitCheck() == B_OK ? B_OK : B_BAD_VALUE); 179 // get FS stat 180 fs_info info; 181 if (error == B_OK && fs_stat_dev(fDevice, &info) != 0) 182 error = errno; 183 // init the directory 184 if (error == B_OK) { 185 node_ref ref; 186 ref.device = info.dev; 187 ref.node = info.root; 188 error = directory->SetTo(&ref); 189 } 190 return error; 191 } 192 193 // Capacity 194 /*! \brief Returns the volume's total storage capacity. 195 \return 196 - The volume's total storage capacity (in bytes), when the object is 197 properly initialized. 198 - \c B_BAD_VALUE otherwise. 199 */ 200 off_t 201 BVolume::Capacity() const 202 { 203 // check initialization 204 status_t error = (InitCheck() == B_OK ? B_OK : B_BAD_VALUE); 205 // get FS stat 206 fs_info info; 207 if (error == B_OK && fs_stat_dev(fDevice, &info) != 0) 208 error = errno; 209 return (error == B_OK ? info.total_blocks * info.block_size : error); 210 } 211 212 // FreeBytes 213 /*! \brief Returns the amount of storage that's currently unused on the 214 volume (in bytes). 215 \return 216 - The amount of storage that's currently unused on the volume (in bytes), 217 when the object is properly initialized. 218 - \c B_BAD_VALUE otherwise. 219 */ 220 off_t 221 BVolume::FreeBytes() const 222 { 223 // check initialization 224 status_t error = (InitCheck() == B_OK ? B_OK : B_BAD_VALUE); 225 // get FS stat 226 fs_info info; 227 if (error == B_OK && fs_stat_dev(fDevice, &info) != 0) 228 error = errno; 229 return (error == B_OK ? info.free_blocks * info.block_size : error); 230 } 231 232 // GetName 233 /*! \brief Returns the name of the volume. 234 235 The name of the volume is copied into the provided buffer. 236 237 \param name A pointer to a pre-allocated character buffer of size 238 \c B_FILE_NAME_LENGTH or larger into which the name of the 239 volume shall be written. 240 \return 241 - \c B_OK: Everything went fine. 242 - \c B_BAD_VALUE: \c NULL \a name or the object is not properly 243 initialized. 244 - another error code 245 */ 246 status_t 247 BVolume::GetName(char *name) const 248 { 249 // check parameter and initialization 250 status_t error = (name && InitCheck() == B_OK ? B_OK : B_BAD_VALUE); 251 // get FS stat 252 fs_info info; 253 if (error == B_OK && fs_stat_dev(fDevice, &info) != 0) 254 error = errno; 255 // copy the name 256 if (error == B_OK) 257 strncpy(name, info.volume_name, B_FILE_NAME_LENGTH); 258 return error; 259 } 260 261 // SetName 262 /*! \brief Sets the name of the volume referred to by this object. 263 \param name The volume's new name. Must not be longer than 264 \c B_FILE_NAME_LENGTH (including the terminating null). 265 \return 266 - \c B_OK: Everything went fine. 267 - \c B_BAD_VALUE: \c NULL \a name or the object is not properly 268 initialized. 269 - another error code 270 */ 271 status_t 272 BVolume::SetName(const char *name) 273 { 274 // check initialization 275 status_t error = (InitCheck() == B_OK ? B_OK : B_BAD_VALUE); 276 if (error == B_OK) 277 error = BPrivate::Storage::set_volume_name(fDevice, name); 278 return error; 279 } 280 281 // GetIcon 282 /*! \brief Returns the icon of the volume. 283 \param icon A pointer to a pre-allocated BBitmap of the correct dimension 284 to store the requested icon (16x16 for the mini and 32x32 for the 285 large icon). 286 \param which Specifies the size of the icon to be retrieved: 287 \c B_MINI_ICON for the mini and \c B_LARGE_ICON for the large icon. 288 */ 289 status_t 290 BVolume::GetIcon(BBitmap *icon, icon_size which) const 291 { 292 // check initialization 293 status_t error = (InitCheck() == B_OK ? B_OK : B_BAD_VALUE); 294 // get FS stat 295 fs_info info; 296 if (error == B_OK && fs_stat_dev(fDevice, &info) != 0) 297 error = errno; 298 // get the icon 299 if (error == B_OK) 300 error = get_device_icon(info.device_name, icon, which); 301 return error; 302 } 303 304 // IsRemovable 305 /*! \brief Returns whether the volume is removable. 306 \return \c true, when the object is properly initialized and the 307 referred to volume is removable, \c false otherwise. 308 */ 309 bool 310 BVolume::IsRemovable() const 311 { 312 // check initialization 313 status_t error = (InitCheck() == B_OK ? B_OK : B_BAD_VALUE); 314 // get FS stat 315 fs_info info; 316 if (error == B_OK && fs_stat_dev(fDevice, &info) != 0) 317 error = errno; 318 return (error == B_OK && (info.flags & B_FS_IS_REMOVABLE)); 319 } 320 321 // IsReadOnly 322 /*! \brief Returns whether the volume is read only. 323 \return \c true, when the object is properly initialized and the 324 referred to volume is read only, \c false otherwise. 325 */ 326 bool 327 BVolume::IsReadOnly(void) const 328 { 329 // check initialization 330 status_t error = (InitCheck() == B_OK ? B_OK : B_BAD_VALUE); 331 // get FS stat 332 fs_info info; 333 if (error == B_OK && fs_stat_dev(fDevice, &info) != 0) 334 error = errno; 335 return (error == B_OK && (info.flags & B_FS_IS_READONLY)); 336 } 337 338 // IsPersistent 339 /*! \brief Returns whether the volume is persistent. 340 \return \c true, when the object is properly initialized and the 341 referred to volume is persistent, \c false otherwise. 342 */ 343 bool 344 BVolume::IsPersistent(void) const 345 { 346 // check initialization 347 status_t error = (InitCheck() == B_OK ? B_OK : B_BAD_VALUE); 348 // get FS stat 349 fs_info info; 350 if (error == B_OK && fs_stat_dev(fDevice, &info) != 0) 351 error = errno; 352 return (error == B_OK && (info.flags & B_FS_IS_PERSISTENT)); 353 } 354 355 // IsShared 356 /*! \brief Returns whether the volume is shared. 357 \return \c true, when the object is properly initialized and the 358 referred to volume is shared, \c false otherwise. 359 */ 360 bool 361 BVolume::IsShared(void) const 362 { 363 // check initialization 364 status_t error = (InitCheck() == B_OK ? B_OK : B_BAD_VALUE); 365 // get FS stat 366 fs_info info; 367 if (error == B_OK && fs_stat_dev(fDevice, &info) != 0) 368 error = errno; 369 return (error == B_OK && (info.flags & B_FS_IS_SHARED)); 370 } 371 372 // KnowsMime 373 /*! \brief Returns whether the volume supports MIME types. 374 \return \c true, when the object is properly initialized and the 375 referred to volume supports MIME types, \c false otherwise. 376 */ 377 bool 378 BVolume::KnowsMime(void) const 379 { 380 // check initialization 381 status_t error = (InitCheck() == B_OK ? B_OK : B_BAD_VALUE); 382 // get FS stat 383 fs_info info; 384 if (error == B_OK && fs_stat_dev(fDevice, &info) != 0) 385 error = errno; 386 return (error == B_OK && (info.flags & B_FS_HAS_MIME)); 387 } 388 389 // KnowsAttr 390 /*! \brief Returns whether the volume supports attributes. 391 \return \c true, when the object is properly initialized and the 392 referred to volume supports attributes, \c false otherwise. 393 */ 394 bool 395 BVolume::KnowsAttr(void) const 396 { 397 // check initialization 398 status_t error = (InitCheck() == B_OK ? B_OK : B_BAD_VALUE); 399 // get FS stat 400 fs_info info; 401 if (error == B_OK && fs_stat_dev(fDevice, &info) != 0) 402 error = errno; 403 return (error == B_OK && (info.flags & B_FS_HAS_ATTR)); 404 } 405 406 // KnowsQuery 407 /*! \brief Returns whether the volume supports queries. 408 \return \c true, when the object is properly initialized and the 409 referred to volume supports queries, \c false otherwise. 410 */ 411 bool 412 BVolume::KnowsQuery(void) const 413 { 414 // check initialization 415 status_t error = (InitCheck() == B_OK ? B_OK : B_BAD_VALUE); 416 // get FS stat 417 fs_info info; 418 if (error == B_OK && fs_stat_dev(fDevice, &info) != 0) 419 error = errno; 420 return (error == B_OK && (info.flags & B_FS_HAS_QUERY)); 421 } 422 423 // == 424 /*! \brief Returns whether two BVolume objects are equal. 425 426 Two volume objects are said to be equal, if they either are both 427 uninitialized, or both are initialized and refer to the same volume. 428 429 \param volume The object to be compared with. 430 \result \c true, if this object and the supplied one are equal, \c false 431 otherwise. 432 */ 433 bool 434 BVolume::operator==(const BVolume &volume) const 435 { 436 return (InitCheck() != B_OK && volume.InitCheck() != B_OK 437 || fDevice == volume.fDevice); 438 } 439 440 // != 441 /*! \brief Returns whether two BVolume objects are unequal. 442 443 Two volume objects are said to be equal, if they either are both 444 uninitialized, or both are initialized and refer to the same volume. 445 446 \param volume The object to be compared with. 447 \result \c true, if this object and the supplied one are unequal, \c false 448 otherwise. 449 */ 450 bool 451 BVolume::operator!=(const BVolume &volume) const 452 { 453 return !(*this == volume); 454 } 455 456 // = 457 /*! \brief Assigns another BVolume object to this one. 458 459 This object is made an exact clone of the supplied one. 460 461 \param volume The volume from which shall be assigned. 462 \return A reference to this object. 463 */ 464 BVolume& 465 BVolume::operator=(const BVolume &volume) 466 { 467 if (&volume != this) { 468 this->fDevice = volume.fDevice; 469 this->fCStatus = volume.fCStatus; 470 } 471 return *this; 472 } 473 474 475 // FBC 476 void BVolume::_TurnUpTheVolume1() {} 477 void BVolume::_TurnUpTheVolume2() {} 478 void BVolume::_TurnUpTheVolume3() {} 479 void BVolume::_TurnUpTheVolume4() {} 480 void BVolume::_TurnUpTheVolume5() {} 481 void BVolume::_TurnUpTheVolume6() {} 482 void BVolume::_TurnUpTheVolume7() {} 483 void BVolume::_TurnUpTheVolume8() {} 484 485 #ifdef USE_OPENBEOS_NAMESPACE 486 } 487 #endif 488