aboutsummaryrefslogtreecommitdiff
path: root/Documentation/driver-model
diff options
context:
space:
mode:
Diffstat (limited to 'Documentation/driver-model')
-rw-r--r--Documentation/driver-model/binding.txt4
-rw-r--r--Documentation/driver-model/bus.txt19
-rw-r--r--Documentation/driver-model/class.txt19
-rw-r--r--Documentation/driver-model/design-patterns.txt116
-rw-r--r--Documentation/driver-model/device.txt154
-rw-r--r--Documentation/driver-model/devres.txt325
-rw-r--r--Documentation/driver-model/driver.txt92
-rw-r--r--Documentation/driver-model/interface.txt129
-rw-r--r--Documentation/driver-model/overview.txt103
-rw-r--r--Documentation/driver-model/platform.txt301
-rw-r--r--Documentation/driver-model/porting.txt4
11 files changed, 777 insertions, 489 deletions
diff --git a/Documentation/driver-model/binding.txt b/Documentation/driver-model/binding.txt
index f7ec9d625bf..abfc8e290d5 100644
--- a/Documentation/driver-model/binding.txt
+++ b/Documentation/driver-model/binding.txt
@@ -48,10 +48,6 @@ devclass_add_device is called to enumerate the device within the class
and actually register it with the class, which happens with the
class's register_dev callback.
-NOTE: The device class structures and core routines to manipulate them
-are not in the mainline kernel, so the discussion is still a bit
-speculative.
-
Driver
~~~~~~
diff --git a/Documentation/driver-model/bus.txt b/Documentation/driver-model/bus.txt
index 5001b751162..6754b2df8aa 100644
--- a/Documentation/driver-model/bus.txt
+++ b/Documentation/driver-model/bus.txt
@@ -3,24 +3,7 @@ Bus Types
Definition
~~~~~~~~~~
-
-struct bus_type {
- char * name;
-
- struct subsystem subsys;
- struct kset drivers;
- struct kset devices;
-
- struct bus_attribute * bus_attrs;
- struct device_attribute * dev_attrs;
- struct driver_attribute * drv_attrs;
-
- int (*match)(struct device * dev, struct device_driver * drv);
- int (*hotplug) (struct device *dev, char **envp,
- int num_envp, char *buffer, int buffer_size);
- int (*suspend)(struct device * dev, pm_message_t state);
- int (*resume)(struct device * dev);
-};
+See the kerneldoc for the struct bus_type.
int bus_register(struct bus_type * bus);
diff --git a/Documentation/driver-model/class.txt b/Documentation/driver-model/class.txt
index 2d1d893a5e5..1fefc480a80 100644
--- a/Documentation/driver-model/class.txt
+++ b/Documentation/driver-model/class.txt
@@ -12,7 +12,7 @@ device. The following device classes have been identified:
Each device class defines a set of semantics and a programming interface
that devices of that class adhere to. Device drivers are the
-implemention of that programming interface for a particular device on
+implementation of that programming interface for a particular device on
a particular bus.
Device classes are agnostic with respect to what bus a device resides
@@ -27,22 +27,7 @@ The device class structure looks like:
typedef int (*devclass_add)(struct device *);
typedef void (*devclass_remove)(struct device *);
-struct device_class {
- char * name;
- rwlock_t lock;
- u32 devnum;
- struct list_head node;
-
- struct list_head drivers;
- struct list_head intf_list;
-
- struct driver_dir_entry dir;
- struct driver_dir_entry device_dir;
- struct driver_dir_entry driver_dir;
-
- devclass_add add_device;
- devclass_remove remove_device;
-};
+See the kerneldoc for the struct class.
A typical device class definition would look like:
diff --git a/Documentation/driver-model/design-patterns.txt b/Documentation/driver-model/design-patterns.txt
new file mode 100644
index 00000000000..ba7b2df6490
--- /dev/null
+++ b/Documentation/driver-model/design-patterns.txt
@@ -0,0 +1,116 @@
+
+Device Driver Design Patterns
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+
+This document describes a few common design patterns found in device drivers.
+It is likely that subsystem maintainers will ask driver developers to
+conform to these design patterns.
+
+1. State Container
+2. container_of()
+
+
+1. State Container
+~~~~~~~~~~~~~~~~~~
+
+While the kernel contains a few device drivers that assume that they will
+only be probed() once on a certain system (singletons), it is custom to assume
+that the device the driver binds to will appear in several instances. This
+means that the probe() function and all callbacks need to be reentrant.
+
+The most common way to achieve this is to use the state container design
+pattern. It usually has this form:
+
+struct foo {
+ spinlock_t lock; /* Example member */
+ (...)
+};
+
+static int foo_probe(...)
+{
+ struct foo *foo;
+
+ foo = devm_kzalloc(dev, sizeof(*foo), GFP_KERNEL);
+ if (!foo)
+ return -ENOMEM;
+ spin_lock_init(&foo->lock);
+ (...)
+}
+
+This will create an instance of struct foo in memory every time probe() is
+called. This is our state container for this instance of the device driver.
+Of course it is then necessary to always pass this instance of the
+state around to all functions that need access to the state and its members.
+
+For example, if the driver is registering an interrupt handler, you would
+pass around a pointer to struct foo like this:
+
+static irqreturn_t foo_handler(int irq, void *arg)
+{
+ struct foo *foo = arg;
+ (...)
+}
+
+static int foo_probe(...)
+{
+ struct foo *foo;
+
+ (...)
+ ret = request_irq(irq, foo_handler, 0, "foo", foo);
+}
+
+This way you always get a pointer back to the correct instance of foo in
+your interrupt handler.
+
+
+2. container_of()
+~~~~~~~~~~~~~~~~~
+
+Continuing on the above example we add an offloaded work:
+
+struct foo {
+ spinlock_t lock;
+ struct workqueue_struct *wq;
+ struct work_struct offload;
+ (...)
+};
+
+static void foo_work(struct work_struct *work)
+{
+ struct foo *foo = container_of(work, struct foo, offload);
+
+ (...)
+}
+
+static irqreturn_t foo_handler(int irq, void *arg)
+{
+ struct foo *foo = arg;
+
+ queue_work(foo->wq, &foo->offload);
+ (...)
+}
+
+static int foo_probe(...)
+{
+ struct foo *foo;
+
+ foo->wq = create_singlethread_workqueue("foo-wq");
+ INIT_WORK(&foo->offload, foo_work);
+ (...)
+}
+
+The design pattern is the same for an hrtimer or something similar that will
+return a single argument which is a pointer to a struct member in the
+callback.
+
+container_of() is a macro defined in <linux/kernel.h>
+
+What container_of() does is to obtain a pointer to the containing struct from
+a pointer to a member by a simple subtraction using the offsetof() macro from
+standard C, which allows something similar to object oriented behaviours.
+Notice that the contained member must not be a pointer, but an actual member
+for this to work.
+
+We can see here that we avoid having global pointers to our struct foo *
+instance this way, while still keeping the number of parameters passed to the
+work function to a single pointer.
diff --git a/Documentation/driver-model/device.txt b/Documentation/driver-model/device.txt
index a05ec50f800..1e70220d20f 100644
--- a/Documentation/driver-model/device.txt
+++ b/Documentation/driver-model/device.txt
@@ -2,96 +2,7 @@
The Basic Device Structure
~~~~~~~~~~~~~~~~~~~~~~~~~~
-struct device {
- struct list_head g_list;
- struct list_head node;
- struct list_head bus_list;
- struct list_head driver_list;
- struct list_head intf_list;
- struct list_head children;
- struct device * parent;
-
- char name[DEVICE_NAME_SIZE];
- char bus_id[BUS_ID_SIZE];
-
- spinlock_t lock;
- atomic_t refcount;
-
- struct bus_type * bus;
- struct driver_dir_entry dir;
-
- u32 class_num;
-
- struct device_driver *driver;
- void *driver_data;
- void *platform_data;
-
- u32 current_state;
- unsigned char *saved_state;
-
- void (*release)(struct device * dev);
-};
-
-Fields
-~~~~~~
-g_list: Node in the global device list.
-
-node: Node in device's parent's children list.
-
-bus_list: Node in device's bus's devices list.
-
-driver_list: Node in device's driver's devices list.
-
-intf_list: List of intf_data. There is one structure allocated for
- each interface that the device supports.
-
-children: List of child devices.
-
-parent: *** FIXME ***
-
-name: ASCII description of device.
- Example: " 3Com Corporation 3c905 100BaseTX [Boomerang]"
-
-bus_id: ASCII representation of device's bus position. This
- field should be a name unique across all devices on the
- bus type the device belongs to.
-
- Example: PCI bus_ids are in the form of
- <bus number>:<slot number>.<function number>
- This name is unique across all PCI devices in the system.
-
-lock: Spinlock for the device.
-
-refcount: Reference count on the device.
-
-bus: Pointer to struct bus_type that device belongs to.
-
-dir: Device's sysfs directory.
-
-class_num: Class-enumerated value of the device.
-
-driver: Pointer to struct device_driver that controls the device.
-
-driver_data: Driver-specific data.
-
-platform_data: Platform data specific to the device.
-
- Example: for devices on custom boards, as typical of embedded
- and SOC based hardware, Linux often uses platform_data to point
- to board-specific structures describing devices and how they
- are wired. That can include what ports are available, chip
- variants, which GPIO pins act in what additional roles, and so
- on. This shrinks the "Board Support Packages" (BSPs) and
- minimizes board-specific #ifdefs in drivers.
-
-current_state: Current power state of the device.
-
-saved_state: Pointer to saved state of the device. This is usable by
- the device driver controlling the device.
-
-release: Callback to free the device after all references have
- gone away. This should be set by the allocator of the
- device (i.e. the bus driver that discovered the device).
+See the kerneldoc for the struct device.
Programming Interface
@@ -127,36 +38,69 @@ void unlock_device(struct device * dev);
Attributes
~~~~~~~~~~
struct device_attribute {
- struct attribute attr;
- ssize_t (*show)(struct device * dev, char * buf, size_t count, loff_t off);
- ssize_t (*store)(struct device * dev, const char * buf, size_t count, loff_t off);
+ struct attribute attr;
+ ssize_t (*show)(struct device *dev, struct device_attribute *attr,
+ char *buf);
+ ssize_t (*store)(struct device *dev, struct device_attribute *attr,
+ const char *buf, size_t count);
};
-Attributes of devices can be exported via drivers using a simple
-procfs-like interface.
+Attributes of devices can be exported by a device driver through sysfs.
Please see Documentation/filesystems/sysfs.txt for more information
on how sysfs works.
+As explained in Documentation/kobject.txt, device attributes must be be
+created before the KOBJ_ADD uevent is generated. The only way to realize
+that is by defining an attribute group.
+
Attributes are declared using a macro called DEVICE_ATTR:
#define DEVICE_ATTR(name,mode,show,store)
Example:
-DEVICE_ATTR(power,0644,show_power,store_power);
+static DEVICE_ATTR(type, 0444, show_type, NULL);
+static DEVICE_ATTR(power, 0644, show_power, store_power);
-This declares a structure of type struct device_attribute named
-'dev_attr_power'. This can then be added and removed to the device's
-directory using:
+This declares two structures of type struct device_attribute with respective
+names 'dev_attr_type' and 'dev_attr_power'. These two attributes can be
+organized as follows into a group:
-int device_create_file(struct device *device, struct device_attribute * entry);
-void device_remove_file(struct device * dev, struct device_attribute * attr);
+static struct attribute *dev_attrs[] = {
+ &dev_attr_type.attr,
+ &dev_attr_power.attr,
+ NULL,
+};
-Example:
+static struct attribute_group dev_attr_group = {
+ .attrs = dev_attrs,
+};
+
+static const struct attribute_group *dev_attr_groups[] = {
+ &dev_attr_group,
+ NULL,
+};
+
+This array of groups can then be associated with a device by setting the
+group pointer in struct device before device_register() is invoked:
+
+ dev->groups = dev_attr_groups;
+ device_register(dev);
-device_create_file(dev,&dev_attr_power);
-device_remove_file(dev,&dev_attr_power);
+The device_register() function will use the 'groups' pointer to create the
+device attributes and the device_unregister() function will use this pointer
+to remove the device attributes.
-The file name will be 'power' with a mode of 0644 (-rw-r--r--).
+Word of warning: While the kernel allows device_create_file() and
+device_remove_file() to be called on a device at any time, userspace has
+strict expectations on when attributes get created. When a new device is
+registered in the kernel, a uevent is generated to notify userspace (like
+udev) that a new device is available. If attributes are added after the
+device is registered, then userspace won't get notified and userspace will
+not know about the new attributes.
+This is important for device driver that need to publish additional
+attributes for a device at driver probe time. If the device driver simply
+calls device_create_file() on the device structure passed to it, then
+userspace will never be notified of the new attributes.
diff --git a/Documentation/driver-model/devres.txt b/Documentation/driver-model/devres.txt
new file mode 100644
index 00000000000..1525e30483f
--- /dev/null
+++ b/Documentation/driver-model/devres.txt
@@ -0,0 +1,325 @@
+Devres - Managed Device Resource
+================================
+
+Tejun Heo <teheo@suse.de>
+
+First draft 10 January 2007
+
+
+1. Intro : Huh? Devres?
+2. Devres : Devres in a nutshell
+3. Devres Group : Group devres'es and release them together
+4. Details : Life time rules, calling context, ...
+5. Overhead : How much do we have to pay for this?
+6. List of managed interfaces : Currently implemented managed interfaces
+
+
+ 1. Intro
+ --------
+
+devres came up while trying to convert libata to use iomap. Each
+iomapped address should be kept and unmapped on driver detach. For
+example, a plain SFF ATA controller (that is, good old PCI IDE) in
+native mode makes use of 5 PCI BARs and all of them should be
+maintained.
+
+As with many other device drivers, libata low level drivers have
+sufficient bugs in ->remove and ->probe failure path. Well, yes,
+that's probably because libata low level driver developers are lazy
+bunch, but aren't all low level driver developers? After spending a
+day fiddling with braindamaged hardware with no document or
+braindamaged document, if it's finally working, well, it's working.
+
+For one reason or another, low level drivers don't receive as much
+attention or testing as core code, and bugs on driver detach or
+initialization failure don't happen often enough to be noticeable.
+Init failure path is worse because it's much less travelled while
+needs to handle multiple entry points.
+
+So, many low level drivers end up leaking resources on driver detach
+and having half broken failure path implementation in ->probe() which
+would leak resources or even cause oops when failure occurs. iomap
+adds more to this mix. So do msi and msix.
+
+
+ 2. Devres
+ ---------
+
+devres is basically linked list of arbitrarily sized memory areas
+associated with a struct device. Each devres entry is associated with
+a release function. A devres can be released in several ways. No
+matter what, all devres entries are released on driver detach. On
+release, the associated release function is invoked and then the
+devres entry is freed.
+
+Managed interface is created for resources commonly used by device
+drivers using devres. For example, coherent DMA memory is acquired
+using dma_alloc_coherent(). The managed version is called
+dmam_alloc_coherent(). It is identical to dma_alloc_coherent() except
+for the DMA memory allocated using it is managed and will be
+automatically released on driver detach. Implementation looks like
+the following.
+
+ struct dma_devres {
+ size_t size;
+ void *vaddr;
+ dma_addr_t dma_handle;
+ };
+
+ static void dmam_coherent_release(struct device *dev, void *res)
+ {
+ struct dma_devres *this = res;
+
+ dma_free_coherent(dev, this->size, this->vaddr, this->dma_handle);
+ }
+
+ dmam_alloc_coherent(dev, size, dma_handle, gfp)
+ {
+ struct dma_devres *dr;
+ void *vaddr;
+
+ dr = devres_alloc(dmam_coherent_release, sizeof(*dr), gfp);
+ ...
+
+ /* alloc DMA memory as usual */
+ vaddr = dma_alloc_coherent(...);
+ ...
+
+ /* record size, vaddr, dma_handle in dr */
+ dr->vaddr = vaddr;
+ ...
+
+ devres_add(dev, dr);
+
+ return vaddr;
+ }
+
+If a driver uses dmam_alloc_coherent(), the area is guaranteed to be
+freed whether initialization fails half-way or the device gets
+detached. If most resources are acquired using managed interface, a
+driver can have much simpler init and exit code. Init path basically
+looks like the following.
+
+ my_init_one()
+ {
+ struct mydev *d;
+
+ d = devm_kzalloc(dev, sizeof(*d), GFP_KERNEL);
+ if (!d)
+ return -ENOMEM;
+
+ d->ring = dmam_alloc_coherent(...);
+ if (!d->ring)
+ return -ENOMEM;
+
+ if (check something)
+ return -EINVAL;
+ ...
+
+ return register_to_upper_layer(d);
+ }
+
+And exit path,
+
+ my_remove_one()
+ {
+ unregister_from_upper_layer(d);
+ shutdown_my_hardware();
+ }
+
+As shown above, low level drivers can be simplified a lot by using
+devres. Complexity is shifted from less maintained low level drivers
+to better maintained higher layer. Also, as init failure path is
+shared with exit path, both can get more testing.
+
+
+ 3. Devres group
+ ---------------
+
+Devres entries can be grouped using devres group. When a group is
+released, all contained normal devres entries and properly nested
+groups are released. One usage is to rollback series of acquired
+resources on failure. For example,
+
+ if (!devres_open_group(dev, NULL, GFP_KERNEL))
+ return -ENOMEM;
+
+ acquire A;
+ if (failed)
+ goto err;
+
+ acquire B;
+ if (failed)
+ goto err;
+ ...
+
+ devres_remove_group(dev, NULL);
+ return 0;
+
+ err:
+ devres_release_group(dev, NULL);
+ return err_code;
+
+As resource acquisition failure usually means probe failure, constructs
+like above are usually useful in midlayer driver (e.g. libata core
+layer) where interface function shouldn't have side effect on failure.
+For LLDs, just returning error code suffices in most cases.
+
+Each group is identified by void *id. It can either be explicitly
+specified by @id argument to devres_open_group() or automatically
+created by passing NULL as @id as in the above example. In both
+cases, devres_open_group() returns the group's id. The returned id
+can be passed to other devres functions to select the target group.
+If NULL is given to those functions, the latest open group is
+selected.
+
+For example, you can do something like the following.
+
+ int my_midlayer_create_something()
+ {
+ if (!devres_open_group(dev, my_midlayer_create_something, GFP_KERNEL))
+ return -ENOMEM;
+
+ ...
+
+ devres_close_group(dev, my_midlayer_create_something);
+ return 0;
+ }
+
+ void my_midlayer_destroy_something()
+ {
+ devres_release_group(dev, my_midlayer_create_something);
+ }
+
+
+ 4. Details
+ ----------
+
+Lifetime of a devres entry begins on devres allocation and finishes
+when it is released or destroyed (removed and freed) - no reference
+counting.
+
+devres core guarantees atomicity to all basic devres operations and
+has support for single-instance devres types (atomic
+lookup-and-add-if-not-found). Other than that, synchronizing
+concurrent accesses to allocated devres data is caller's
+responsibility. This is usually non-issue because bus ops and
+resource allocations already do the job.
+
+For an example of single-instance devres type, read pcim_iomap_table()
+in lib/devres.c.
+
+All devres interface functions can be called without context if the
+right gfp mask is given.
+
+
+ 5. Overhead
+ -----------
+
+Each devres bookkeeping info is allocated together with requested data
+area. With debug option turned off, bookkeeping info occupies 16
+bytes on 32bit machines and 24 bytes on 64bit (three pointers rounded
+up to ull alignment). If singly linked list is used, it can be
+reduced to two pointers (8 bytes on 32bit, 16 bytes on 64bit).
+
+Each devres group occupies 8 pointers. It can be reduced to 6 if
+singly linked list is used.
+
+Memory space overhead on ahci controller with two ports is between 300
+and 400 bytes on 32bit machine after naive conversion (we can
+certainly invest a bit more effort into libata core layer).
+
+
+ 6. List of managed interfaces
+ -----------------------------
+
+MEM
+ devm_kzalloc()
+ devm_kfree()
+ devm_kmemdup()
+ devm_get_free_pages()
+ devm_free_pages()
+
+IIO
+ devm_iio_device_alloc()
+ devm_iio_device_free()
+ devm_iio_trigger_alloc()
+ devm_iio_trigger_free()
+ devm_iio_device_register()
+ devm_iio_device_unregister()
+
+IO region
+ devm_request_region()
+ devm_request_mem_region()
+ devm_release_region()
+ devm_release_mem_region()
+
+IRQ
+ devm_request_irq()
+ devm_free_irq()
+
+DMA
+ dmam_alloc_coherent()
+ dmam_free_coherent()
+ dmam_alloc_noncoherent()
+ dmam_free_noncoherent()
+ dmam_declare_coherent_memory()
+ dmam_pool_create()
+ dmam_pool_destroy()
+
+PCI
+ pcim_enable_device() : after success, all PCI ops become managed
+ pcim_pin_device() : keep PCI device enabled after release
+
+IOMAP
+ devm_ioport_map()
+ devm_ioport_unmap()
+ devm_ioremap()
+ devm_ioremap_nocache()
+ devm_iounmap()
+ devm_ioremap_resource() : checks resource, requests memory region, ioremaps
+ devm_request_and_ioremap() : obsoleted by devm_ioremap_resource()
+ pcim_iomap()
+ pcim_iounmap()
+ pcim_iomap_table() : array of mapped addresses indexed by BAR
+ pcim_iomap_regions() : do request_region() and iomap() on multiple BARs
+
+REGULATOR
+ devm_regulator_get()
+ devm_regulator_put()
+ devm_regulator_bulk_get()
+ devm_regulator_register()
+
+CLOCK
+ devm_clk_get()
+ devm_clk_put()
+
+PINCTRL
+ devm_pinctrl_get()
+ devm_pinctrl_put()
+
+PWM
+ devm_pwm_get()
+ devm_pwm_put()
+
+PHY
+ devm_usb_get_phy()
+ devm_usb_put_phy()
+
+SLAVE DMA ENGINE
+ devm_acpi_dma_controller_register()
+
+SPI
+ devm_spi_register_master()
+
+GPIO
+ devm_gpiod_get()
+ devm_gpiod_get_index()
+ devm_gpiod_get_optional()
+ devm_gpiod_get_index_optional()
+ devm_gpiod_put()
+
+MDIO
+ devm_mdiobus_alloc()
+ devm_mdiobus_alloc_size()
+ devm_mdiobus_free()
diff --git a/Documentation/driver-model/driver.txt b/Documentation/driver-model/driver.txt
index fabaca1ab1b..4421135826a 100644
--- a/Documentation/driver-model/driver.txt
+++ b/Documentation/driver-model/driver.txt
@@ -1,23 +1,7 @@
Device Drivers
-struct device_driver {
- char * name;
- struct bus_type * bus;
-
- struct completion unloaded;
- struct kobject kobj;
- list_t devices;
-
- struct module *owner;
-
- int (*probe) (struct device * dev);
- int (*remove) (struct device * dev);
-
- int (*suspend) (struct device * dev, pm_message_t state, u32 level);
- int (*resume) (struct device * dev, u32 level);
-};
-
+See the kerneldoc for the struct device_driver.
Allocation
@@ -178,7 +162,7 @@ the driver to that device.
A driver's probe() may return a negative errno value to indicate that
the driver did not bind to this device, in which case it should have
-released all reasources it allocated.
+released all resources it allocated.
int (*remove) (struct device * dev);
@@ -194,77 +178,21 @@ device; i.e. anything in the device's driver_data field.
If the device is still present, it should quiesce the device and place
it into a supported low-power state.
- int (*suspend) (struct device * dev, pm_message_t state, u32 level);
-
-suspend is called to put the device in a low power state. There are
-several stages to successfully suspending a device, which is denoted in
-the @level parameter. Breaking the suspend transition into several
-stages affords the platform flexibility in performing device power
-management based on the requirements of the system and the
-user-defined policy.
-
-SUSPEND_NOTIFY notifies the device that a suspend transition is about
-to happen. This happens on system power state transitions to verify
-that all devices can successfully suspend.
-
-A driver may choose to fail on this call, which should cause the
-entire suspend transition to fail. A driver should fail only if it
-knows that the device will not be able to be resumed properly when the
-system wakes up again. It could also fail if it somehow determines it
-is in the middle of an operation too important to stop.
-
-SUSPEND_DISABLE tells the device to stop I/O transactions. When it
-stops transactions, or what it should do with unfinished transactions
-is a policy of the driver. After this call, the driver should not
-accept any other I/O requests.
-
-SUSPEND_SAVE_STATE tells the device to save the context of the
-hardware. This includes any bus-specific hardware state and
-device-specific hardware state. A pointer to this saved state can be
-stored in the device's saved_state field.
-
-SUSPEND_POWER_DOWN tells the driver to place the device in the low
-power state requested.
-
-Whether suspend is called with a given level is a policy of the
-platform. Some levels may be omitted; drivers must not assume the
-reception of any level. However, all levels must be called in the
-order above; i.e. notification will always come before disabling;
-disabling the device will come before suspending the device.
-
-All calls are made with interrupts enabled, except for the
-SUSPEND_POWER_DOWN level.
-
- int (*resume) (struct device * dev, u32 level);
-
-Resume is used to bring a device back from a low power state. Like the
-suspend transition, it happens in several stages.
-
-RESUME_POWER_ON tells the driver to set the power state to the state
-before the suspend call (The device could have already been in a low
-power state before the suspend call to put in a lower power state).
-
-RESUME_RESTORE_STATE tells the driver to restore the state saved by
-the SUSPEND_SAVE_STATE suspend call.
+ int (*suspend) (struct device * dev, pm_message_t state);
-RESUME_ENABLE tells the driver to start accepting I/O transactions
-again. Depending on driver policy, the device may already have pending
-I/O requests.
+suspend is called to put the device in a low power state.
-RESUME_POWER_ON is called with interrupts disabled. The other resume
-levels are called with interrupts enabled.
+ int (*resume) (struct device * dev);
-As with the various suspend stages, the driver must not assume that
-any other resume calls have been or will be made. Each call should be
-self-contained and not dependent on any external state.
+Resume is used to bring a device back from a low power state.
Attributes
~~~~~~~~~~
struct driver_attribute {
struct attribute attr;
- ssize_t (*show)(struct device_driver *, char * buf, size_t count, loff_t off);
- ssize_t (*store)(struct device_driver *, const char * buf, size_t count, loff_t off);
+ ssize_t (*show)(struct device_driver *driver, char *buf);
+ ssize_t (*store)(struct device_driver *, const char * buf, size_t count);
};
Device drivers can export attributes via their sysfs directories.
@@ -282,5 +210,5 @@ struct driver_attribute driver_attr_debug;
This can then be used to add and remove the attribute from the
driver's directory using:
-int driver_create_file(struct device_driver *, struct driver_attribute *);
-void driver_remove_file(struct device_driver *, struct driver_attribute *);
+int driver_create_file(struct device_driver *, const struct driver_attribute *);
+void driver_remove_file(struct device_driver *, const struct driver_attribute *);
diff --git a/Documentation/driver-model/interface.txt b/Documentation/driver-model/interface.txt
deleted file mode 100644
index c66912bfe86..00000000000
--- a/Documentation/driver-model/interface.txt
+++ /dev/null
@@ -1,129 +0,0 @@
-
-Device Interfaces
-
-Introduction
-~~~~~~~~~~~~
-
-Device interfaces are the logical interfaces of device classes that correlate
-directly to userspace interfaces, like device nodes.
-
-Each device class may have multiple interfaces through which you can
-access the same device. An input device may support the mouse interface,
-the 'evdev' interface, and the touchscreen interface. A SCSI disk would
-support the disk interface, the SCSI generic interface, and possibly a raw
-device interface.
-
-Device interfaces are registered with the class they belong to. As devices
-are added to the class, they are added to each interface registered with
-the class. The interface is responsible for determining whether the device
-supports the interface or not.
-
-
-Programming Interface
-~~~~~~~~~~~~~~~~~~~~~
-
-struct device_interface {
- char * name;
- rwlock_t lock;
- u32 devnum;
- struct device_class * devclass;
-
- struct list_head node;
- struct driver_dir_entry dir;
-
- int (*add_device)(struct device *);
- int (*add_device)(struct intf_data *);
-};
-
-int interface_register(struct device_interface *);
-void interface_unregister(struct device_interface *);
-
-
-An interface must specify the device class it belongs to. It is added
-to that class's list of interfaces on registration.
-
-
-Interfaces can be added to a device class at any time. Whenever it is
-added, each device in the class is passed to the interface's
-add_device callback. When an interface is removed, each device is
-removed from the interface.
-
-
-Devices
-~~~~~~~
-Once a device is added to a device class, it is added to each
-interface that is registered with the device class. The class
-is expected to place a class-specific data structure in
-struct device::class_data. The interface can use that (along with
-other fields of struct device) to determine whether or not the driver
-and/or device support that particular interface.
-
-
-Data
-~~~~
-
-struct intf_data {
- struct list_head node;
- struct device_interface * intf;
- struct device * dev;
- u32 intf_num;
-};
-
-int interface_add_data(struct interface_data *);
-
-The interface is responsible for allocating and initializing a struct
-intf_data and calling interface_add_data() to add it to the device's list
-of interfaces it belongs to. This list will be iterated over when the device
-is removed from the class (instead of all possible interfaces for a class).
-This structure should probably be embedded in whatever per-device data
-structure the interface is allocating anyway.
-
-Devices are enumerated within the interface. This happens in interface_add_data()
-and the enumerated value is stored in the struct intf_data for that device.
-
-sysfs
-~~~~~
-Each interface is given a directory in the directory of the device
-class it belongs to:
-
-Interfaces get a directory in the class's directory as well:
-
- class/
- `-- input
- |-- devices
- |-- drivers
- |-- mouse
- `-- evdev
-
-When a device is added to the interface, a symlink is created that points
-to the device's directory in the physical hierarchy:
-
- class/
- `-- input
- |-- devices
- | `-- 1 -> ../../../root/pci0/00:1f.0/usb_bus/00:1f.2-1:0/
- |-- drivers
- | `-- usb:usb_mouse -> ../../../bus/drivers/usb_mouse/
- |-- mouse
- | `-- 1 -> ../../../root/pci0/00:1f.0/usb_bus/00:1f.2-1:0/
- `-- evdev
- `-- 1 -> ../../../root/pci0/00:1f.0/usb_bus/00:1f.2-1:0/
-
-
-Future Plans
-~~~~~~~~~~~~
-A device interface is correlated directly with a userspace interface
-for a device, specifically a device node. For instance, a SCSI disk
-exposes at least two interfaces to userspace: the standard SCSI disk
-interface and the SCSI generic interface. It might also export a raw
-device interface.
-
-Many interfaces have a major number associated with them and each
-device gets a minor number. Or, multiple interfaces might share one
-major number, and each will receive a range of minor numbers (like in
-the case of input devices).
-
-These major and minor numbers could be stored in the interface
-structure. Major and minor allocations could happen when the interface
-is registered with the class, or via a helper function.
-
diff --git a/Documentation/driver-model/overview.txt b/Documentation/driver-model/overview.txt
index 44662735cf8..6a8f9a8075d 100644
--- a/Documentation/driver-model/overview.txt
+++ b/Documentation/driver-model/overview.txt
@@ -1,50 +1,43 @@
The Linux Kernel Device Model
-Patrick Mochel <mochel@osdl.org>
+Patrick Mochel <mochel@digitalimplant.org>
-26 August 2002
+Drafted 26 August 2002
+Updated 31 January 2006
Overview
~~~~~~~~
-This driver model is a unification of all the current, disparate driver models
-that are currently in the kernel. It is intended to augment the
+The Linux Kernel Driver Model is a unification of all the disparate driver
+models that were previously used in the kernel. It is intended to augment the
bus-specific drivers for bridges and devices by consolidating a set of data
and operations into globally accessible data structures.
-Current driver models implement some sort of tree-like structure (sometimes
-just a list) for the devices they control. But, there is no linkage between
-the different bus types.
+Traditional driver models implemented some sort of tree-like structure
+(sometimes just a list) for the devices they control. There wasn't any
+uniformity across the different bus types.
-A common data structure can provide this linkage with little overhead: when a
-bus driver discovers a particular device, it can insert it into the global
-tree as well as its local tree. In fact, the local tree becomes just a subset
-of the global tree.
-
-Common data fields can also be moved out of the local bus models into the
-global model. Some of the manipulations of these fields can also be
-consolidated. Most likely, manipulation functions will become a set
-of helper functions, which the bus drivers wrap around to include any
-bus-specific items.
-
-The common device and bridge interface currently reflects the goals of the
-modern PC: namely the ability to do seamless Plug and Play, power management,
-and hot plug. (The model dictated by Intel and Microsoft (read: ACPI) ensures
-us that any device in the system may fit any of these criteria.)
-
-In reality, not every bus will be able to support such operations. But, most
-buses will support a majority of those operations, and all future buses will.
-In other words, a bus that doesn't support an operation is the exception,
-instead of the other way around.
+The current driver model provides a common, uniform data model for describing
+a bus and the devices that can appear under the bus. The unified bus
+model includes a set of common attributes which all busses carry, and a set
+of common callbacks, such as device discovery during bus probing, bus
+shutdown, bus power management, etc.
+The common device and bridge interface reflects the goals of the modern
+computer: namely the ability to do seamless device "plug and play", power
+management, and hot plug. In particular, the model dictated by Intel and
+Microsoft (namely ACPI) ensures that almost every device on almost any bus
+on an x86-compatible system can work within this paradigm. Of course,
+not every bus is able to support all such operations, although most
+buses support most of those operations.
Downstream Access
~~~~~~~~~~~~~~~~~
Common data fields have been moved out of individual bus layers into a common
-data structure. But, these fields must still be accessed by the bus layers,
+data structure. These fields must still be accessed by the bus layers,
and sometimes by the device-specific drivers.
Other bus layers are encouraged to do what has been done for the PCI layer.
@@ -53,25 +46,29 @@ struct pci_dev now looks like this:
struct pci_dev {
...
- struct device device;
+ struct device dev; /* Generic device interface */
+ ...
};
-Note first that it is statically allocated. This means only one allocation on
-device discovery. Note also that it is at the _end_ of struct pci_dev. This is
-to make people think about what they're doing when switching between the bus
-driver and the global driver; and to prevent against mindless casts between
-the two.
+Note first that the struct device dev within the struct pci_dev is
+statically allocated. This means only one allocation on device discovery.
+
+Note also that that struct device dev is not necessarily defined at the
+front of the pci_dev structure. This is to make people think about what
+they're doing when switching between the bus driver and the global driver,
+and to discourage meaningless and incorrect casts between the two.
The PCI bus layer freely accesses the fields of struct device. It knows about
the structure of struct pci_dev, and it should know the structure of struct
-device. PCI devices that have been converted generally do not touch the fields
-of struct device. More precisely, device-specific drivers should not touch
-fields of struct device unless there is a strong compelling reason to do so.
+device. Individual PCI device drivers that have been converted to the current
+driver model generally do not and should not touch the fields of struct device,
+unless there is a compelling reason to do so.
-This abstraction is prevention of unnecessary pain during transitional phases.
-If the name of the field changes or is removed, then every downstream driver
-will break. On the other hand, if only the bus layer (and not the device
-layer) accesses struct device, it is only that layer that needs to change.
+The above abstraction prevents unnecessary pain during transitional phases.
+If it were not done this way, then when a field was renamed or removed, every
+downstream driver would break. On the other hand, if only the bus layer
+(and not the device layer) accesses the struct device, it is only the bus
+layer that needs to change.
User Interface
@@ -80,15 +77,27 @@ User Interface
By virtue of having a complete hierarchical view of all the devices in the
system, exporting a complete hierarchical view to userspace becomes relatively
easy. This has been accomplished by implementing a special purpose virtual
-file system named sysfs. It is hence possible for the user to mount the
-whole sysfs filesystem anywhere in userspace.
+file system named sysfs.
+
+Almost all mainstream Linux distros mount this filesystem automatically; you
+can see some variation of the following in the output of the "mount" command:
+
+$ mount
+...
+none on /sys type sysfs (rw,noexec,nosuid,nodev)
+...
+$
+
+The auto-mounting of sysfs is typically accomplished by an entry similar to
+the following in the /etc/fstab file:
+
+none /sys sysfs defaults 0 0
-This can be done permanently by providing the following entry into the
-/etc/fstab (under the provision that the mount point does exist, of course):
+or something similar in the /lib/init/fstab file on Debian-based systems:
-none /sys sysfs defaults 0 0
+none /sys sysfs nodev,noexec,nosuid 0 0
-Or by hand on the command line:
+If sysfs is not automatically mounted, you can always do it manually with:
# mount -t sysfs sysfs /sys
diff --git a/Documentation/driver-model/platform.txt b/Documentation/driver-model/platform.txt
index 5eee3e0bfc4..07795ec51cd 100644
--- a/Documentation/driver-model/platform.txt
+++ b/Documentation/driver-model/platform.txt
@@ -1,99 +1,230 @@
Platform Devices and Drivers
~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+See <linux/platform_device.h> for the driver model interface to the
+platform bus: platform_device, and platform_driver. This pseudo-bus
+is used to connect devices on busses with minimal infrastructure,
+like those used to integrate peripherals on many system-on-chip
+processors, or some "legacy" PC interconnects; as opposed to large
+formally specified ones like PCI or USB.
+
Platform devices
~~~~~~~~~~~~~~~~
Platform devices are devices that typically appear as autonomous
entities in the system. This includes legacy port-based devices and
-host bridges to peripheral buses.
-
-
-Platform drivers
-~~~~~~~~~~~~~~~~
-Drivers for platform devices are typically very simple and
-unstructured. Either the device was present at a particular I/O port
-and the driver was loaded, or it was not. There was no possibility
-of hotplugging or alternative discovery besides probing at a specific
-I/O address and expecting a specific response.
+host bridges to peripheral buses, and most controllers integrated
+into system-on-chip platforms. What they usually have in common
+is direct addressing from a CPU bus. Rarely, a platform_device will
+be connected through a segment of some other kind of bus; but its
+registers will still be directly addressable.
+Platform devices are given a name, used in driver binding, and a
+list of resources such as addresses and IRQs.
-Other Architectures, Modern Firmware, and new Platforms
-~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
-These devices are not always at the legacy I/O ports. This is true on
-other architectures and on some modern architectures. In most cases,
-the drivers are modified to discover the devices at other well-known
-ports for the given platform. However, the firmware in these systems
-does usually know where exactly these devices reside, and in some
-cases, it's the only way of discovering them.
+struct platform_device {
+ const char *name;
+ u32 id;
+ struct device dev;
+ u32 num_resources;
+ struct resource *resource;
+};
-The Platform Bus
+Platform drivers
~~~~~~~~~~~~~~~~
-A platform bus has been created to deal with these issues. First and
-foremost, it groups all the legacy devices under a common bus, and
-gives them a common parent if they don't already have one.
-
-But, besides the organizational benefits, the platform bus can also
-accommodate firmware-based enumeration.
+Platform drivers follow the standard driver model convention, where
+discovery/enumeration is handled outside the drivers, and drivers
+provide probe() and remove() methods. They support power management
+and shutdown notifications using the standard conventions.
+
+struct platform_driver {
+ int (*probe)(struct platform_device *);
+ int (*remove)(struct platform_device *);
+ void (*shutdown)(struct platform_device *);
+ int (*suspend)(struct platform_device *, pm_message_t state);
+ int (*suspend_late)(struct platform_device *, pm_message_t state);
+ int (*resume_early)(struct platform_device *);
+ int (*resume)(struct platform_device *);
+ struct device_driver driver;
+};
+
+Note that probe() should in general verify that the specified device hardware
+actually exists; sometimes platform setup code can't be sure. The probing
+can use device resources, including clocks, and device platform_data.
+
+Platform drivers register themselves the normal way:
+
+ int platform_driver_register(struct platform_driver *drv);
+
+Or, in common situations where the device is known not to be hot-pluggable,
+the probe() routine can live in an init section to reduce the driver's
+runtime memory footprint:
+
+ int platform_driver_probe(struct platform_driver *drv,
+ int (*probe)(struct platform_device *))
+
+
+Device Enumeration
+~~~~~~~~~~~~~~~~~~
+As a rule, platform specific (and often board-specific) setup code will
+register platform devices:
+
+ int platform_device_register(struct platform_device *pdev);
+ int platform_add_devices(struct platform_device **pdevs, int ndev);
+
+The general rule is to register only those devices that actually exist,
+but in some cases extra devices might be registered. For example, a kernel
+might be configured to work with an external network adapter that might not
+be populated on all boards, or likewise to work with an integrated controller
+that some boards might not hook up to any peripherals.
-Device Discovery
-~~~~~~~~~~~~~~~~
-The platform bus has no concept of probing for devices. Devices
-discovery is left up to either the legacy drivers or the
-firmware. These entities are expected to notify the platform of
-devices that it discovers via the bus's add() callback:
-
- platform_bus.add(parent,bus_id).
-
-
-Bus IDs
-~~~~~~~
-Bus IDs are the canonical names for the devices. There is no globally
-standard addressing mechanism for legacy devices. In the IA-32 world,
-we have Pnp IDs to use, as well as the legacy I/O ports. However,
-neither tell what the device really is or have any meaning on other
-platforms.
-
-Since both PnP IDs and the legacy I/O ports (and other standard I/O
-ports for specific devices) have a 1:1 mapping, we map the
-platform-specific name or identifier to a generic name (at least
-within the scope of the kernel).
-
-For example, a serial driver might find a device at I/O 0x3f8. The
-ACPI firmware might also discover a device with PnP ID (_HID)
-PNP0501. Both correspond to the same device and should be mapped to the
-canonical name 'serial'.
-
-The bus_id field should be a concatenation of the canonical name and
-the instance of that type of device. For example, the device at I/O
-port 0x3f8 should have a bus_id of "serial0". This places the
-responsibility of enumerating devices of a particular type up to the
-discovery mechanism. But, they are the entity that should know best
-(as opposed to the platform bus driver).
-
-
-Drivers
-~~~~~~~
-Drivers for platform devices should have a name that is the same as
-the canonical name of the devices they support. This allows the
-platform bus driver to do simple matching with the basic data
-structures to determine if a driver supports a certain device.
-
-For example, a legacy serial driver should have a name of 'serial' and
-register itself with the platform bus.
-
-
-Driver Binding
-~~~~~~~~~~~~~~
-Legacy drivers assume they are bound to the device once they start up
-and probe an I/O port. Divorcing them from this will be a difficult
-process. However, that shouldn't prevent us from implementing
-firmware-based enumeration.
-
-The firmware should notify the platform bus about devices before the
-legacy drivers have had a chance to load. Once the drivers are loaded,
-they driver model core will attempt to bind the driver to any
-previously-discovered devices. Once that has happened, it will be free
-to discover any other devices it pleases.
-
+In some cases, boot firmware will export tables describing the devices
+that are populated on a given board. Without such tables, often the
+only way for system setup code to set up the correct devices is to build
+a kernel for a specific target board. Such board-specific kernels are
+common with embedded and custom systems development.
+
+In many cases, the memory and IRQ resources associated with the platform
+device are not enough to let the device's driver work. Board setup code
+will often provide additional information using the device's platform_data
+field to hold additional information.
+
+Embedded systems frequently need one or more clocks for platform devices,
+which are normally kept off until they're actively needed (to save power).
+System setup also associates those clocks with the device, so that that
+calls to clk_get(&pdev->dev, clock_name) return them as needed.
+
+
+Legacy Drivers: Device Probing
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+Some drivers are not fully converted to the driver model, because they take
+on a non-driver role: the driver registers its platform device, rather than
+leaving that for system infrastructure. Such drivers can't be hotplugged
+or coldplugged, since those mechanisms require device creation to be in a
+different system component than the driver.
+
+The only "good" reason for this is to handle older system designs which, like
+original IBM PCs, rely on error-prone "probe-the-hardware" models for hardware
+configuration. Newer systems have largely abandoned that model, in favor of
+bus-level support for dynamic configuration (PCI, USB), or device tables
+provided by the boot firmware (e.g. PNPACPI on x86). There are too many
+conflicting options about what might be where, and even educated guesses by
+an operating system will be wrong often enough to make trouble.
+
+This style of driver is discouraged. If you're updating such a driver,
+please try to move the device enumeration to a more appropriate location,
+outside the driver. This will usually be cleanup, since such drivers
+tend to already have "normal" modes, such as ones using device nodes that
+were created by PNP or by platform device setup.
+
+None the less, there are some APIs to support such legacy drivers. Avoid
+using these calls except with such hotplug-deficient drivers.
+
+ struct platform_device *platform_device_alloc(
+ const char *name, int id);
+
+You can use platform_device_alloc() to dynamically allocate a device, which
+you will then initialize with resources and platform_device_register().
+A better solution is usually:
+
+ struct platform_device *platform_device_register_simple(
+ const char *name, int id,
+ struct resource *res, unsigned int nres);
+
+You can use platform_device_register_simple() as a one-step call to allocate
+and register a device.
+
+
+Device Naming and Driver Binding
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+The platform_device.dev.bus_id is the canonical name for the devices.
+It's built from two components:
+
+ * platform_device.name ... which is also used to for driver matching.
+
+ * platform_device.id ... the device instance number, or else "-1"
+ to indicate there's only one.
+
+These are concatenated, so name/id "serial"/0 indicates bus_id "serial.0", and
+"serial/3" indicates bus_id "serial.3"; both would use the platform_driver
+named "serial". While "my_rtc"/-1 would be bus_id "my_rtc" (no instance id)
+and use the platform_driver called "my_rtc".
+
+Driver binding is performed automatically by the driver core, invoking
+driver probe() after finding a match between device and driver. If the
+probe() succeeds, the driver and device are bound as usual. There are
+three different ways to find such a match:
+
+ - Whenever a device is registered, the drivers for that bus are
+ checked for matches. Platform devices should be registered very
+ early during system boot.
+
+ - When a driver is registered using platform_driver_register(), all
+ unbound devices on that bus are checked for matches. Drivers
+ usually register later during booting, or by module loading.
+
+ - Registering a driver using platform_driver_probe() works just like
+ using platform_driver_register(), except that the driver won't
+ be probed later if another device registers. (Which is OK, since
+ this interface is only for use with non-hotpluggable devices.)
+
+
+Early Platform Devices and Drivers
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+The early platform interfaces provide platform data to platform device
+drivers early on during the system boot. The code is built on top of the
+early_param() command line parsing and can be executed very early on.
+
+Example: "earlyprintk" class early serial console in 6 steps
+
+1. Registering early platform device data
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+The architecture code registers platform device data using the function
+early_platform_add_devices(). In the case of early serial console this
+should be hardware configuration for the serial port. Devices registered
+at this point will later on be matched against early platform drivers.
+
+2. Parsing kernel command line
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+The architecture code calls parse_early_param() to parse the kernel
+command line. This will execute all matching early_param() callbacks.
+User specified early platform devices will be registered at this point.
+For the early serial console case the user can specify port on the
+kernel command line as "earlyprintk=serial.0" where "earlyprintk" is
+the class string, "serial" is the name of the platform driver and
+0 is the platform device id. If the id is -1 then the dot and the
+id can be omitted.
+
+3. Installing early platform drivers belonging to a certain class
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+The architecture code may optionally force registration of all early
+platform drivers belonging to a certain class using the function
+early_platform_driver_register_all(). User specified devices from
+step 2 have priority over these. This step is omitted by the serial
+driver example since the early serial driver code should be disabled
+unless the user has specified port on the kernel command line.
+
+4. Early platform driver registration
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+Compiled-in platform drivers making use of early_platform_init() are
+automatically registered during step 2 or 3. The serial driver example
+should use early_platform_init("earlyprintk", &platform_driver).
+
+5. Probing of early platform drivers belonging to a certain class
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+The architecture code calls early_platform_driver_probe() to match
+registered early platform devices associated with a certain class with
+registered early platform drivers. Matched devices will get probed().
+This step can be executed at any point during the early boot. As soon
+as possible may be good for the serial port case.
+
+6. Inside the early platform driver probe()
+~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+The driver code needs to take special care during early boot, especially
+when it comes to memory allocation and interrupt registration. The code
+in the probe() function can use is_early_platform_device() to check if
+it is called at early platform device or at the regular platform device
+time. The early serial driver performs register_console() at this point.
+
+For further information, see <linux/platform_device.h>.
diff --git a/Documentation/driver-model/porting.txt b/Documentation/driver-model/porting.txt
index ff2fef2107f..92d86f7271b 100644
--- a/Documentation/driver-model/porting.txt
+++ b/Documentation/driver-model/porting.txt
@@ -92,7 +92,7 @@ struct device represents a single device. It mainly contains metadata
describing the relationship the device has to other entities.
-- Embedd a struct device in the bus-specific device type.
+- Embed a struct device in the bus-specific device type.
struct pci_dev {
@@ -350,7 +350,7 @@ When a driver is registered, the bus's list of devices is iterated
over. bus->match() is called for each device that is not already
claimed by a driver.
-When a device is successfully bound to a device, device->driver is
+When a device is successfully bound to a driver, device->driver is
set, the device is added to a per-driver list of devices, and a
symlink is created in the driver's sysfs directory that points to the
device's physical directory: