Copyright ©1995 by NeXT Computer, Inc. All Rights Reserved.
IODevice |
Inherits From: | Object | |
Declared In: | driverkit/IODevice.h |
Class Description |
IODevice is an abstract class that is the superclass of all device driver classes. Functionality provided by IODevice includes: |
Standard driver startup and connection to driver objects | ||
Standard ways of getting and setting driver parameters | ||
Getting and setting standard information such as the instance's unit number | ||
Mapping IOReturn values to strings and to UNIX error numbers | ||
Adding and removing drivers from UNIX device switch tables | ||
Getting the Driver Kit version that the IODevice was compiled under |
Getting and Setting Parameters
The IODevice methods getCharValues:forParameter:count:, getIntValues:forParameter:count:, setIntValues:forParameter:count:, and setCharValues:forParameter:count: provide a general, extensible means for user-level programs to get and set device-specific parameters for drivers that reside in the kernel. The general scheme is as follows: |
A parameter's value is either an array of ints or an array of chars. The maximum number of elements in a parameter array is IO_MAX_PARAMETER_ARRAY_LENGTH, a system constant (currently 512 though you shouldn't count on this value). | ||
Parameters are specified with human-readable strings. For example, the parameter for getting an IODevice's unit number is named "IOUnit" and defined as the constant IO_UNIT. | ||
Any subclass of IODevice can define any parameters it wishes. Any class that does so must implement the appropriate methods by which the parameters can be accessed (getIntValues:..., for example). If such a method is invoked with a parameter name that the class does not recognize, the method invocation should be passed up to super. If no classes recognize the parameter name, IODevice returns IO_R_UNSUPPORTED. | ||
By sending messages to an IODeviceMaster object, a user program can find the desired instance of a device driver and get or set device-specific parameters. |
Implementing a Subclass
Subclasses of IODevice that are indirect or direct device drivers must implement the following methods: |
+ deviceStyle + probe: initFromDeviceDescription: |
Indirect device drivers also need to implement the requiredProtocols class method.
Note: If your class's direct superclass isn't IODevice, check the documentation for the superclass--it may implement some or all of these methods for you. During initialization, indirect and direct drivers must invoke the following methods: |
registerDevice setDeviceKind: setLocation: setName: |
The registerDevice method should be invoked at the end of initialization. Generally, indirect and direct drivers also invoke setUnit:. |
Instance Variables |
None declared in this class. |
Method Types |
Creating, initializing, and freeing instances |
+ probe: init initFromDeviceDescription: free |
Registering the class | + deviceStyle |
+ registerClass: + unregisterClass: + requiredProtocols |
Registering the instance | registerDevice |
unregisterDevice |
Getting and setting standard information |
setDeviceKind: deviceKind setLocation: location setName: name setUnit: unit |
Converting an IOReturn value | + stringFromReturn: |
stringFromReturn: errnoFromReturn: |
Adding and removing the driver from UNIX device switch tables |
+ addToBdevswFromDescription:open:close:strategy: dump:psize:isTape: + addToCdevswFromDescription:open:close:read:write: ioctl:stop:reset:select:mmap:getc:putc: + blockMajor + characterMajor + removeFromBdevsw + removeFromCdevsw + setBlockMajor: + setCharacterMajor: |
Getting the Driver Kit version of the IODevice |
+ driverKitVersion + driverKitVersionForDriverNamed: |
Getting and setting parameter values |
setCharValues:forParameter:count: getCharValues:forParameter:count: setIntValues:forParameter:count: getIntValues:forParameter:count: |
Class Methods |
addToBdevswFromDescription:open:close:strategy:dump:psize:isTape: |
+ (BOOL)addToBdevswFromDescription:(id)deviceDescription |
open:(IOSwitchFunc)openFunc close:(IOSwitchFunc)closeFunc strategy:(IOSwitchFunc)strategyFunc dump:(IOSwitchFunc)dumpFunc psize:(IOSwitchFunc)psizeFunc isTape:(BOOL)isTape |
Adds the specified values to the bdevsw table. Drivers that have UNIX block entry points should use this method during initialization.
The major number to use is taken from the value of the "Block Major" key in the class's configuration table. If "Block Major" isn't specified, the first available major number is used. If the entry is successfully added, this method invokes setBlockMajor:. If the entry was successfully added, this method returns YES; otherwise, it logs an error message and returns NO. See also: + blockMajor, + addToCdevswFromDescription:open:close:read:write: |
addToCdevswFromDescription:open:close:read:write:ioctl:stop:reset:select:mmap:getc:putc: |
+ (BOOL)addToCdevswFromDescription:(id)deviceDescription |
open:(IOSwitchFunc)openFunc close:(IOSwitchFunc)closeFunc read:(IOSwitchFunc)readFunc write:(IOSwitchFunc)writeFunc ioctl:(IOSwitchFunc)ioctlFunc stop:(IOSwitchFunc)stopFunc reset:(IOSwitchFunc)resetFunc select:(IOSwitchFunc)selectFunc mmap:(IOSwitchFunc)mmapFunc getc:(IOSwitchFunc)getcFunc putc:(IOSwitchFunc)putcFunc |
Adds the specified values to the cdevsw table. Drivers that have UNIX character entry points should use this method during initialization.
The major number to use is taken from the value of the "Character Major" key in the class's configuration table. If "Character Major" isn't specified, the first available major number is used. If the entry is successfully added, this method invokes setCharacterMajor:. If the entry was successfully added, this method returns YES; otherwise, it logs an error message and returns NO. See also: + characterMajor, + addToBdevswFromDescription:open:close:strategy: |
blockMajor |
+ (int)blockMajor |
Returns the block major number associated with this driver, or 1 if this driver has no block major number. The block major number is set using setBlockMajor:, which is invoked by addToBdevswFromDescription.... |
characterMajor |
+ (int)characterMajor |
Returns the character major number associated with this driver, or 1 if this driver has no character major number. The character major number is set using setCharacterMajor:, which is invoked by addToCdevswFromDescription.... |
deviceStyle |
+ (IODeviceStyle)deviceStyle |
Implemented by subclasses to return the basic style of driver (IO_DirectDevice, IO_IndirectDevice, or IO_PseudoDevice). The meaning of direct, indirect, and pseudo device drivers is discussed in Chapters 1 and 2.
See also: + deviceStyle (IODirectDevice) |
driverKitVersion |
+ (int)driverKitVersion |
Returns the version of the currently running DriverKit objects. The Driver Kit compares this value to the value returned by driverKitVersionForDriverNamed: to determine whether the driver is compatible with the driver environment. |
driverKitVersionForDriverNamed: |
+ (int)driverKitVersionForDriverNamed:(char *)driverName |
Returns the version of the Driver Kit that the specified driver was compiled for. The Driver Kit compares this value to the value returned by driverKitVersion to determine whether the driver is compatible with the driver environment. |
probe: |
+ (BOOL)probe:(id)deviceDescription |
Does nothing and returns NO. This method is invoked by the kernel (in the context of the kernel I/O task) to conditionally instantiate an instance of an IODevice subclass.
This method should be implemented by every direct and indirect driver. It should determine whether it needs to instantiate itself, examining the hardware if appropriate. It should then allocate and initialize all the necessary instances for the specified deviceDescription. Should return YES if any IODevice objects were created; otherwise, this method should return NO. See Chapter 1 for information on when probe: is invoked. See also: initFromDeviceDescription: |
registerClass: |
+ (void)registerClass:aClass |
Adds the specified class to the kernel list of device driver classes.
See also: + unregisterClass: |
removeFromBdevsw |
+ (BOOL)removeFromBdevsw |
Removes the driver's entry from the bdevsw table. This method finds the driver's entry in the table by invoking blockMajor. If blockMajor is 1, this method does nothing and returns NO. Otherwise, this method sets the block major number to 1 (using setBlockMajor:) and returns YES. |
removeFromCdevsw |
+ (BOOL)removeFromCdevsw |
Removes the driver's entry from the cdevsw table. This method finds the driver's entry in the table by invoking characterMajor. If characterMajor is 1, this method does nothing and returns NO. Otherwise, this method sets the character major number to 1 (using setCharacterMajor:) and returns YES. |
requiredProtocols |
+ (Protocol **)requiredProtocols |
Returns NULL. Indirect device drivers should implement this method to return a NULL-terminated list of the protocols to which associated drivers must conform. Kernel-level indirect devices must implement this. |
setBlockMajor: |
+ (void)setBlockMajor:(int)bmajor |
Sets the driver's block major number. You usually don't have to invoke this, since it's invoked by addToBdevswFromDescription:.... |
setCharacterMajor: |
+ (void)setCharacterMajor:(int)cmajor |
Sets the driver's character major number. You usually don't have to invoke this, since it's invoked by addToCdevswFromDescription:.... |
stringFromReturn: |
+ (const char *)stringFromReturn:(IOReturn)returnValue |
Returns a text string that describes the specified IOReturn value.
See also: stringFromReturn: |
unregisterClass: |
+ (void)unregisterClass:classId |
Removes the specified class from the kernel list of device driver classes. This method is invoked when a class is being removed from the address space of a program such as the kernel.
See also: + registerClass: |
Instance Methods |
deviceKind |
(const char *)deviceKind |
Returns a string that identifies the object in general terms. For example, IOSCSIDisk objects return "SCSIDisk". See the description of setDeviceKind: for more information.
See also: setDeviceKind: |
errnoFromReturn: |
(int)errnoFromReturn:(IOReturn)returnValue |
Returns a UNIX error number that corresponds to the specified IOReturn value. Subclasses that add additional IOReturn values should override this method and send an errnoFromReturn: to super for IOReturn values that the subclass doesn't handle. |
free |
free |
Frees resources used by the IODevice and returns nil. |
getCharValues:forParameter:count: |
(IOReturn)getCharValues:(unsigned char *)array forParameter:(IOParameterName)parameter |
count:(unsigned int *)count |
Gets the array of character values associated with parameter. IODevice accepts the following character parameters: IO_CLASS_NAME (which returns [[self class] name]), IO_DEVICE_NAME (which returns [self name]), and IO_DEVICE_KIND (which returns [self deviceKind]).
Subclasses should override this method if they support parameters not understood by the superclass. Here's an example of overriding this method: |
- (IOReturn)getCharValues : (unsigned char *)parameterArray
forParameter : (IOParameterName)parameterName
count : (unsigned int *)count
{
const char *param;
unsigned int length;
unsigned int maxCount = *count;
if(strcmp(parameterName, my_PARAMETER_NAME) == 0){
param = _myParameter; /* _myParameter is an instance var */
length = strlen(param);
if(length >= maxCount) {
length = maxCount - 1;
}
*count = length + 1;
strncpy(parameterArray, param, length);
parameterArray[length] = '\0';
return IO_R_SUCCESS;
}
else {
/* Pass parameters we don't recognize to our superclass. */
return [super getCharValues:parameterArray
forParameter:parameterName count:count];
}
}
Returns IO_R_SUCCESS if parameter is a valid parameter with character values that can be read; otherwise, returns IO_R_UNSUPPORTED.
See also: getIntValues:forParameter:count:, setCharValues:forParameter:count: |
getIntValues:forParameter:count: |
(IOReturn)getIntValues:(unsigned int *)array forParameter:(IOParameterName)parameter |
count:(unsigned int *)count |
Returns IO_R_UNSUPPORTED. Subclasses should implement this method if necessary to return (in array) the array of integer values associated with parameter. See getCharValues:forParameter:count: for an example of implementing this kind of method. This method should return IO_R_SUCCESS if parameter is a valid parameter with integer values that can be read; otherwise, it should return IO_R_UNSUPPORTED.
See also: getCharValues:forParameter:count:, setIntValues:forParameter:count: |
init |
init |
Initializes and returns a newly allocated IODevice. Returns self if successful; otherwise, returns nil.
Note: Direct and indirect drivers should use initFromDeviceDescription: instead of this method. |
initFromDeviceDescription: |
initFromDeviceDescription:deviceDescription |
Does nothing and returns self. Subclasses that implement this method should have it initialize and return a newly allocated instance of the subclass, using the information from deviceDescription. This method should return nil on error.
See also: initFromDeviceDescription: (IODirectDevice) |
location |
(const char *)location |
Returns the device-specific location of the IODevice--for example, "0xf7f04000". See the description of setLocation: for information on how this location is used.
See also: setLocation: |
name |
(const char *)name |
Returns the device-specific name of the IODevice--for example, "sd0a". See the description of setName: for information on how the name is used.
See also: setName: |
registerDevice |
registerDevice |
Registers the IODevice in the current name space and adds a string to the system log that announces the device's registration. The IODevice must be ready to perform I/O, its name must have been set already using setName:, and its location (set with setLocation:) must be either valid or NULL.
This method also probes all indirect IODevices that require this object's protocols, giving them a chance to connect to this object. Each IODevice should invoke this method at the end of its initialization. Returns self. Note: I/O can begin before this method returns. See also: unregisterDevice |
setCharValues:forParameter:count: |
(IOReturn)setCharValues:(unsigned char *)array forParameter:(IOParameterName)parameter |
count:(unsigned int)count |
Returns IO_R_UNSUPPORTED. Subclasses should implement this method if necessary to set (from array) the array of character values associated with parameter. See getCharValues:forParameter:count: for an example of implementing this kind of method. This method should return IO_R_SUCCESS if parameter is a valid parameter with character values that can be written; otherwise, it should return IO_R_UNSUPPORTED.
See also: setIntValues:forParameter:count:, getCharValues:forParameter:count: |
setDeviceKind: |
(void)setDeviceKind:(const char *)type |
Sets a string that identifies the object in general terms. For example, IOFrameBufferDisplay objects have a device kind of "Linear Framebuffer". The string should be no longer than IO_STRING_LENGTH 1 characters. The standard parameter name IO_DEVICE_KIND refers to this string.
See also: deviceKind |
setIntValues:forParameter:count: |
(IOReturn)setIntValues:(unsigned int *)array forParameter:(IOParameterName)parameter |
count:(unsigned int)count |
Returns IO_R_UNSUPPORTED. Subclasses should implement this method if necessary to set (from array) the array of character values associated with parameter. See getCharValues:forParameter:count: for an example of implementing this kind of method. This method should return IO_R_SUCCESS if parameter is a valid parameter with integer values that can be written; otherwise, it should return IO_R_UNSUPPORTED.
See also: setCharValues:forParameter:count:, getIntValues:forParameter:count: |
setLocation: |
(void)setLocation:(const char *)location |
Sets the device-specific location of the IODevice--for example, "0xf7f04000". If the location is irrelevant, its value should be set to NULL. The location is used in the system log when this object is registered and unregistered.
See also: location |
setName: |
(void)setName:(const char *)name |
Sets the device-specific name of the IODevice--for example, "sd0a". The name should be no longer than IO_STRING_LENGTH 1 characters.
The specified name is used to identify this instance. For example, it's used in the system log when this object is registered and unregistered, and it's used by the UNIX command iostat. The name is also used by user-level programs to find this object, using the IODeviceMaster method lookUpByDeviceName:objectNumber:deviceKind:. The standard parameter name IO_DEVICE_NAME refers to this string. See also: name |
setUnit: |
(void)setUnit:(unsigned int)unit |
Sets the IODevice's unit number, a device-specific number that can be used like a UNIX minor number.
See also: unit |
stringFromReturn: |
(const char *)stringFromReturn:(IOReturn)returnValue |
Returns the text string that corresponds to the specified IOReturn value. Subclasses that add additional IOReturn values should override this method and invoke stringFromReturn: against the superclass for IOReturn values that the subclass doesn't handle.
See also: + stringFromReturn: |
unit |
(unsigned int)unit |
Returns the IODevice's unit number, a device-specific number that can be used like a UNIX minor number.
See also: setUnit: |
unregisterDevice |
(void)unregisterDevice |
Removes the IODevice from the current name space.
See also: registerDevice |