diff options
author | Oded Gabbay <oded.gabbay@gmail.com> | 2019-07-30 11:56:09 +0300 |
---|---|---|
committer | Oded Gabbay <oded.gabbay@gmail.com> | 2019-09-05 14:55:26 +0300 |
commit | eb7caf84b029387fe5addb484a0fc5792a9058e1 (patch) | |
tree | ef8f47ebec036c8eb39a5a93ebfb95f453b5f856 /drivers/misc/habanalabs/goya | |
parent | 86d5307a6d3507258460939fab040c6aafb506f9 (diff) |
habanalabs: maintain a list of file private data objects
This patch adds a new list to the driver's device structure. The list will
keep the file private data structures that the driver creates when a user
process opens the device.
This change is needed because it is useless to try to count how many FD
are open. Instead, track our own private data structure per open file and
once it is released, remove it from the list. As long as the list is not
empty, it means we have a user that can do something with our device.
Signed-off-by: Oded Gabbay <oded.gabbay@gmail.com>
Reviewed-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org>
Diffstat (limited to 'drivers/misc/habanalabs/goya')
-rw-r--r-- | drivers/misc/habanalabs/goya/goya_hwmgr.c | 27 |
1 files changed, 19 insertions, 8 deletions
diff --git a/drivers/misc/habanalabs/goya/goya_hwmgr.c b/drivers/misc/habanalabs/goya/goya_hwmgr.c index a51d836542a1..a2a700c3d597 100644 --- a/drivers/misc/habanalabs/goya/goya_hwmgr.c +++ b/drivers/misc/habanalabs/goya/goya_hwmgr.c @@ -254,11 +254,11 @@ static ssize_t pm_mng_profile_store(struct device *dev, goto out; } - mutex_lock(&hdev->fd_open_cnt_lock); + mutex_lock(&hdev->fpriv_list_lock); - if (atomic_read(&hdev->fd_open_cnt) > 0) { + if (hdev->compute_ctx) { dev_err(hdev->dev, - "Can't change PM profile while user process is opened on the device\n"); + "Can't change PM profile while compute context is opened on the device\n"); count = -EPERM; goto unlock_mutex; } @@ -266,24 +266,35 @@ static ssize_t pm_mng_profile_store(struct device *dev, if (strncmp("auto", buf, strlen("auto")) == 0) { /* Make sure we are in LOW PLL when changing modes */ if (hdev->pm_mng_profile == PM_MANUAL) { - atomic_set(&hdev->curr_pll_profile, PLL_HIGH); + hdev->curr_pll_profile = PLL_HIGH; hl_device_set_frequency(hdev, PLL_LOW); hdev->pm_mng_profile = PM_AUTO; } } else if (strncmp("manual", buf, strlen("manual")) == 0) { - /* Make sure we are in LOW PLL when changing modes */ if (hdev->pm_mng_profile == PM_AUTO) { - flush_delayed_work(&hdev->work_freq); + /* Must release the lock because the work thread also + * takes this lock. But before we release it, set + * the mode to manual so nothing will change if a user + * suddenly opens the device + */ hdev->pm_mng_profile = PM_MANUAL; + + mutex_unlock(&hdev->fpriv_list_lock); + + /* Flush the current work so we can return to the user + * knowing that he is the only one changing frequencies + */ + flush_delayed_work(&hdev->work_freq); + + return count; } } else { dev_err(hdev->dev, "value should be auto or manual\n"); count = -EINVAL; - goto unlock_mutex; } unlock_mutex: - mutex_unlock(&hdev->fd_open_cnt_lock); + mutex_unlock(&hdev->fpriv_list_lock); out: return count; } |