1/*
2 * Copyright (c) 1998-2014 Apple Inc. All rights reserved.
3 *
4 * @APPLE_LICENSE_HEADER_START@
5 *
6 * This file contains Original Code and/or Modifications of Original Code
7 * as defined in and that are subject to the Apple Public Source License
8 * Version 2.0 (the 'License'). You may not use this file except in
9 * compliance with the License. Please obtain a copy of the License at
10 * http://www.opensource.apple.com/apsl/ and read it before using this
11 * file.
12 *
13 * The Original Code and all software distributed under the License are
14 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
15 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
16 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR NON-INFRINGEMENT.
18 * Please see the License for the specific language governing rights and
19 * limitations under the License.
20 *
21 * @APPLE_LICENSE_HEADER_END@
22 */
23
24/*!
25 * @header IOMedia
26 * @abstract
27 * This header contains the IOMedia class definition.
28 */
29
30#ifndef _IOMEDIA_H
31#define _IOMEDIA_H
32
33#include <IOKit/IOTypes.h>
34
35/*!
36 * @defined kIOMediaClass
37 * @abstract
38 * The name of the IOMedia class.
39 */
40
41#define kIOMediaClass "IOMedia"
42
43/*!
44 * @defined kIOMediaContentKey
45 * @abstract
46 * A property of IOMedia objects.
47 * @discussion
48 * The kIOMediaContentKey property has an OSString
49 * value and contains a description of the media's
50 * contents.  The description is the same as the hint at the time of the
51 * object's creation, but it is possible that the description has been overridden
52 * by a client (which has probed the media and identified the content correctly)
53 * of the media object.  It is more accurate than the hint for this reason.  The
54 * string is formed in the likeness of Apple's "Apple_HFS" strings or in the
55 * likeness of a UUID.
56 */
57
58#define kIOMediaContentKey "Content"
59
60/*!
61 * @defined kIOMediaContentHintKey
62 * @abstract
63 * A property of IOMedia objects.
64 * @discussion
65 * The kIOMediaContentHintKey property has an OSString
66 * value and contains a hint of the media's contents.
67 * The hint is set at the time of the object's creation, should the creator have
68 * a clue as to what it may contain.  The hint string does not change for the
69 * lifetime of the object and is formed in the likeness of Apple's "Apple_HFS"
70 * strings or in the likeness of a UUID.
71 */
72
73#define kIOMediaContentHintKey "Content Hint"
74
75/*!
76 * @defined kIOMediaEjectableKey
77 * @abstract
78 * A property of IOMedia objects.
79 * @discussion
80 * The kIOMediaEjectableKey property has an OSBoolean
81 * value and describes whether the media is ejectable
82 * from the drive mechanism under software control.  Implies IOMediaRemovable
83 * is also true.
84 */
85
86#define kIOMediaEjectableKey "Ejectable"
87
88/*!
89 * @defined kIOMediaLeafKey
90 * @abstract
91 * A property of IOMedia objects.
92 * @discussion
93 * The kIOMediaLeafKey property has an OSBoolean value and describes whether the media is a leaf, that is,
94 * it is the deepest media object in this branch of the I/O Registry.
95 */
96
97#define kIOMediaLeafKey "Leaf"
98
99/*!
100 * @defined kIOMediaOpenKey
101 * @abstract
102 * A property of IOMedia objects.
103 * @discussion
104 * The kIOMediaOpenKey property has an OSBoolean value and describes whether
105 * a client presently has an open on this media.
106 */
107
108#define kIOMediaOpenKey "Open"
109
110/*!
111 * @defined kIOMediaPreferredBlockSizeKey
112 * @abstract
113 * A property of IOMedia objects.
114 * @discussion
115 * The kIOMediaPreferredBlockSizeKey property has an
116 * OSNumber value and describes the media's natural
117 * block size in bytes.  This information is useful to clients that want to
118 * optimize access to the media.
119 */
120
121#define kIOMediaPreferredBlockSizeKey "Preferred Block Size"
122
123/*!
124 * @defined kIOMediaRemovableKey
125 * @abstract
126 * A property of IOMedia objects.
127 * @discussion
128 * The kIOMediaRemovableKey property has an OSBoolean
129 * value and describes whether the media is removable
130 * from the drive mechanism.
131 */
132
133#define kIOMediaRemovableKey "Removable"
134
135/*!
136 * @defined kIOMediaSizeKey
137 * @abstract
138 * A property of IOMedia objects.
139 * @discussion
140 * The kIOMediaSizeKey property has an OSNumber value and describes the total length of the media in
141 * bytes.
142 */
143
144#define kIOMediaSizeKey "Size"
145
146/*!
147 * @defined kIOMediaUUIDKey
148 * @abstract
149 * A property of IOMedia objects.
150 * @discussion
151 * The kIOMediaUUIDKey property has an OSString value and contains a persistent
152 * Universal Unique Identifier for the media if such an identifier is available.
153 */
154
155#define kIOMediaUUIDKey "UUID"
156
157/*!
158 * @defined kIOMediaWholeKey
159 * @abstract
160 * A property of IOMedia objects.
161 * @discussion
162 * The kIOMediaWholeKey property has an OSBoolean
163 * value and describes whether the media is whole, that is,
164 * it represents the whole disk (the physical disk, or a virtual replica
165 * thereof).
166 */
167
168#define kIOMediaWholeKey "Whole"
169
170/*!
171 * @defined kIOMediaWritableKey
172 * @abstract
173 * A property of IOMedia objects.
174 * @discussion
175 * The kIOMediaWritableKey property has an OSBoolean
176 * value and describes whether the media is writable.
177 */
178
179#define kIOMediaWritableKey "Writable"
180
181/*!
182 * @defined kIOMediaContentMaskKey
183 * @abstract
184 * A property of IOMedia clients.
185 * @discussion
186 * The kIOMediaContentMaskKey property has an OSString
187 * value and must exist in all IOMedia clients that
188 * drive new content (that is, produce new media objects).  When the client
189 * matches against the provider media, the value of the client's
190 * kIOMediaContentMaskKey property is used to replace the provider's
191 * kIOMediaContentKey property.
192 */
193
194#define kIOMediaContentMaskKey "Content Mask"
195
196/*!
197 * @defined kIOMediaIconKey
198 * @abstract
199 * A property of any object in the media stack.
200 * @discussion
201 * kIOMediaIconKey is a property of any object in the media stack that wishes
202 * to override the default icon shown for the media objects in the stack.  It
203 * is usually defined in a provider object below the media object.  It has an
204 * OSDictionary value, with properties identical to the kIOIconKey definition,
205 * that is, kCFBundleIdentifierKey and kIOBundleResourceFileKey.
206 */
207
208#define kIOMediaIconKey "IOMediaIcon"
209
210/*!
211 * @enum IOMediaAttributeMask
212 * @discussion
213 * The IOMediaAttributeMask bit mask describes various attributes of
214 * the media object, such as its ejectability and its removability.
215 * @constant kIOMediaAttributeEjectableMask
216 * Indicates whether the media is ejectable from the drive mechanism
217 * under software control.  Implies kIOMediaAttributeRemovableMask.
218 * @constant kIOMediaAttributeRemovableMask
219 * Indicates whether the media is removable from the drive mechanism.
220 */
221
222enum
223{
224    kIOMediaAttributeEjectableMask = 0x00000001,
225    kIOMediaAttributeRemovableMask = 0x00000002,
226    kIOMediaAttributeReservedMask  = 0xFFFFFFFC
227};
228
229typedef UInt32 IOMediaAttributeMask;
230
231#ifdef KERNEL
232#ifdef __cplusplus
233
234/*
235 * Kernel
236 */
237
238#include <IOKit/storage/IOStorage.h>
239
240/*!
241 * @class IOMedia
242 * @abstract
243 * A random-access disk device abstraction.
244 * @discussion
245 * The IOMedia class is a random-access disk device abstraction.   It provides a
246 * consistent interface for both real and virtual disk devices, for subdivisions
247 * of disks such as partitions, for supersets of disks such as RAID volumes, and
248 * so on.   It extends the IOStorage class by implementing the appropriate open,
249 * close, read, write, and matching semantics for media objects.  The properties
250 * it has reflect the properties of real disk devices,  such as ejectability and
251 * writability.
252 *
253 * The read and write interfaces support byte-level access to the storage space,
254 * with the appropriate deblocking handled by the block storage driver, however,
255 * a typical client will want to get the natural block size in order to optimize
256 * access to the real disk device.  A read or write is accepted so long as the
257 * client's access is valid, the media is formatted and the transfer is within
258 * the bounds of the media.  An optional non-zero base (offset) is then applied
259 * before the read or write is passed to the provider object.
260 */
261
262class IOMedia : public IOStorage
263{
264    OSDeclareDefaultStructors(IOMedia)
265
266protected:
267
268    struct ExpansionData { /* */ };
269    ExpansionData * _expansionData;
270
271    UInt32          _attributes;
272
273    bool            _isWhole;
274    bool            _isWritable;
275
276    UInt64          _mediaBase;  /* (relative to the storage object below us) */
277    UInt64          _mediaSize;
278
279    IOStorageAccess _openLevel;
280    OSDictionary *  _openClients;
281
282    UInt32          _reserved0320;
283
284    UInt64          _preferredBlockSize;
285
286    /*
287     * Free all of this object's outstanding resources.
288     */
289
290    virtual void free();
291
292    /*!
293     * @function handleOpen
294     * @discussion
295     * The handleOpen method grants or denies permission to access this object
296     * to an interested client.  The argument is an IOStorageAccess value that
297     * specifies the level of access desired -- reader or reader-writer.
298     *
299     * This method can be invoked to upgrade or downgrade the access level for
300     * an existing client as well.  The previous access level will prevail for
301     * upgrades that fail, of course.   A downgrade should never fail.  If the
302     * new access level should be the same as the old for a given client, this
303     * method will do nothing and return success.  In all cases, one, singular
304     * close-per-client is expected for all opens-per-client received.
305     *
306     * This implementation replaces the IOService definition of handleOpen().
307     * @param client
308     * Client requesting the open.
309     * @param options
310     * Options for the open.  Set to zero.
311     * @param access
312     * Access level for the open.  Set to kIOStorageAccessReader or
313     * kIOStorageAccessReaderWriter.
314     * @result
315     * Returns true if the open was successful, false otherwise.
316     */
317
318    virtual bool handleOpen(IOService *  client,
319                            IOOptionBits options,
320                            void *       access);
321
322    /*!
323     * @function handleIsOpen
324     * @discussion
325     * The handleIsOpen method determines whether the specified client, or any
326     * client if none is specified, presently has an open on this object.
327     *
328     * This implementation replaces the IOService definition of handleIsOpen().
329     * @param client
330     * Client to check the open state of.  Set to zero to check the open state
331     * of all clients.
332     * @result
333     * Returns true if the client was (or clients were) open, false otherwise.
334     */
335
336    virtual bool handleIsOpen(const IOService * client) const;
337
338    /*!
339     * @function handleClose
340     * @discussion
341     * The handleClose method closes the client's access to this object.
342     *
343     * This implementation replaces the IOService definition of handleClose().
344     * @param client
345     * Client requesting the close.
346     * @param options
347     * Options for the close.  Set to zero.
348     */
349
350    virtual void handleClose(IOService * client, IOOptionBits options);
351
352public:
353
354    using IOStorage::read;
355    using IOStorage::write;
356
357#ifndef __LP64__
358    virtual bool init(UInt64         base,
359                      UInt64         size,
360                      UInt64         preferredBlockSize,
361                      bool           isEjectable,
362                      bool           isWhole,
363                      bool           isWritable,
364                      const char *   contentHint = 0,
365                      OSDictionary * properties  = 0) __attribute__ ((deprecated));
366#endif /* !__LP64__ */
367
368    /*
369     * This method is called for each client interested in the services we
370     * provide.  The superclass links us as a parent to this client in the
371     * I/O Kit registry on success.
372     */
373
374    virtual bool attachToChild(IORegistryEntry *       client,
375                               const IORegistryPlane * plane);
376
377    /*
378     * This method is called for each client that loses interest in the
379     * services we provide.  The superclass unlinks us from this client
380     * in the I/O Kit registry on success.
381     */
382
383    virtual void detachFromChild(IORegistryEntry *       client,
384                                 const IORegistryPlane * plane);
385
386    /*
387     * Obtain this object's provider.  We override the superclass's method to
388     * return a more specific subclass of OSObject -- IOStorage.  This method
389     * serves simply as a convenience to subclass developers.
390     */
391
392    virtual IOStorage * getProvider() const;
393
394    /*
395     * Compare the properties in the supplied table to this object's properties.
396     */
397
398    virtual bool matchPropertyTable(OSDictionary * table, SInt32 * score);
399
400    /*!
401     * @function read
402     * @discussion
403     * Read data from the storage object at the specified byte offset into the
404     * specified buffer, asynchronously.   When the read completes, the caller
405     * will be notified via the specified completion action.
406     *
407     * The buffer will be retained for the duration of the read.
408     * @param client
409     * Client requesting the read.
410     * @param byteStart
411     * Starting byte offset for the data transfer.
412     * @param buffer
413     * Buffer for the data transfer.  The size of the buffer implies the size of
414     * the data transfer.
415     * @param attributes
416     * Attributes of the data transfer.  See IOStorageAttributes.  It is the
417     * responsibility of the callee to maintain the information for the duration
418     * of the data transfer, as necessary.
419     * @param completion
420     * Completion routine to call once the data transfer is complete.  It is the
421     * responsibility of the callee to maintain the information for the duration
422     * of the data transfer, as necessary.
423     */
424
425    virtual void read(IOService *           client,
426                      UInt64                byteStart,
427                      IOMemoryDescriptor *  buffer,
428                      IOStorageAttributes * attributes,
429                      IOStorageCompletion * completion);
430
431    /*!
432     * @function write
433     * @discussion
434     * Write data into the storage object at the specified byte offset from the
435     * specified buffer, asynchronously.   When the write completes, the caller
436     * will be notified via the specified completion action.
437     *
438     * The buffer will be retained for the duration of the write.
439     * @param client
440     * Client requesting the write.
441     * @param byteStart
442     * Starting byte offset for the data transfer.
443     * @param buffer
444     * Buffer for the data transfer.  The size of the buffer implies the size of
445     * the data transfer.
446     * @param attributes
447     * Attributes of the data transfer.  See IOStorageAttributes.  It is the
448     * responsibility of the callee to maintain the information for the duration
449     * of the data transfer, as necessary.
450     * @param completion
451     * Completion routine to call once the data transfer is complete.  It is the
452     * responsibility of the callee to maintain the information for the duration
453     * of the data transfer, as necessary.
454     */
455
456    virtual void write(IOService *           client,
457                       UInt64                byteStart,
458                       IOMemoryDescriptor *  buffer,
459                       IOStorageAttributes * attributes,
460                       IOStorageCompletion * completion);
461
462    /*!
463     * @function synchronizeCache
464     * @discussion
465     * Flush the cached data in the storage object, if any, synchronously.
466     * @param client
467     * Client requesting the cache synchronization.
468     * @result
469     * Returns the status of the cache synchronization.
470     */
471
472    virtual IOReturn synchronizeCache(IOService * client);
473
474    /*!
475     * @function unmap
476     * @discussion
477     * Delete unused data from the storage object at the specified byte offsets,
478     * synchronously.
479     * @param client
480     * Client requesting the operation.
481     * @param extents
482     * List of extents.  See IOStorageExtent.  It is legal for the callee to
483     * overwrite the contents of this buffer in order to satisfy the request.
484     * @param extentsCount
485     * Number of extents.
486     * @result
487     * Returns the status of the operation.
488     */
489
490    virtual IOReturn unmap(IOService *       client,
491                           IOStorageExtent * extents,
492                           UInt32            extentsCount,
493                           UInt32            options = 0);
494
495    /*!
496     * @function lockPhysicalExtents
497     * @discussion
498     * Lock the contents of the storage object against relocation temporarily,
499     * for the purpose of getting physical extents.
500     * @param client
501     * Client requesting the operation.
502     * @result
503     * Returns true if the lock was successful, false otherwise.
504     */
505
506    virtual bool lockPhysicalExtents(IOService * client);
507
508    /*!
509     * @function copyPhysicalExtent
510     * @discussion
511     * Convert the specified byte offset into a physical byte offset, relative
512     * to a physical storage object.  This call should only be made within the
513     * context of lockPhysicalExtents().
514     * @param client
515     * Client requesting the operation.
516     * @param byteStart
517     * Starting byte offset for the operation.  Returns a physical byte offset,
518     * relative to the physical storage object, on success.
519     * @param byteCount
520     * Size of the operation.  Returns the actual number of bytes which can be
521     * transferred, relative to the physical storage object, on success.
522     * @result
523     * A reference to the physical storage object, which should be released by
524     * the caller, or a null on error.
525     */
526
527    virtual IOStorage * copyPhysicalExtent(IOService * client,
528                                           UInt64 *    byteStart,
529                                           UInt64 *    byteCount);
530
531    /*!
532     * @function unlockPhysicalExtents
533     * @discussion
534     * Unlock the contents of the storage object for relocation again.  This
535     * call must balance a successful call to lockPhysicalExtents().
536     * @param client
537     * Client requesting the operation.
538     */
539
540    virtual void unlockPhysicalExtents(IOService * client);
541
542    /*!
543     * @function setPriority
544     * @discussion
545     * Reprioritize read or write requests at the specified byte offsets.
546     * @param client
547     * Client requesting the operation.
548     * @param extents
549     * List of extents.  See IOStorageExtent.  It is legal for the callee to
550     * overwrite the contents of this buffer in order to satisfy the request.
551     * @param extentsCount
552     * Number of extents.
553     * @param priority
554     * New priority.  See IOStoragePriority.
555     * @result
556     * Returns the status of the operation.
557     */
558
559    virtual IOReturn setPriority(IOService *       client,
560                                 IOStorageExtent * extents,
561                                 UInt32            extentsCount,
562                                 IOStoragePriority priority);
563
564    /*!
565     * @function getPreferredBlockSize
566     * @discussion
567     * Ask the media object for its natural block size.  This information
568     * is useful to clients that want to optimize access to the media.
569     * @result
570     * Natural block size, in bytes.
571     */
572
573    virtual UInt64 getPreferredBlockSize() const;
574
575    /*!
576     * @function getSize
577     * @discussion
578     * Ask the media object for its total length in bytes.
579     * @result
580     * Media size, in bytes.
581     */
582
583    virtual UInt64 getSize() const;
584
585    /*!
586     * @function getBase
587     * @discussion
588     * Ask the media object for its byte offset relative to the provider media.
589     * @result
590     * Media offset, in bytes.
591     */
592
593    virtual UInt64 getBase() const;
594
595    /*!
596     * @function isEjectable
597     * @discussion
598     * Ask the media object whether it is ejectable.
599     * @result
600     * Returns true if the media is ejectable, false otherwise.
601     */
602
603    virtual bool isEjectable() const;
604
605    /*!
606     * @function isFormatted
607     * @discussion
608     * Ask the media object whether it is formatted.
609     * @result
610     * Returns true if the media is formatted, false otherwise.
611     */
612
613    virtual bool isFormatted() const;
614
615    /*!
616     * @function isWhole
617     * @discussion
618     * Ask the media object whether it represents the whole disk.
619     * @result
620     * Returns true if the media represents the whole disk, false otherwise.
621     */
622
623    virtual bool isWhole() const;
624
625    /*!
626     * @function isWritable
627     * @discussion
628     * Ask the media object whether it is writable.
629     * @result
630     * Returns true if the media is writable, false otherwise.
631     */
632
633    virtual bool isWritable() const;
634
635    /*!
636     * @function getContent
637     * @discussion
638     * Ask the media object for a description of its contents.  The description
639     * is the same as the hint at the time of the object's creation,  but it is
640     * possible that the description has been overridden by a client (which has probed
641     * the media and identified the content correctly) of the media object.  It
642     * is more accurate than the hint for this reason.  The string is formed in
643     * the likeness of Apple's "Apple_HFS" strings or in the likeness of a UUID.
644     *
645     * The content description can be overridden by any client that matches onto
646     * this media object with a match category of kIOStorageCategory.  The media
647     * object checks for a kIOMediaContentMaskKey property in the client, and if
648     * it finds one, it copies it into kIOMediaContentKey property.
649     * @result
650     * Description of media's contents.
651     */
652
653    virtual const char * getContent() const;
654
655    /*!
656     * @function getContentHint
657     * @discussion
658     * Ask the media object for a hint of its contents.  The hint is set at the
659     * time of the object's creation, should the creator have a clue as to what
660     * it may contain.  The hint string does not change for the lifetime of the
661     * object and is also formed in the likeness of Apple's "Apple_HFS" strings
662     * or in the likeness of a UUID.
663     * @result
664     * Hint of media's contents.
665     */
666
667    virtual const char * getContentHint() const;
668
669    /*!
670     * @function init
671     * @discussion
672     * Initialize this object's minimal state.
673     * @param base
674     * Media offset, in bytes.
675     * @param size
676     * Media size, in bytes.
677     * @param preferredBlockSize
678     * Natural block size, in bytes.
679     * @param attributes
680     * Media attributes, such as ejectability and removability.  See
681     * IOMediaAttributeMask.
682     * @param isWhole
683     * Indicates whether the media represents the whole disk.
684     * @param isWritable
685     * Indicates whether the media is writable.
686     * @param contentHint
687     * Hint of media's contents (optional).  See getContentHint().
688     * @param properties
689     * Substitute property table for this object (optional).
690     * @result
691     * Returns true on success, false otherwise.
692     */
693
694    virtual bool init(UInt64               base,
695                      UInt64               size,
696                      UInt64               preferredBlockSize,
697                      IOMediaAttributeMask attributes,
698                      bool                 isWhole,
699                      bool                 isWritable,
700                      const char *         contentHint = 0,
701                      OSDictionary *       properties  = 0); /* 10.2.0 */
702
703    /*!
704     * @function getAttributes
705     * @discussion
706     * Ask the media object for its attributes.
707     * @result
708     * Media attributes, such as ejectability and removability.  See
709     * IOMediaAttributeMask.
710     */
711
712    virtual IOMediaAttributeMask getAttributes() const; /* 10.2.0 */
713
714#ifdef __LP64__
715    OSMetaClassDeclareReservedUnused(IOMedia,  0);
716    OSMetaClassDeclareReservedUnused(IOMedia,  1);
717#else /* !__LP64__ */
718    OSMetaClassDeclareReservedUsed(IOMedia,  0);
719    OSMetaClassDeclareReservedUsed(IOMedia,  1);
720#endif /* !__LP64__ */
721    OSMetaClassDeclareReservedUnused(IOMedia,  2);
722    OSMetaClassDeclareReservedUnused(IOMedia,  3);
723    OSMetaClassDeclareReservedUnused(IOMedia,  4);
724    OSMetaClassDeclareReservedUnused(IOMedia,  5);
725    OSMetaClassDeclareReservedUnused(IOMedia,  6);
726    OSMetaClassDeclareReservedUnused(IOMedia,  7);
727    OSMetaClassDeclareReservedUnused(IOMedia,  8);
728    OSMetaClassDeclareReservedUnused(IOMedia,  9);
729    OSMetaClassDeclareReservedUnused(IOMedia, 10);
730    OSMetaClassDeclareReservedUnused(IOMedia, 11);
731    OSMetaClassDeclareReservedUnused(IOMedia, 12);
732    OSMetaClassDeclareReservedUnused(IOMedia, 13);
733    OSMetaClassDeclareReservedUnused(IOMedia, 14);
734    OSMetaClassDeclareReservedUnused(IOMedia, 15);
735};
736
737#endif /* __cplusplus */
738#endif /* KERNEL */
739#endif /* !_IOMEDIA_H */
740