summaryrefslogtreecommitdiffstats
path: root/drivers/base/component.c
Commit message (Collapse)AuthorAgeFilesLines
* Merge 4.5-rc4 into driver-core-nextGreg Kroah-Hartman2016-02-141-21/+28
|\ | | | | | | | | | | We want the fixes in here as well. Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
| * component: remove device from master match list on failed addDaniel Stone2016-02-111-0/+2
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | Calling component_add() may result in the completion of a set of devices, which will try to bring up a master. In bringing the master up, we populate its match array with the current set of children. If binding any of the devices fails, component_add() itself will fail, free the struct component entry, and return to the caller. The now-freed entry is never removed from the master's match array, and will later be used in a futile attempt to bind to freed memory. Bring component_add's behaviour on failure to bring up a master into line with component_del by removing the (to-be-freed) component from the master's match array. The specific case which broke was: - rockchip_drm_drv adds a component master - dwhdmi_rockchip adds a child component in probe (master incomplete) - rockchip_drm_vop adds two children in probe, which completes the set - inside component_add, we try to bring up the master, having populated the master's match array, and fail with EPROBE_DEFER from dwhdmi_rockchip; we delete the putative component - rockchip_drm_vop's probe fails and returns EPROBE_DEFER - we later re-probe rockchip_drm_vop and add the component; the master is complete, so we attempt to bring it up again - walking the match array, we find the previous child, whose master pointer doesn't match (as it has been freed in the meantime) - rockchip_drm_vop probe fails, and will never be attempted again Fixes: ffc30b74fd6d01588bd3fdebc3b1acc0857e6fc8 Signed-off-by: Daniel Stone <daniels@collabora.com> Cc: Russell King <rmk+kernel@arm.linux.org.uk> Cc: Thierry Reding <treding@nvidia.com> Cc: Laurent Pinchart <laurent.pinchart@ideasonboard.com> Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
| * component: Detach components when deleting master structJon Medhurst (Tixy)2016-01-271-19/+22
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | component_master_add_with_match calls find_components which, if any components already exist, it attaches to the master struct. However, if we later encounter an error the master struct is deleted, leaving components with a dangling pointer to it. If the error was a temporary one, e.g. for probe deferral, then when the master device is re-probed, it will fail to find the required components as they appear to already be attached to a master. Fix this by nulling components pointers to the master struct when it is deleted. This code is factored out into a separate function so it can be shared with component_master_del. Signed-off-by: Jon Medhurst <tixy@linaro.org> Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
| * component: fix crash on x86_64 with hda audio driversRussell King2016-01-261-2/+4
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | Maarten reports that the addition of releasing match data to the component helper results in a general protection fault on x86_64. This is caused by the devm resources being freed in reverse order to their allocation, which caused a use-after-free of the match array. Switch the match array to be a more conventional kmalloc/kfree() affair, explicitly freeing it along with the parent match data structure. Reported-by: Maarten Lankhorst <maarten.lankhorst@linux.intel.com> Fixes: ce657b1cddf1 ("component: add support for releasing match data") Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
* | component: remove impossible conditionSudip Mukherjee2016-02-091-1/+1
|/ | | | | | | | | | We will be evaluating this condition only if match->num == match->alloc and that means we have already dereferenced match which implies match can not be NULL at this point. Moreover we have done a NULL check on match just before this. Signed-off-by: Sudip Mukherjee <sudip@vectorindia.org> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
* component: add support for releasing match dataRussell King2015-12-071-35/+66
| | | | | | | | | | | | | | | The component helper treats the void match data pointer as an opaque object which needs no further management. When device nodes being passed, this is not true: the caller should pass its refcount to the component helper, and there should be a way to drop the refcount when the matching information is destroyed. This patch provides a per-match release method in addition to the match method to solve this issue. Rather than using component_match_add(), users should use component_match_add_release() which takes an additional function pointer for releasing this reference. Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
* component: track components via array rather than listRussell King2015-12-071-74/+80
| | | | | | | | | | Since we now have an array which defines each component, maintain the components to be bound in the array rather than a separate list. We also need duplicate tracking so we can eliminate multiple bind calls for the same component: we preserve the list-based component order in that the first match which adds the component determines its position. Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
* component: move check for unbound master into try_to_bring_up_masters()Russell King2015-12-071-10/+5
| | | | | | | | | | Clean up the code a little; we don't need to check that the master is unbound for every invocation of try_to_bring_up_master(), so let's move it to where it's really needed - try_to_bring_up_masters(), where we may encounter already bound masters. Reviewed-by: Thierry Reding <treding@nvidia.com> Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
* component: remove old add_components methodRussell King2015-12-071-26/+5
| | | | | | | | | | | Now that drivers create an array of component matches at probe time, we can retire the old methods. This involves removing the add_components master method, and removing component_master_add_child() from public view. We also remove component_add_master() as that interface is no longer useful. Acked-by: Andrew Lunn <andrew@lunn.ch> Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
* component: fix bug with legacy APIRussell King2014-07-041-4/+6
| | | | | | | | | Sachin Kamat reports that "component: add support for component match array" broke Exynos DRM due to a NULL pointer deref. Fix this. Reported-by: Sachin Kamat <sachin.kamat@samsung.com> Tested-by: Sachin Kamat <sachin.kamat@samsung.com> Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
* component: add support for component match arrayRussell King2014-07-031-3/+117
| | | | | | | | | | | Add support for generating a set of component matches at master probe time, and submitting them to the component layer. This allows the component layer to perform the matches internally without needing to call into the master driver, and allows for further restructuring of the component helper. Acked-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com> Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
* component: ignore multiple additions of the same componentRussell King2014-07-031-2/+8
| | | | | | | | | | Permit masters to call component_master_add_child() and match the same child multiple times. This may happen if there's multiple connections to a single component device from other devices. In such scenarios, we should not return a failure, but instead ignore the attempt. Acked-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com> Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
* component: fix missed cleanup in case of devres failureRussell King2014-07-031-31/+31
| | | | | | | | | In try_to_bring_up_master(), we tear down the master's component list for each error case, except for devres group failure. Fix this oversight by making the code less prone to such mistakes. Acked-by: Laurent Pinchart <laurent.pinchart@ideasonboard.com> Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
* drivers/base: fix devres handling for master deviceRussell King2014-02-071-0/+8
| | | | | | | | | We weren't handling the devres issues for the master device failing a bind, or being unbound properly. Add a devres group to contain these, and release the resources at the appropriate points. Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
* drivers/base: provide an infrastructure for componentised subsystemsRussell King2014-01-101-0/+382
Subsystems such as ALSA, DRM and others require a single card-level device structure to represent a subsystem. However, firmware tends to describe the individual devices and the connections between them. Therefore, we need a way to gather up the individual component devices together, and indicate when we have all the component devices. We do this in DT by providing a "superdevice" node which specifies the components, eg: imx-drm { compatible = "fsl,drm"; crtcs = <&ipu1>; connectors = <&hdmi>; }; The superdevice is declared into the component support, along with the subcomponents. The superdevice receives callbacks to locate the subcomponents, and identify when all components are present. At this point, we bind the superdevice, which causes the appropriate subsystem to be initialised in the conventional way. When any of the components or superdevice are removed from the system, we unbind the superdevice, thereby taking the subsystem down. Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk> Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>