diff options
| author | Rob Herring <robh@kernel.org> | 2018-03-08 10:21:07 -0500 |
|---|---|---|
| committer | Rob Herring <robh@kernel.org> | 2018-03-08 10:21:07 -0500 |
| commit | c679fa6e3aaa5c58fc514b5b88cfa82774b8d390 (patch) | |
| tree | 0c10b339368bd1795152a66a4e245e6f654fb3ec /drivers | |
| parent | bdb7013df910681f84eff27b07791d4c160cb76f (diff) | |
| parent | 4fd98e374fd377ae0458a9dc44aa779cf9631ddd (diff) | |
Merge branch 'dtc-update' into dt/next
Diffstat (limited to 'drivers')
252 files changed, 2282 insertions, 1569 deletions
diff --git a/drivers/acpi/bus.c b/drivers/acpi/bus.c index 676c9788e1c8..0dad0bd9327b 100644 --- a/drivers/acpi/bus.c +++ b/drivers/acpi/bus.c | |||
| @@ -660,13 +660,15 @@ struct acpi_device *acpi_companion_match(const struct device *dev) | |||
| 660 | * acpi_of_match_device - Match device object using the "compatible" property. | 660 | * acpi_of_match_device - Match device object using the "compatible" property. |
| 661 | * @adev: ACPI device object to match. | 661 | * @adev: ACPI device object to match. |
| 662 | * @of_match_table: List of device IDs to match against. | 662 | * @of_match_table: List of device IDs to match against. |
| 663 | * @of_id: OF ID if matched | ||
| 663 | * | 664 | * |
| 664 | * If @dev has an ACPI companion which has ACPI_DT_NAMESPACE_HID in its list of | 665 | * If @dev has an ACPI companion which has ACPI_DT_NAMESPACE_HID in its list of |
| 665 | * identifiers and a _DSD object with the "compatible" property, use that | 666 | * identifiers and a _DSD object with the "compatible" property, use that |
| 666 | * property to match against the given list of identifiers. | 667 | * property to match against the given list of identifiers. |
| 667 | */ | 668 | */ |
| 668 | static bool acpi_of_match_device(struct acpi_device *adev, | 669 | static bool acpi_of_match_device(struct acpi_device *adev, |
| 669 | const struct of_device_id *of_match_table) | 670 | const struct of_device_id *of_match_table, |
| 671 | const struct of_device_id **of_id) | ||
| 670 | { | 672 | { |
| 671 | const union acpi_object *of_compatible, *obj; | 673 | const union acpi_object *of_compatible, *obj; |
| 672 | int i, nval; | 674 | int i, nval; |
| @@ -690,8 +692,11 @@ static bool acpi_of_match_device(struct acpi_device *adev, | |||
| 690 | const struct of_device_id *id; | 692 | const struct of_device_id *id; |
| 691 | 693 | ||
| 692 | for (id = of_match_table; id->compatible[0]; id++) | 694 | for (id = of_match_table; id->compatible[0]; id++) |
| 693 | if (!strcasecmp(obj->string.pointer, id->compatible)) | 695 | if (!strcasecmp(obj->string.pointer, id->compatible)) { |
| 696 | if (of_id) | ||
| 697 | *of_id = id; | ||
| 694 | return true; | 698 | return true; |
| 699 | } | ||
| 695 | } | 700 | } |
| 696 | 701 | ||
| 697 | return false; | 702 | return false; |
| @@ -762,10 +767,11 @@ static bool __acpi_match_device_cls(const struct acpi_device_id *id, | |||
| 762 | return true; | 767 | return true; |
| 763 | } | 768 | } |
| 764 | 769 | ||
| 765 | static const struct acpi_device_id *__acpi_match_device( | 770 | static bool __acpi_match_device(struct acpi_device *device, |
| 766 | struct acpi_device *device, | 771 | const struct acpi_device_id *acpi_ids, |
| 767 | const struct acpi_device_id *ids, | 772 | const struct of_device_id *of_ids, |
| 768 | const struct of_device_id *of_ids) | 773 | const struct acpi_device_id **acpi_id, |
| 774 | const struct of_device_id **of_id) | ||
| 769 | { | 775 | { |
| 770 | const struct acpi_device_id *id; | 776 | const struct acpi_device_id *id; |
| 771 | struct acpi_hardware_id *hwid; | 777 | struct acpi_hardware_id *hwid; |
| @@ -775,30 +781,32 @@ static const struct acpi_device_id *__acpi_match_device( | |||
| 775 | * driver for it. | 781 | * driver for it. |
| 776 | */ | 782 | */ |
| 777 | if (!device || !device->status.present) | 783 | if (!device || !device->status.present) |
| 778 | return NULL; | 784 | return false; |
| 779 | 785 | ||
| 780 | list_for_each_entry(hwid, &device->pnp.ids, list) { | 786 | list_for_each_entry(hwid, &device->pnp.ids, list) { |
| 781 | /* First, check the ACPI/PNP IDs provided by the caller. */ | 787 | /* First, check the ACPI/PNP IDs provided by the caller. */ |
| 782 | for (id = ids; id->id[0] || id->cls; id++) { | 788 | if (acpi_ids) { |
| 783 | if (id->id[0] && !strcmp((char *) id->id, hwid->id)) | 789 | for (id = acpi_ids; id->id[0] || id->cls; id++) { |
| 784 | return id; | 790 | if (id->id[0] && !strcmp((char *)id->id, hwid->id)) |
| 785 | else if (id->cls && __acpi_match_device_cls(id, hwid)) | 791 | goto out_acpi_match; |
| 786 | return id; | 792 | if (id->cls && __acpi_match_device_cls(id, hwid)) |
| 793 | goto out_acpi_match; | ||
| 794 | } | ||
| 787 | } | 795 | } |
| 788 | 796 | ||
| 789 | /* | 797 | /* |
| 790 | * Next, check ACPI_DT_NAMESPACE_HID and try to match the | 798 | * Next, check ACPI_DT_NAMESPACE_HID and try to match the |
| 791 | * "compatible" property if found. | 799 | * "compatible" property if found. |
| 792 | * | ||
| 793 | * The id returned by the below is not valid, but the only | ||
| 794 | * caller passing non-NULL of_ids here is only interested in | ||
| 795 | * whether or not the return value is NULL. | ||
| 796 | */ | 800 | */ |
| 797 | if (!strcmp(ACPI_DT_NAMESPACE_HID, hwid->id) | 801 | if (!strcmp(ACPI_DT_NAMESPACE_HID, hwid->id)) |
| 798 | && acpi_of_match_device(device, of_ids)) | 802 | return acpi_of_match_device(device, of_ids, of_id); |
| 799 | return id; | ||
| 800 | } | 803 | } |
| 801 | return NULL; | 804 | return false; |
| 805 | |||
| 806 | out_acpi_match: | ||
| 807 | if (acpi_id) | ||
| 808 | *acpi_id = id; | ||
| 809 | return true; | ||
| 802 | } | 810 | } |
| 803 | 811 | ||
| 804 | /** | 812 | /** |
| @@ -815,32 +823,29 @@ static const struct acpi_device_id *__acpi_match_device( | |||
| 815 | const struct acpi_device_id *acpi_match_device(const struct acpi_device_id *ids, | 823 | const struct acpi_device_id *acpi_match_device(const struct acpi_device_id *ids, |
| 816 | const struct device *dev) | 824 | const struct device *dev) |
| 817 | { | 825 | { |
| 818 | return __acpi_match_device(acpi_companion_match(dev), ids, NULL); | 826 | const struct acpi_device_id *id = NULL; |
| 827 | |||
| 828 | __acpi_match_device(acpi_companion_match(dev), ids, NULL, &id, NULL); | ||
| 829 | return id; | ||
| 819 | } | 830 | } |
| 820 | EXPORT_SYMBOL_GPL(acpi_match_device); | 831 | EXPORT_SYMBOL_GPL(acpi_match_device); |
| 821 | 832 | ||
| 822 | void *acpi_get_match_data(const struct device *dev) | 833 | const void *acpi_device_get_match_data(const struct device *dev) |
| 823 | { | 834 | { |
| 824 | const struct acpi_device_id *match; | 835 | const struct acpi_device_id *match; |
| 825 | 836 | ||
| 826 | if (!dev->driver) | ||
| 827 | return NULL; | ||
| 828 | |||
| 829 | if (!dev->driver->acpi_match_table) | ||
| 830 | return NULL; | ||
| 831 | |||
| 832 | match = acpi_match_device(dev->driver->acpi_match_table, dev); | 837 | match = acpi_match_device(dev->driver->acpi_match_table, dev); |
| 833 | if (!match) | 838 | if (!match) |
| 834 | return NULL; | 839 | return NULL; |
| 835 | 840 | ||
| 836 | return (void *)match->driver_data; | 841 | return (const void *)match->driver_data; |
| 837 | } | 842 | } |
| 838 | EXPORT_SYMBOL_GPL(acpi_get_match_data); | 843 | EXPORT_SYMBOL_GPL(acpi_device_get_match_data); |
| 839 | 844 | ||
| 840 | int acpi_match_device_ids(struct acpi_device *device, | 845 | int acpi_match_device_ids(struct acpi_device *device, |
| 841 | const struct acpi_device_id *ids) | 846 | const struct acpi_device_id *ids) |
| 842 | { | 847 | { |
| 843 | return __acpi_match_device(device, ids, NULL) ? 0 : -ENOENT; | 848 | return __acpi_match_device(device, ids, NULL, NULL, NULL) ? 0 : -ENOENT; |
| 844 | } | 849 | } |
| 845 | EXPORT_SYMBOL(acpi_match_device_ids); | 850 | EXPORT_SYMBOL(acpi_match_device_ids); |
| 846 | 851 | ||
| @@ -849,10 +854,12 @@ bool acpi_driver_match_device(struct device *dev, | |||
| 849 | { | 854 | { |
| 850 | if (!drv->acpi_match_table) | 855 | if (!drv->acpi_match_table) |
| 851 | return acpi_of_match_device(ACPI_COMPANION(dev), | 856 | return acpi_of_match_device(ACPI_COMPANION(dev), |
| 852 | drv->of_match_table); | 857 | drv->of_match_table, |
| 858 | NULL); | ||
| 853 | 859 | ||
| 854 | return !!__acpi_match_device(acpi_companion_match(dev), | 860 | return __acpi_match_device(acpi_companion_match(dev), |
| 855 | drv->acpi_match_table, drv->of_match_table); | 861 | drv->acpi_match_table, drv->of_match_table, |
| 862 | NULL, NULL); | ||
| 856 | } | 863 | } |
| 857 | EXPORT_SYMBOL_GPL(acpi_driver_match_device); | 864 | EXPORT_SYMBOL_GPL(acpi_driver_match_device); |
| 858 | 865 | ||
diff --git a/drivers/acpi/ec.c b/drivers/acpi/ec.c index d9f38c645e4a..30a572956557 100644 --- a/drivers/acpi/ec.c +++ b/drivers/acpi/ec.c | |||
| @@ -1927,6 +1927,9 @@ static int acpi_ec_suspend_noirq(struct device *dev) | |||
| 1927 | ec->reference_count >= 1) | 1927 | ec->reference_count >= 1) |
| 1928 | acpi_set_gpe(NULL, ec->gpe, ACPI_GPE_DISABLE); | 1928 | acpi_set_gpe(NULL, ec->gpe, ACPI_GPE_DISABLE); |
| 1929 | 1929 | ||
| 1930 | if (acpi_sleep_no_ec_events()) | ||
| 1931 | acpi_ec_enter_noirq(ec); | ||
| 1932 | |||
| 1930 | return 0; | 1933 | return 0; |
| 1931 | } | 1934 | } |
| 1932 | 1935 | ||
| @@ -1934,6 +1937,9 @@ static int acpi_ec_resume_noirq(struct device *dev) | |||
| 1934 | { | 1937 | { |
| 1935 | struct acpi_ec *ec = acpi_driver_data(to_acpi_device(dev)); | 1938 | struct acpi_ec *ec = acpi_driver_data(to_acpi_device(dev)); |
| 1936 | 1939 | ||
| 1940 | if (acpi_sleep_no_ec_events()) | ||
| 1941 | acpi_ec_leave_noirq(ec); | ||
| 1942 | |||
| 1937 | if (ec_no_wakeup && test_bit(EC_FLAGS_STARTED, &ec->flags) && | 1943 | if (ec_no_wakeup && test_bit(EC_FLAGS_STARTED, &ec->flags) && |
| 1938 | ec->reference_count >= 1) | 1944 | ec->reference_count >= 1) |
| 1939 | acpi_set_gpe(NULL, ec->gpe, ACPI_GPE_ENABLE); | 1945 | acpi_set_gpe(NULL, ec->gpe, ACPI_GPE_ENABLE); |
diff --git a/drivers/acpi/property.c b/drivers/acpi/property.c index 466d1503aba0..5815356ea6ad 100644 --- a/drivers/acpi/property.c +++ b/drivers/acpi/property.c | |||
| @@ -1271,11 +1271,11 @@ static int acpi_fwnode_graph_parse_endpoint(const struct fwnode_handle *fwnode, | |||
| 1271 | return 0; | 1271 | return 0; |
| 1272 | } | 1272 | } |
| 1273 | 1273 | ||
| 1274 | static void * | 1274 | static const void * |
| 1275 | acpi_fwnode_device_get_match_data(const struct fwnode_handle *fwnode, | 1275 | acpi_fwnode_device_get_match_data(const struct fwnode_handle *fwnode, |
| 1276 | const struct device *dev) | 1276 | const struct device *dev) |
| 1277 | { | 1277 | { |
| 1278 | return acpi_get_match_data(dev); | 1278 | return acpi_device_get_match_data(dev); |
| 1279 | } | 1279 | } |
| 1280 | 1280 | ||
| 1281 | #define DECLARE_ACPI_FWNODE_OPS(ops) \ | 1281 | #define DECLARE_ACPI_FWNODE_OPS(ops) \ |
diff --git a/drivers/acpi/spcr.c b/drivers/acpi/spcr.c index 89e97d21a89c..9d52743080a4 100644 --- a/drivers/acpi/spcr.c +++ b/drivers/acpi/spcr.c | |||
| @@ -115,6 +115,7 @@ int __init acpi_parse_spcr(bool enable_earlycon, bool enable_console) | |||
| 115 | table->serial_port.access_width))) { | 115 | table->serial_port.access_width))) { |
| 116 | default: | 116 | default: |
| 117 | pr_err("Unexpected SPCR Access Width. Defaulting to byte size\n"); | 117 | pr_err("Unexpected SPCR Access Width. Defaulting to byte size\n"); |
| 118 | /* fall through */ | ||
| 118 | case 8: | 119 | case 8: |
| 119 | iotype = "mmio"; | 120 | iotype = "mmio"; |
| 120 | break; | 121 | break; |
diff --git a/drivers/android/binder.c b/drivers/android/binder.c index 15e3d3c2260d..764b63a5aade 100644 --- a/drivers/android/binder.c +++ b/drivers/android/binder.c | |||
| @@ -1991,8 +1991,14 @@ static void binder_send_failed_reply(struct binder_transaction *t, | |||
| 1991 | &target_thread->reply_error.work); | 1991 | &target_thread->reply_error.work); |
| 1992 | wake_up_interruptible(&target_thread->wait); | 1992 | wake_up_interruptible(&target_thread->wait); |
| 1993 | } else { | 1993 | } else { |
| 1994 | WARN(1, "Unexpected reply error: %u\n", | 1994 | /* |
| 1995 | target_thread->reply_error.cmd); | 1995 | * Cannot get here for normal operation, but |
| 1996 | * we can if multiple synchronous transactions | ||
| 1997 | * are sent without blocking for responses. | ||
| 1998 | * Just ignore the 2nd error in this case. | ||
| 1999 | */ | ||
| 2000 | pr_warn("Unexpected reply error: %u\n", | ||
| 2001 | target_thread->reply_error.cmd); | ||
| 1996 | } | 2002 | } |
| 1997 | binder_inner_proc_unlock(target_thread->proc); | 2003 | binder_inner_proc_unlock(target_thread->proc); |
| 1998 | binder_thread_dec_tmpref(target_thread); | 2004 | binder_thread_dec_tmpref(target_thread); |
| @@ -2193,7 +2199,7 @@ static void binder_transaction_buffer_release(struct binder_proc *proc, | |||
| 2193 | int debug_id = buffer->debug_id; | 2199 | int debug_id = buffer->debug_id; |
| 2194 | 2200 | ||
| 2195 | binder_debug(BINDER_DEBUG_TRANSACTION, | 2201 | binder_debug(BINDER_DEBUG_TRANSACTION, |
| 2196 | "%d buffer release %d, size %zd-%zd, failed at %p\n", | 2202 | "%d buffer release %d, size %zd-%zd, failed at %pK\n", |
| 2197 | proc->pid, buffer->debug_id, | 2203 | proc->pid, buffer->debug_id, |
| 2198 | buffer->data_size, buffer->offsets_size, failed_at); | 2204 | buffer->data_size, buffer->offsets_size, failed_at); |
| 2199 | 2205 | ||
| @@ -3705,7 +3711,7 @@ static int binder_thread_write(struct binder_proc *proc, | |||
| 3705 | } | 3711 | } |
| 3706 | } | 3712 | } |
| 3707 | binder_debug(BINDER_DEBUG_DEAD_BINDER, | 3713 | binder_debug(BINDER_DEBUG_DEAD_BINDER, |
| 3708 | "%d:%d BC_DEAD_BINDER_DONE %016llx found %p\n", | 3714 | "%d:%d BC_DEAD_BINDER_DONE %016llx found %pK\n", |
| 3709 | proc->pid, thread->pid, (u64)cookie, | 3715 | proc->pid, thread->pid, (u64)cookie, |
| 3710 | death); | 3716 | death); |
| 3711 | if (death == NULL) { | 3717 | if (death == NULL) { |
| @@ -4376,6 +4382,15 @@ static int binder_thread_release(struct binder_proc *proc, | |||
| 4376 | 4382 | ||
| 4377 | binder_inner_proc_unlock(thread->proc); | 4383 | binder_inner_proc_unlock(thread->proc); |
| 4378 | 4384 | ||
| 4385 | /* | ||
| 4386 | * This is needed to avoid races between wake_up_poll() above and | ||
| 4387 | * and ep_remove_waitqueue() called for other reasons (eg the epoll file | ||
| 4388 | * descriptor being closed); ep_remove_waitqueue() holds an RCU read | ||
| 4389 | * lock, so we can be sure it's done after calling synchronize_rcu(). | ||
| 4390 | */ | ||
| 4391 | if (thread->looper & BINDER_LOOPER_STATE_POLL) | ||
| 4392 | synchronize_rcu(); | ||
| 4393 | |||
| 4379 | if (send_reply) | 4394 | if (send_reply) |
| 4380 | binder_send_failed_reply(send_reply, BR_DEAD_REPLY); | 4395 | binder_send_failed_reply(send_reply, BR_DEAD_REPLY); |
| 4381 | binder_release_work(proc, &thread->todo); | 4396 | binder_release_work(proc, &thread->todo); |
| @@ -4391,6 +4406,8 @@ static __poll_t binder_poll(struct file *filp, | |||
| 4391 | bool wait_for_proc_work; | 4406 | bool wait_for_proc_work; |
| 4392 | 4407 | ||
| 4393 | thread = binder_get_thread(proc); | 4408 | thread = binder_get_thread(proc); |
| 4409 | if (!thread) | ||
| 4410 | return POLLERR; | ||
| 4394 | 4411 | ||
| 4395 | binder_inner_proc_lock(thread->proc); | 4412 | binder_inner_proc_lock(thread->proc); |
| 4396 | thread->looper |= BINDER_LOOPER_STATE_POLL; | 4413 | thread->looper |= BINDER_LOOPER_STATE_POLL; |
| @@ -5034,7 +5051,7 @@ static void print_binder_transaction_ilocked(struct seq_file *m, | |||
| 5034 | spin_lock(&t->lock); | 5051 | spin_lock(&t->lock); |
| 5035 | to_proc = t->to_proc; | 5052 | to_proc = t->to_proc; |
| 5036 | seq_printf(m, | 5053 | seq_printf(m, |
| 5037 | "%s %d: %p from %d:%d to %d:%d code %x flags %x pri %ld r%d", | 5054 | "%s %d: %pK from %d:%d to %d:%d code %x flags %x pri %ld r%d", |
| 5038 | prefix, t->debug_id, t, | 5055 | prefix, t->debug_id, t, |
| 5039 | t->from ? t->from->proc->pid : 0, | 5056 | t->from ? t->from->proc->pid : 0, |
| 5040 | t->from ? t->from->pid : 0, | 5057 | t->from ? t->from->pid : 0, |
| @@ -5058,7 +5075,7 @@ static void print_binder_transaction_ilocked(struct seq_file *m, | |||
| 5058 | } | 5075 | } |
| 5059 | if (buffer->target_node) | 5076 | if (buffer->target_node) |
| 5060 | seq_printf(m, " node %d", buffer->target_node->debug_id); | 5077 | seq_printf(m, " node %d", buffer->target_node->debug_id); |
| 5061 | seq_printf(m, " size %zd:%zd data %p\n", | 5078 | seq_printf(m, " size %zd:%zd data %pK\n", |
| 5062 | buffer->data_size, buffer->offsets_size, | 5079 | buffer->data_size, buffer->offsets_size, |
| 5063 | buffer->data); | 5080 | buffer->data); |
| 5064 | } | 5081 | } |
diff --git a/drivers/base/core.c b/drivers/base/core.c index b2261f92f2f1..5847364f25d9 100644 --- a/drivers/base/core.c +++ b/drivers/base/core.c | |||
| @@ -310,6 +310,9 @@ static void __device_link_del(struct device_link *link) | |||
| 310 | dev_info(link->consumer, "Dropping the link to %s\n", | 310 | dev_info(link->consumer, "Dropping the link to %s\n", |
| 311 | dev_name(link->supplier)); | 311 | dev_name(link->supplier)); |
| 312 | 312 | ||
| 313 | if (link->flags & DL_FLAG_PM_RUNTIME) | ||
| 314 | pm_runtime_drop_link(link->consumer); | ||
| 315 | |||
| 313 | list_del(&link->s_node); | 316 | list_del(&link->s_node); |
| 314 | list_del(&link->c_node); | 317 | list_del(&link->c_node); |
| 315 | device_link_free(link); | 318 | device_link_free(link); |
diff --git a/drivers/base/power/wakeirq.c b/drivers/base/power/wakeirq.c index a8ac86e4d79e..6637fc319269 100644 --- a/drivers/base/power/wakeirq.c +++ b/drivers/base/power/wakeirq.c | |||
| @@ -321,7 +321,8 @@ void dev_pm_arm_wake_irq(struct wake_irq *wirq) | |||
| 321 | return; | 321 | return; |
| 322 | 322 | ||
| 323 | if (device_may_wakeup(wirq->dev)) { | 323 | if (device_may_wakeup(wirq->dev)) { |
| 324 | if (wirq->status & WAKE_IRQ_DEDICATED_ALLOCATED) | 324 | if (wirq->status & WAKE_IRQ_DEDICATED_ALLOCATED && |
| 325 | !pm_runtime_status_suspended(wirq->dev)) | ||
| 325 | enable_irq(wirq->irq); | 326 | enable_irq(wirq->irq); |
| 326 | 327 | ||
| 327 | enable_irq_wake(wirq->irq); | 328 | enable_irq_wake(wirq->irq); |
| @@ -343,7 +344,8 @@ void dev_pm_disarm_wake_irq(struct wake_irq *wirq) | |||
| 343 | if (device_may_wakeup(wirq->dev)) { | 344 | if (device_may_wakeup(wirq->dev)) { |
| 344 | disable_irq_wake(wirq->irq); | 345 | disable_irq_wake(wirq->irq); |
| 345 | 346 | ||
| 346 | if (wirq->status & WAKE_IRQ_DEDICATED_ALLOCATED) | 347 | if (wirq->status & WAKE_IRQ_DEDICATED_ALLOCATED && |
| 348 | !pm_runtime_status_suspended(wirq->dev)) | ||
| 347 | disable_irq_nosync(wirq->irq); | 349 | disable_irq_nosync(wirq->irq); |
| 348 | } | 350 | } |
| 349 | } | 351 | } |
diff --git a/drivers/base/property.c b/drivers/base/property.c index 302236281d83..8f205f6461ed 100644 --- a/drivers/base/property.c +++ b/drivers/base/property.c | |||
| @@ -1410,9 +1410,8 @@ int fwnode_graph_parse_endpoint(const struct fwnode_handle *fwnode, | |||
| 1410 | } | 1410 | } |
| 1411 | EXPORT_SYMBOL(fwnode_graph_parse_endpoint); | 1411 | EXPORT_SYMBOL(fwnode_graph_parse_endpoint); |
| 1412 | 1412 | ||
| 1413 | void *device_get_match_data(struct device *dev) | 1413 | const void *device_get_match_data(struct device *dev) |
| 1414 | { | 1414 | { |
| 1415 | return fwnode_call_ptr_op(dev_fwnode(dev), device_get_match_data, | 1415 | return fwnode_call_ptr_op(dev_fwnode(dev), device_get_match_data, dev); |
| 1416 | dev); | ||
| 1417 | } | 1416 | } |
| 1418 | EXPORT_SYMBOL_GPL(device_get_match_data); | 1417 | EXPORT_SYMBOL_GPL(device_get_match_data); |
diff --git a/drivers/char/hw_random/via-rng.c b/drivers/char/hw_random/via-rng.c index d1f5bb534e0e..6e9df558325b 100644 --- a/drivers/char/hw_random/via-rng.c +++ b/drivers/char/hw_random/via-rng.c | |||
| @@ -162,7 +162,7 @@ static int via_rng_init(struct hwrng *rng) | |||
| 162 | /* Enable secondary noise source on CPUs where it is present. */ | 162 | /* Enable secondary noise source on CPUs where it is present. */ |
| 163 | 163 | ||
| 164 | /* Nehemiah stepping 8 and higher */ | 164 | /* Nehemiah stepping 8 and higher */ |
| 165 | if ((c->x86_model == 9) && (c->x86_mask > 7)) | 165 | if ((c->x86_model == 9) && (c->x86_stepping > 7)) |
| 166 | lo |= VIA_NOISESRC2; | 166 | lo |= VIA_NOISESRC2; |
| 167 | 167 | ||
| 168 | /* Esther */ | 168 | /* Esther */ |
diff --git a/drivers/clocksource/mips-gic-timer.c b/drivers/clocksource/mips-gic-timer.c index a04808a21d4e..65e18c86d9b9 100644 --- a/drivers/clocksource/mips-gic-timer.c +++ b/drivers/clocksource/mips-gic-timer.c | |||
| @@ -205,12 +205,12 @@ static int __init gic_clocksource_of_init(struct device_node *node) | |||
| 205 | } else if (of_property_read_u32(node, "clock-frequency", | 205 | } else if (of_property_read_u32(node, "clock-frequency", |
| 206 | &gic_frequency)) { | 206 | &gic_frequency)) { |
| 207 | pr_err("GIC frequency not specified.\n"); | 207 | pr_err("GIC frequency not specified.\n"); |
| 208 | return -EINVAL;; | 208 | return -EINVAL; |
| 209 | } | 209 | } |
| 210 | gic_timer_irq = irq_of_parse_and_map(node, 0); | 210 | gic_timer_irq = irq_of_parse_and_map(node, 0); |
| 211 | if (!gic_timer_irq) { | 211 | if (!gic_timer_irq) { |
| 212 | pr_err("GIC timer IRQ not specified.\n"); | 212 | pr_err("GIC timer IRQ not specified.\n"); |
| 213 | return -EINVAL;; | 213 | return -EINVAL; |
| 214 | } | 214 | } |
| 215 | 215 | ||
| 216 | ret = __gic_clocksource_init(); | 216 | ret = __gic_clocksource_init(); |
diff --git a/drivers/clocksource/timer-sun5i.c b/drivers/clocksource/timer-sun5i.c index 2a3fe83ec337..3b56ea3f52af 100644 --- a/drivers/clocksource/timer-sun5i.c +++ b/drivers/clocksource/timer-sun5i.c | |||
| @@ -334,7 +334,7 @@ static int __init sun5i_timer_init(struct device_node *node) | |||
| 334 | timer_base = of_io_request_and_map(node, 0, of_node_full_name(node)); | 334 | timer_base = of_io_request_and_map(node, 0, of_node_full_name(node)); |
| 335 | if (IS_ERR(timer_base)) { | 335 | if (IS_ERR(timer_base)) { |
| 336 | pr_err("Can't map registers\n"); | 336 | pr_err("Can't map registers\n"); |
| 337 | return PTR_ERR(timer_base);; | 337 | return PTR_ERR(timer_base); |
| 338 | } | 338 | } |
| 339 | 339 | ||
| 340 | irq = irq_of_parse_and_map(node, 0); | 340 | irq = irq_of_parse_and_map(node, 0); |
diff --git a/drivers/cpufreq/acpi-cpufreq.c b/drivers/cpufreq/acpi-cpufreq.c index 3a2ca0f79daf..d0c34df0529c 100644 --- a/drivers/cpufreq/acpi-cpufreq.c +++ b/drivers/cpufreq/acpi-cpufreq.c | |||
| @@ -629,7 +629,7 @@ static int acpi_cpufreq_blacklist(struct cpuinfo_x86 *c) | |||
| 629 | if (c->x86_vendor == X86_VENDOR_INTEL) { | 629 | if (c->x86_vendor == X86_VENDOR_INTEL) { |
| 630 | if ((c->x86 == 15) && | 630 | if ((c->x86 == 15) && |
| 631 | (c->x86_model == 6) && | 631 | (c->x86_model == 6) && |
| 632 | (c->x86_mask == 8)) { | 632 | (c->x86_stepping == 8)) { |
| 633 | pr_info("Intel(R) Xeon(R) 7100 Errata AL30, processors may lock up on frequency changes: disabling acpi-cpufreq\n"); | 633 | pr_info("Intel(R) Xeon(R) 7100 Errata AL30, processors may lock up on frequency changes: disabling acpi-cpufreq\n"); |
| 634 | return -ENODEV; | 634 | return -ENODEV; |
| 635 | } | 635 | } |
diff --git a/drivers/cpufreq/longhaul.c b/drivers/cpufreq/longhaul.c index 942632a27b50..f730b6528c18 100644 --- a/drivers/cpufreq/longhaul.c +++ b/drivers/cpufreq/longhaul.c | |||
| @@ -775,7 +775,7 @@ static int longhaul_cpu_init(struct cpufreq_policy *policy) | |||
| 775 | break; | 775 | break; |
| 776 | 776 | ||
| 777 | case 7: | 777 | case 7: |
| 778 | switch (c->x86_mask) { | 778 | switch (c->x86_stepping) { |
| 779 | case 0: | 779 | case 0: |
| 780 | longhaul_version = TYPE_LONGHAUL_V1; | 780 | longhaul_version = TYPE_LONGHAUL_V1; |
| 781 | cpu_model = CPU_SAMUEL2; | 781 | cpu_model = CPU_SAMUEL2; |
| @@ -787,7 +787,7 @@ static int longhaul_cpu_init(struct cpufreq_policy *policy) | |||
| 787 | break; | 787 | break; |
| 788 | case 1 ... 15: | 788 | case 1 ... 15: |
| 789 | longhaul_version = TYPE_LONGHAUL_V2; | 789 | longhaul_version = TYPE_LONGHAUL_V2; |
| 790 | if (c->x86_mask < 8) { | 790 | if (c->x86_stepping < 8) { |
| 791 | cpu_model = CPU_SAMUEL2; | 791 | cpu_model = CPU_SAMUEL2; |
| 792 | cpuname = "C3 'Samuel 2' [C5B]"; | 792 | cpuname = "C3 'Samuel 2' [C5B]"; |
| 793 | } else { | 793 | } else { |
| @@ -814,7 +814,7 @@ static int longhaul_cpu_init(struct cpufreq_policy *policy) | |||
| 814 | numscales = 32; | 814 | numscales = 32; |
| 815 | memcpy(mults, nehemiah_mults, sizeof(nehemiah_mults)); | 815 | memcpy(mults, nehemiah_mults, sizeof(nehemiah_mults)); |
| 816 | memcpy(eblcr, nehemiah_eblcr, sizeof(nehemiah_eblcr)); | 816 | memcpy(eblcr, nehemiah_eblcr, sizeof(nehemiah_eblcr)); |
| 817 | switch (c->x86_mask) { | 817 | switch (c->x86_stepping) { |
| 818 | case 0 ... 1: | 818 | case 0 ... 1: |
| 819 | cpu_model = CPU_NEHEMIAH; | 819 | cpu_model = CPU_NEHEMIAH; |
| 820 | cpuname = "C3 'Nehemiah A' [C5XLOE]"; | 820 | cpuname = "C3 'Nehemiah A' [C5XLOE]"; |
diff --git a/drivers/cpufreq/p4-clockmod.c b/drivers/cpufreq/p4-clockmod.c index fd77812313f3..a25741b1281b 100644 --- a/drivers/cpufreq/p4-clockmod.c +++ b/drivers/cpufreq/p4-clockmod.c | |||
| @@ -168,7 +168,7 @@ static int cpufreq_p4_cpu_init(struct cpufreq_policy *policy) | |||
| 168 | #endif | 168 | #endif |
| 169 | 169 | ||
| 170 | /* Errata workaround */ | 170 | /* Errata workaround */ |
| 171 | cpuid = (c->x86 << 8) | (c->x86_model << 4) | c->x86_mask; | 171 | cpuid = (c->x86 << 8) | (c->x86_model << 4) | c->x86_stepping; |
| 172 | switch (cpuid) { | 172 | switch (cpuid) { |
| 173 | case 0x0f07: | 173 | case 0x0f07: |
| 174 | case 0x0f0a: | 174 | case 0x0f0a: |
diff --git a/drivers/cpufreq/powernow-k7.c b/drivers/cpufreq/powernow-k7.c index 80ac313e6c59..302e9ce793a0 100644 --- a/drivers/cpufreq/powernow-k7.c +++ b/drivers/cpufreq/powernow-k7.c | |||
| @@ -131,7 +131,7 @@ static int check_powernow(void) | |||
| 131 | return 0; | 131 | return 0; |
| 132 | } | 132 | } |
| 133 | 133 | ||
| 134 | if ((c->x86_model == 6) && (c->x86_mask == 0)) { | 134 | if ((c->x86_model == 6) && (c->x86_stepping == 0)) { |
| 135 | pr_info("K7 660[A0] core detected, enabling errata workarounds\n"); | 135 | pr_info("K7 660[A0] core detected, enabling errata workarounds\n"); |
| 136 | have_a0 = 1; | 136 | have_a0 = 1; |
| 137 | } | 137 | } |
diff --git a/drivers/cpufreq/speedstep-centrino.c b/drivers/cpufreq/speedstep-centrino.c index 41bc5397f4bb..4fa5adf16c70 100644 --- a/drivers/cpufreq/speedstep-centrino.c +++ b/drivers/cpufreq/speedstep-centrino.c | |||
| @@ -37,7 +37,7 @@ struct cpu_id | |||
| 37 | { | 37 | { |
| 38 | __u8 x86; /* CPU family */ | 38 | __u8 x86; /* CPU family */ |
| 39 | __u8 x86_model; /* model */ | 39 | __u8 x86_model; /* model */ |
| 40 | __u8 x86_mask; /* stepping */ | 40 | __u8 x86_stepping; /* stepping */ |
| 41 | }; | 41 | }; |
| 42 | 42 | ||
| 43 | enum { | 43 | enum { |
| @@ -277,7 +277,7 @@ static int centrino_verify_cpu_id(const struct cpuinfo_x86 *c, | |||
| 277 | { | 277 | { |
| 278 | if ((c->x86 == x->x86) && | 278 | if ((c->x86 == x->x86) && |
| 279 | (c->x86_model == x->x86_model) && | 279 | (c->x86_model == x->x86_model) && |
| 280 | (c->x86_mask == x->x86_mask)) | 280 | (c->x86_stepping == x->x86_stepping)) |
| 281 | return 1; | 281 | return 1; |
| 282 | return 0; | 282 | return 0; |
| 283 | } | 283 | } |
diff --git a/drivers/cpufreq/speedstep-lib.c b/drivers/cpufreq/speedstep-lib.c index 8085ec9000d1..e3a9962ee410 100644 --- a/drivers/cpufreq/speedstep-lib.c +++ b/drivers/cpufreq/speedstep-lib.c | |||
| @@ -272,9 +272,9 @@ unsigned int speedstep_detect_processor(void) | |||
| 272 | ebx = cpuid_ebx(0x00000001); | 272 | ebx = cpuid_ebx(0x00000001); |
| 273 | ebx &= 0x000000FF; | 273 | ebx &= 0x000000FF; |
| 274 | 274 | ||
| 275 | pr_debug("ebx value is %x, x86_mask is %x\n", ebx, c->x86_mask); | 275 | pr_debug("ebx value is %x, x86_stepping is %x\n", ebx, c->x86_stepping); |
| 276 | 276 | ||
| 277 | switch (c->x86_mask) { | 277 | switch (c->x86_stepping) { |
| 278 | case 4: | 278 | case 4: |
| 279 | /* | 279 | /* |
| 280 | * B-stepping [M-P4-M] | 280 | * B-stepping [M-P4-M] |
| @@ -361,7 +361,7 @@ unsigned int speedstep_detect_processor(void) | |||
| 361 | msr_lo, msr_hi); | 361 | msr_lo, msr_hi); |
| 362 | if ((msr_hi & (1<<18)) && | 362 | if ((msr_hi & (1<<18)) && |
| 363 | (relaxed_check ? 1 : (msr_hi & (3<<24)))) { | 363 | (relaxed_check ? 1 : (msr_hi & (3<<24)))) { |
| 364 | if (c->x86_mask == 0x01) { | 364 | if (c->x86_stepping == 0x01) { |
| 365 | pr_debug("early PIII version\n"); | 365 | pr_debug("early PIII version\n"); |
| 366 | return SPEEDSTEP_CPU_PIII_C_EARLY; | 366 | return SPEEDSTEP_CPU_PIII_C_EARLY; |
| 367 | } else | 367 | } else |
diff --git a/drivers/crypto/caam/ctrl.c b/drivers/crypto/caam/ctrl.c index 75d280cb2dc0..e843cf410373 100644 --- a/drivers/crypto/caam/ctrl.c +++ b/drivers/crypto/caam/ctrl.c | |||
| @@ -228,12 +228,16 @@ static int instantiate_rng(struct device *ctrldev, int state_handle_mask, | |||
| 228 | * without any error (HW optimizations for later | 228 | * without any error (HW optimizations for later |
| 229 | * CAAM eras), then try again. | 229 | * CAAM eras), then try again. |
| 230 | */ | 230 | */ |
| 231 | if (ret) | ||
| 232 | break; | ||
| 233 | |||
| 231 | rdsta_val = rd_reg32(&ctrl->r4tst[0].rdsta) & RDSTA_IFMASK; | 234 | rdsta_val = rd_reg32(&ctrl->r4tst[0].rdsta) & RDSTA_IFMASK; |
| 232 | if ((status && status != JRSTA_SSRC_JUMP_HALT_CC) || | 235 | if ((status && status != JRSTA_SSRC_JUMP_HALT_CC) || |
| 233 | !(rdsta_val & (1 << sh_idx))) | 236 | !(rdsta_val & (1 << sh_idx))) { |
| 234 | ret = -EAGAIN; | 237 | ret = -EAGAIN; |
| 235 | if (ret) | ||
| 236 | break; | 238 | break; |
| 239 | } | ||
| 240 | |||
| 237 | dev_info(ctrldev, "Instantiated RNG4 SH%d\n", sh_idx); | 241 | dev_info(ctrldev, "Instantiated RNG4 SH%d\n", sh_idx); |
| 238 | /* Clear the contents before recreating the descriptor */ | 242 | /* Clear the contents before recreating the descriptor */ |
| 239 | memset(desc, 0x00, CAAM_CMD_SZ * 7); | 243 | memset(desc, 0x00, CAAM_CMD_SZ * 7); |
diff --git a/drivers/crypto/padlock-aes.c b/drivers/crypto/padlock-aes.c index 4b6642a25df5..1c6cbda56afe 100644 --- a/drivers/crypto/padlock-aes.c +++ b/drivers/crypto/padlock-aes.c | |||
| @@ -512,7 +512,7 @@ static int __init padlock_init(void) | |||
| 512 | 512 | ||
| 513 | printk(KERN_NOTICE PFX "Using VIA PadLock ACE for AES algorithm.\n"); | 513 | printk(KERN_NOTICE PFX "Using VIA PadLock ACE for AES algorithm.\n"); |
| 514 | 514 | ||
| 515 | if (c->x86 == 6 && c->x86_model == 15 && c->x86_mask == 2) { | 515 | if (c->x86 == 6 && c->x86_model == 15 && c->x86_stepping == 2) { |
| 516 | ecb_fetch_blocks = MAX_ECB_FETCH_BLOCKS; | 516 | ecb_fetch_blocks = MAX_ECB_FETCH_BLOCKS; |
| 517 | cbc_fetch_blocks = MAX_CBC_FETCH_BLOCKS; | 517 | cbc_fetch_blocks = MAX_CBC_FETCH_BLOCKS; |
| 518 | printk(KERN_NOTICE PFX "VIA Nano stepping 2 detected: enabling workaround.\n"); | 518 | printk(KERN_NOTICE PFX "VIA Nano stepping 2 detected: enabling workaround.\n"); |
diff --git a/drivers/crypto/s5p-sss.c b/drivers/crypto/s5p-sss.c index 188f44b7eb27..5d64c08b7f47 100644 --- a/drivers/crypto/s5p-sss.c +++ b/drivers/crypto/s5p-sss.c | |||
| @@ -1922,15 +1922,21 @@ static void s5p_aes_crypt_start(struct s5p_aes_dev *dev, unsigned long mode) | |||
| 1922 | uint32_t aes_control; | 1922 | uint32_t aes_control; |
| 1923 | unsigned long flags; | 1923 | unsigned long flags; |
| 1924 | int err; | 1924 | int err; |
| 1925 | u8 *iv; | ||
| 1925 | 1926 | ||
| 1926 | aes_control = SSS_AES_KEY_CHANGE_MODE; | 1927 | aes_control = SSS_AES_KEY_CHANGE_MODE; |
| 1927 | if (mode & FLAGS_AES_DECRYPT) | 1928 | if (mode & FLAGS_AES_DECRYPT) |
| 1928 | aes_control |= SSS_AES_MODE_DECRYPT; | 1929 | aes_control |= SSS_AES_MODE_DECRYPT; |
| 1929 | 1930 | ||
| 1930 | if ((mode & FLAGS_AES_MODE_MASK) == FLAGS_AES_CBC) | 1931 | if ((mode & FLAGS_AES_MODE_MASK) == FLAGS_AES_CBC) { |
| 1931 | aes_control |= SSS_AES_CHAIN_MODE_CBC; | 1932 | aes_control |= SSS_AES_CHAIN_MODE_CBC; |
| 1932 | else if ((mode & FLAGS_AES_MODE_MASK) == FLAGS_AES_CTR) | 1933 | iv = req->info; |
| 1934 | } else if ((mode & FLAGS_AES_MODE_MASK) == FLAGS_AES_CTR) { | ||
| 1933 | aes_control |= SSS_AES_CHAIN_MODE_CTR; | 1935 | aes_control |= SSS_AES_CHAIN_MODE_CTR; |
| 1936 | iv = req->info; | ||
| 1937 | } else { | ||
| 1938 | iv = NULL; /* AES_ECB */ | ||
| 1939 | } | ||
| 1934 | 1940 | ||
| 1935 | if (dev->ctx->keylen == AES_KEYSIZE_192) | 1941 | if (dev->ctx->keylen == AES_KEYSIZE_192) |
| 1936 | aes_control |= SSS_AES_KEY_SIZE_192; | 1942 | aes_control |= SSS_AES_KEY_SIZE_192; |
| @@ -1961,7 +1967,7 @@ static void s5p_aes_crypt_start(struct s5p_aes_dev *dev, unsigned long mode) | |||
| 1961 | goto outdata_error; | 1967 | goto outdata_error; |
| 1962 | 1968 | ||
| 1963 | SSS_AES_WRITE(dev, AES_CONTROL, aes_control); | 1969 | SSS_AES_WRITE(dev, AES_CONTROL, aes_control); |
| 1964 | s5p_set_aes(dev, dev->ctx->aes_key, req->info, dev->ctx->keylen); | 1970 | s5p_set_aes(dev, dev->ctx->aes_key, iv, dev->ctx->keylen); |
| 1965 | 1971 | ||
| 1966 | s5p_set_dma_indata(dev, dev->sg_src); | 1972 | s5p_set_dma_indata(dev, dev->sg_src); |
| 1967 | s5p_set_dma_outdata(dev, dev->sg_dst); | 1973 | s5p_set_dma_outdata(dev, dev->sg_dst); |
diff --git a/drivers/crypto/sunxi-ss/sun4i-ss-prng.c b/drivers/crypto/sunxi-ss/sun4i-ss-prng.c index 0d01d1624252..63d636424161 100644 --- a/drivers/crypto/sunxi-ss/sun4i-ss-prng.c +++ b/drivers/crypto/sunxi-ss/sun4i-ss-prng.c | |||
| @@ -28,7 +28,7 @@ int sun4i_ss_prng_generate(struct crypto_rng *tfm, const u8 *src, | |||
| 28 | algt = container_of(alg, struct sun4i_ss_alg_template, alg.rng); | 28 | algt = container_of(alg, struct sun4i_ss_alg_template, alg.rng); |
| 29 | ss = algt->ss; | 29 | ss = algt->ss; |
| 30 | 30 | ||
| 31 | spin_lock(&ss->slock); | 31 | spin_lock_bh(&ss->slock); |
| 32 | 32 | ||
| 33 | writel(mode, ss->base + SS_CTL); | 33 | writel(mode, ss->base + SS_CTL); |
| 34 | 34 | ||
| @@ -51,6 +51,6 @@ int sun4i_ss_prng_generate(struct crypto_rng *tfm, const u8 *src, | |||
| 51 | } | 51 | } |
| 52 | 52 | ||
| 53 | writel(0, ss->base + SS_CTL); | 53 | writel(0, ss->base + SS_CTL); |
| 54 | spin_unlock(&ss->slock); | 54 | spin_unlock_bh(&ss->slock); |
| 55 | return dlen; | 55 | return 0; |
| 56 | } | 56 | } |
diff --git a/drivers/crypto/talitos.c b/drivers/crypto/talitos.c index 9c80e0cb1664..6882fa2f8bad 100644 --- a/drivers/crypto/talitos.c +++ b/drivers/crypto/talitos.c | |||
| @@ -1138,6 +1138,10 @@ static int talitos_sg_map(struct device *dev, struct scatterlist *src, | |||
| 1138 | struct talitos_private *priv = dev_get_drvdata(dev); | 1138 | struct talitos_private *priv = dev_get_drvdata(dev); |
| 1139 | bool is_sec1 = has_ftr_sec1(priv); | 1139 | bool is_sec1 = has_ftr_sec1(priv); |
| 1140 | 1140 | ||
| 1141 | if (!src) { | ||
| 1142 | to_talitos_ptr(ptr, 0, 0, is_sec1); | ||
| 1143 | return 1; | ||
| 1144 | } | ||
| 1141 | if (sg_count == 1) { | 1145 | if (sg_count == 1) { |
| 1142 | to_talitos_ptr(ptr, sg_dma_address(src) + offset, len, is_sec1); | 1146 | to_talitos_ptr(ptr, sg_dma_address(src) + offset, len, is_sec1); |
| 1143 | return sg_count; | 1147 | return sg_count; |
diff --git a/drivers/edac/amd64_edac.c b/drivers/edac/amd64_edac.c index 8b16ec595fa7..329cb96f886f 100644 --- a/drivers/edac/amd64_edac.c +++ b/drivers/edac/amd64_edac.c | |||
| @@ -3147,7 +3147,7 @@ static struct amd64_family_type *per_family_init(struct amd64_pvt *pvt) | |||
| 3147 | struct amd64_family_type *fam_type = NULL; | 3147 | struct amd64_family_type *fam_type = NULL; |
| 3148 | 3148 | ||
| 3149 | pvt->ext_model = boot_cpu_data.x86_model >> 4; | 3149 | pvt->ext_model = boot_cpu_data.x86_model >> 4; |
| 3150 | pvt->stepping = boot_cpu_data.x86_mask; | 3150 | pvt->stepping = boot_cpu_data.x86_stepping; |
| 3151 | pvt->model = boot_cpu_data.x86_model; | 3151 | pvt->model = boot_cpu_data.x86_model; |
| 3152 | pvt->fam = boot_cpu_data.x86; | 3152 | pvt->fam = boot_cpu_data.x86; |
| 3153 | 3153 | ||
diff --git a/drivers/extcon/extcon-axp288.c b/drivers/extcon/extcon-axp288.c index 0a44d43802fe..3ec4c715e240 100644 --- a/drivers/extcon/extcon-axp288.c +++ b/drivers/extcon/extcon-axp288.c | |||
| @@ -1,7 +1,6 @@ | |||
| 1 | /* | 1 | /* |
| 2 | * extcon-axp288.c - X-Power AXP288 PMIC extcon cable detection driver | 2 | * extcon-axp288.c - X-Power AXP288 PMIC extcon cable detection driver |
| 3 | * | 3 | * |
| 4 | * Copyright (C) 2016-2017 Hans de Goede <hdegoede@redhat.com> | ||
| 5 | * Copyright (C) 2015 Intel Corporation | 4 | * Copyright (C) 2015 Intel Corporation |
| 6 | * Author: Ramakrishna Pallala <ramakrishna.pallala@intel.com> | 5 | * Author: Ramakrishna Pallala <ramakrishna.pallala@intel.com> |
| 7 | * | 6 | * |
| @@ -98,15 +97,13 @@ struct axp288_extcon_info { | |||
| 98 | struct device *dev; | 97 | struct device *dev; |
| 99 | struct regmap *regmap; | 98 | struct regmap *regmap; |
| 100 | struct regmap_irq_chip_data *regmap_irqc; | 99 | struct regmap_irq_chip_data *regmap_irqc; |
| 101 | struct delayed_work det_work; | ||
| 102 | int irq[EXTCON_IRQ_END]; | 100 | int irq[EXTCON_IRQ_END]; |
| 103 | struct extcon_dev *edev; | 101 | struct extcon_dev *edev; |
| 104 | unsigned int previous_cable; | 102 | unsigned int previous_cable; |
| 105 | bool first_detect_done; | ||
| 106 | }; | 103 | }; |
| 107 | 104 | ||
| 108 | /* Power up/down reason string array */ | 105 | /* Power up/down reason string array */ |
| 109 | static char *axp288_pwr_up_down_info[] = { | 106 | static const char * const axp288_pwr_up_down_info[] = { |
| 110 | "Last wake caused by user pressing the power button", | 107 | "Last wake caused by user pressing the power button", |
| 111 | "Last wake caused by a charger insertion", | 108 | "Last wake caused by a charger insertion", |
| 112 | "Last wake caused by a battery insertion", | 109 | "Last wake caused by a battery insertion", |
| @@ -124,7 +121,7 @@ static char *axp288_pwr_up_down_info[] = { | |||
| 124 | */ | 121 | */ |
| 125 | static void axp288_extcon_log_rsi(struct axp288_extcon_info *info) | 122 | static void axp288_extcon_log_rsi(struct axp288_extcon_info *info) |
| 126 | { | 123 | { |
| 127 | char **rsi; | 124 | const char * const *rsi; |
| 128 | unsigned int val, i, clear_mask = 0; | 125 | unsigned int val, i, clear_mask = 0; |
| 129 | int ret; | 126 | int ret; |
| 130 | 127 | ||
| @@ -140,25 +137,6 @@ static void axp288_extcon_log_rsi(struct axp288_extcon_info *info) | |||
| 140 | regmap_write(info->regmap, AXP288_PS_BOOT_REASON_REG, clear_mask); | 137 | regmap_write(info->regmap, AXP288_PS_BOOT_REASON_REG, clear_mask); |
| 141 | } | 138 | } |
| 142 | 139 | ||
| 143 | static void axp288_chrg_detect_complete(struct axp288_extcon_info *info) | ||
| 144 | { | ||
| 145 | /* | ||
| 146 | * We depend on other drivers to do things like mux the data lines, | ||
| 147 | * enable/disable vbus based on the id-pin, etc. Sometimes the BIOS has | ||
| 148 | * not set these things up correctly resulting in the initial charger | ||
| 149 | * cable type detection giving a wrong result and we end up not charging | ||
| 150 | * or charging at only 0.5A. | ||
| 151 | * | ||
| 152 | * So we schedule a second cable type detection after 2 seconds to | ||
| 153 | * give the other drivers time to load and do their thing. | ||
| 154 | */ | ||
| 155 | if (!info->first_detect_done) { | ||
| 156 | queue_delayed_work(system_wq, &info->det_work, | ||
| 157 | msecs_to_jiffies(2000)); | ||
| 158 | info->first_detect_done = true; | ||
| 159 | } | ||
| 160 | } | ||
| 161 | |||
| 162 | static int axp288_handle_chrg_det_event(struct axp288_extcon_info *info) | 140 | static int axp288_handle_chrg_det_event(struct axp288_extcon_info *info) |
| 163 | { | 141 | { |
| 164 | int ret, stat, cfg, pwr_stat; | 142 | int ret, stat, cfg, pwr_stat; |
| @@ -223,8 +201,6 @@ no_vbus: | |||
| 223 | info->previous_cable = cable; | 201 | info->previous_cable = cable; |
| 224 | } | 202 | } |
| 225 | 203 | ||
| 226 | axp288_chrg_detect_complete(info); | ||
| 227 | |||
| 228 | return 0; | 204 | return 0; |
| 229 | 205 | ||
| 230 | dev_det_ret: | 206 | dev_det_ret: |
| @@ -246,11 +222,8 @@ static irqreturn_t axp288_extcon_isr(int irq, void *data) | |||
| 246 | return IRQ_HANDLED; | 222 | return IRQ_HANDLED; |
| 247 | } | 223 | } |
| 248 | 224 | ||
| 249 | static void axp288_extcon_det_work(struct work_struct *work) | 225 | static void axp288_extcon_enable(struct axp288_extcon_info *info) |
| 250 | { | 226 | { |
| 251 | struct axp288_extcon_info *info = | ||
| 252 | container_of(work, struct axp288_extcon_info, det_work.work); | ||
| 253 | |||
| 254 | regmap_update_bits(info->regmap, AXP288_BC_GLOBAL_REG, | 227 | regmap_update_bits(info->regmap, AXP288_BC_GLOBAL_REG, |
| 255 | BC_GLOBAL_RUN, 0); | 228 | BC_GLOBAL_RUN, 0); |
| 256 | /* Enable the charger detection logic */ | 229 | /* Enable the charger detection logic */ |
| @@ -272,7 +245,6 @@ static int axp288_extcon_probe(struct platform_device *pdev) | |||
| 272 | info->regmap = axp20x->regmap; | 245 | info->regmap = axp20x->regmap; |
| 273 | info->regmap_irqc = axp20x->regmap_irqc; | 246 | info->regmap_irqc = axp20x->regmap_irqc; |
| 274 | info->previous_cable = EXTCON_NONE; | 247 | info->previous_cable = EXTCON_NONE; |
| 275 | INIT_DELAYED_WORK(&info->det_work, axp288_extcon_det_work); | ||
| 276 | 248 | ||
| 277 | platform_set_drvdata(pdev, info); | 249 | platform_set_drvdata(pdev, info); |
| 278 | 250 | ||
| @@ -318,7 +290,7 @@ static int axp288_extcon_probe(struct platform_device *pdev) | |||
| 318 | } | 290 | } |
| 319 | 291 | ||
| 320 | /* Start charger cable type detection */ | 292 | /* Start charger cable type detection */ |
| 321 | queue_delayed_work(system_wq, &info->det_work, 0); | 293 | axp288_extcon_enable(info); |
| 322 | 294 | ||
| 323 | return 0; | 295 | return 0; |
| 324 | } | 296 | } |
diff --git a/drivers/extcon/extcon-intel-int3496.c b/drivers/extcon/extcon-intel-int3496.c index c8691b5a9cb0..191e99f06a9a 100644 --- a/drivers/extcon/extcon-intel-int3496.c +++ b/drivers/extcon/extcon-intel-int3496.c | |||
| @@ -153,8 +153,9 @@ static int int3496_probe(struct platform_device *pdev) | |||
| 153 | return ret; | 153 | return ret; |
| 154 | } | 154 | } |
| 155 | 155 | ||
| 156 | /* queue initial processing of id-pin */ | 156 | /* process id-pin so that we start with the right status */ |
| 157 | queue_delayed_work(system_wq, &data->work, 0); | 157 | queue_delayed_work(system_wq, &data->work, 0); |
| 158 | flush_delayed_work(&data->work); | ||
| 158 | 159 | ||
| 159 | platform_set_drvdata(pdev, data); | 160 | platform_set_drvdata(pdev, data); |
| 160 | 161 | ||
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_atpx_handler.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_atpx_handler.c index e2c3c5ec42d1..c53095b3b0fb 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_atpx_handler.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_atpx_handler.c | |||
| @@ -568,6 +568,7 @@ static const struct amdgpu_px_quirk amdgpu_px_quirk_list[] = { | |||
| 568 | /* HG _PR3 doesn't seem to work on this A+A weston board */ | 568 | /* HG _PR3 doesn't seem to work on this A+A weston board */ |
| 569 | { 0x1002, 0x6900, 0x1002, 0x0124, AMDGPU_PX_QUIRK_FORCE_ATPX }, | 569 | { 0x1002, 0x6900, 0x1002, 0x0124, AMDGPU_PX_QUIRK_FORCE_ATPX }, |
| 570 | { 0x1002, 0x6900, 0x1028, 0x0812, AMDGPU_PX_QUIRK_FORCE_ATPX }, | 570 | { 0x1002, 0x6900, 0x1028, 0x0812, AMDGPU_PX_QUIRK_FORCE_ATPX }, |
| 571 | { 0x1002, 0x6900, 0x1028, 0x0813, AMDGPU_PX_QUIRK_FORCE_ATPX }, | ||
| 571 | { 0, 0, 0, 0, 0 }, | 572 | { 0, 0, 0, 0, 0 }, |
| 572 | }; | 573 | }; |
| 573 | 574 | ||
diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_connectors.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_connectors.c index 8ca3783f2deb..74d2efaec52f 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_connectors.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_connectors.c | |||
| @@ -736,9 +736,11 @@ amdgpu_connector_lvds_detect(struct drm_connector *connector, bool force) | |||
| 736 | enum drm_connector_status ret = connector_status_disconnected; | 736 | enum drm_connector_status ret = connector_status_disconnected; |
| 737 | int r; | 737 | int r; |
| 738 | 738 | ||
| 739 | r = pm_runtime_get_sync(connector->dev->dev); | 739 | if (!drm_kms_helper_is_poll_worker()) { |
| 740 | if (r < 0) | 740 | r = pm_runtime_get_sync(connector->dev->dev); |
| 741 | return connector_status_disconnected; | 741 | if (r < 0) |
| 742 | return connector_status_disconnected; | ||
| 743 | } | ||
| 742 | 744 | ||
| 743 | if (encoder) { | 745 | if (encoder) { |
| 744 | struct amdgpu_encoder *amdgpu_encoder = to_amdgpu_encoder(encoder); | 746 | struct amdgpu_encoder *amdgpu_encoder = to_amdgpu_encoder(encoder); |
| @@ -757,8 +759,12 @@ amdgpu_connector_lvds_detect(struct drm_connector *connector, bool force) | |||
| 757 | /* check acpi lid status ??? */ | 759 | /* check acpi lid status ??? */ |
| 758 | 760 | ||
| 759 | amdgpu_connector_update_scratch_regs(connector, ret); | 761 | amdgpu_connector_update_scratch_regs(connector, ret); |
| 760 | pm_runtime_mark_last_busy(connector->dev->dev); | 762 | |
| 761 | pm_runtime_put_autosuspend(connector->dev->dev); | 763 | if (!drm_kms_helper_is_poll_worker()) { |
| 764 | pm_runtime_mark_last_busy(connector->dev->dev); | ||
| 765 | pm_runtime_put_autosuspend(connector->dev->dev); | ||
| 766 | } | ||
| 767 | |||
| 762 | return ret; | 768 | return ret; |
| 763 | } | 769 | } |
| 764 | 770 | ||
| @@ -868,9 +874,11 @@ amdgpu_connector_vga_detect(struct drm_connector *connector, bool force) | |||
| 868 | enum drm_connector_status ret = connector_status_disconnected; | 874 | enum drm_connector_status ret = connector_status_disconnected; |
| 869 | int r; | 875 | int r; |
| 870 | 876 | ||
| 871 | r = pm_runtime_get_sync(connector->dev->dev); | 877 | if (!drm_kms_helper_is_poll_worker()) { |
| 872 | if (r < 0) | 878 | r = pm_runtime_get_sync(connector->dev->dev); |
| 873 | return connector_status_disconnected; | 879 | if (r < 0) |
| 880 | return connector_status_disconnected; | ||
| 881 | } | ||
| 874 | 882 | ||
| 875 | encoder = amdgpu_connector_best_single_encoder(connector); | 883 | encoder = amdgpu_connector_best_single_encoder(connector); |
| 876 | if (!encoder) | 884 | if (!encoder) |
| @@ -924,8 +932,10 @@ amdgpu_connector_vga_detect(struct drm_connector *connector, bool force) | |||
| 924 | amdgpu_connector_update_scratch_regs(connector, ret); | 932 | amdgpu_connector_update_scratch_regs(connector, ret); |
| 925 | 933 | ||
| 926 | out: | 934 | out: |
| 927 | pm_runtime_mark_last_busy(connector->dev->dev); | 935 | if (!drm_kms_helper_is_poll_worker()) { |
| 928 | pm_runtime_put_autosuspend(connector->dev->dev); | 936 | pm_runtime_mark_last_busy(connector->dev->dev); |
| 937 | pm_runtime_put_autosuspend(connector->dev->dev); | ||
| 938 | } | ||
| 929 | 939 | ||
| 930 | return ret; | 940 | return ret; |
| 931 | } | 941 | } |
| @@ -988,9 +998,11 @@ amdgpu_connector_dvi_detect(struct drm_connector *connector, bool force) | |||
| 988 | enum drm_connector_status ret = connector_status_disconnected; | 998 | enum drm_connector_status ret = connector_status_disconnected; |
| 989 | bool dret = false, broken_edid = false; | 999 | bool dret = false, broken_edid = false; |
| 990 | 1000 | ||
| 991 | r = pm_runtime_get_sync(connector->dev->dev); | 1001 | if (!drm_kms_helper_is_poll_worker()) { |
| 992 | if (r < 0) | 1002 | r = pm_runtime_get_sync(connector->dev->dev); |
| 993 | return connector_status_disconnected; | 1003 | if (r < 0) |
| 1004 | return connector_status_disconnected; | ||
| 1005 | } | ||
| 994 | 1006 | ||
| 995 | if (!force && amdgpu_connector_check_hpd_status_unchanged(connector)) { | 1007 | if (!force && amdgpu_connector_check_hpd_status_unchanged(connector)) { |
| 996 | ret = connector->status; | 1008 | ret = connector->status; |
| @@ -1115,8 +1127,10 @@ out: | |||
| 1115 | amdgpu_connector_update_scratch_regs(connector, ret); | 1127 | amdgpu_connector_update_scratch_regs(connector, ret); |
| 1116 | 1128 | ||
| 1117 | exit: | 1129 | exit: |
| 1118 | pm_runtime_mark_last_busy(connector->dev->dev); | 1130 | if (!drm_kms_helper_is_poll_worker()) { |
| 1119 | pm_runtime_put_autosuspend(connector->dev->dev); | 1131 | pm_runtime_mark_last_busy(connector->dev->dev); |
| 1132 | pm_runtime_put_autosuspend(connector->dev->dev); | ||
| 1133 | } | ||
| 1120 | 1134 | ||
| 1121 | return ret; | 1135 | return ret; |
| 1122 | } | 1136 | } |
| @@ -1359,9 +1373,11 @@ amdgpu_connector_dp_detect(struct drm_connector *connector, bool force) | |||
| 1359 | struct drm_encoder *encoder = amdgpu_connector_best_single_encoder(connector); | 1373 | struct drm_encoder *encoder = amdgpu_connector_best_single_encoder(connector); |
| 1360 | int r; | 1374 | int r; |
| 1361 | 1375 | ||
| 1362 | r = pm_runtime_get_sync(connector->dev->dev); | 1376 | if (!drm_kms_helper_is_poll_worker()) { |
| 1363 | if (r < 0) | 1377 | r = pm_runtime_get_sync(connector->dev->dev); |
| 1364 | return connector_status_disconnected; | 1378 | if (r < 0) |
| 1379 | return connector_status_disconnected; | ||
| 1380 | } | ||
| 1365 | 1381 | ||
| 1366 | if (!force && amdgpu_connector_check_hpd_status_unchanged(connector)) { | 1382 | if (!force && amdgpu_connector_check_hpd_status_unchanged(connector)) { |
| 1367 | ret = connector->status; | 1383 | ret = connector->status; |
| @@ -1429,8 +1445,10 @@ amdgpu_connector_dp_detect(struct drm_connector *connector, bool force) | |||
| 1429 | 1445 | ||
| 1430 | amdgpu_connector_update_scratch_regs(connector, ret); | 1446 | amdgpu_connector_update_scratch_regs(connector, ret); |
| 1431 | out: | 1447 | out: |
| 1432 | pm_runtime_mark_last_busy(connector->dev->dev); | 1448 | if (!drm_kms_helper_is_poll_worker()) { |
| 1433 | pm_runtime_put_autosuspend(connector->dev->dev); | 1449 | pm_runtime_mark_last_busy(connector->dev->dev); |
| 1450 | pm_runtime_put_autosuspend(connector->dev->dev); | ||
| 1451 | } | ||
| 1434 | 1452 | ||
| 1435 | return ret; | 1453 | return ret; |
| 1436 | } | 1454 | } |
diff --git a/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c b/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c index 61e8c3e02d16..33d91e4474ea 100644 --- a/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c +++ b/drivers/gpu/drm/amd/display/dc/core/dc_link_dp.c | |||
| @@ -718,7 +718,7 @@ static enum link_training_result perform_channel_equalization_sequence( | |||
| 718 | uint32_t retries_ch_eq; | 718 | uint32_t retries_ch_eq; |
| 719 | enum dc_lane_count lane_count = lt_settings->link_settings.lane_count; | 719 | enum dc_lane_count lane_count = lt_settings->link_settings.lane_count; |
| 720 | union lane_align_status_updated dpcd_lane_status_updated = {{0}}; | 720 | union lane_align_status_updated dpcd_lane_status_updated = {{0}}; |
| 721 | union lane_status dpcd_lane_status[LANE_COUNT_DP_MAX] = {{{0}}};; | 721 | union lane_status dpcd_lane_status[LANE_COUNT_DP_MAX] = {{{0}}}; |
| 722 | 722 | ||
| 723 | hw_tr_pattern = get_supported_tp(link); | 723 | hw_tr_pattern = get_supported_tp(link); |
| 724 | 724 | ||
diff --git a/drivers/gpu/drm/amd/powerplay/amd_powerplay.c b/drivers/gpu/drm/amd/powerplay/amd_powerplay.c index 4c3223a4d62b..adb6e7b9280c 100644 --- a/drivers/gpu/drm/amd/powerplay/amd_powerplay.c +++ b/drivers/gpu/drm/amd/powerplay/amd_powerplay.c | |||
| @@ -162,7 +162,7 @@ static int pp_hw_init(void *handle) | |||
| 162 | if(hwmgr->smumgr_funcs->start_smu(pp_handle->hwmgr)) { | 162 | if(hwmgr->smumgr_funcs->start_smu(pp_handle->hwmgr)) { |
| 163 | pr_err("smc start failed\n"); | 163 | pr_err("smc start failed\n"); |
| 164 | hwmgr->smumgr_funcs->smu_fini(pp_handle->hwmgr); | 164 | hwmgr->smumgr_funcs->smu_fini(pp_handle->hwmgr); |
| 165 | return -EINVAL;; | 165 | return -EINVAL; |
| 166 | } | 166 | } |
| 167 | if (ret == PP_DPM_DISABLED) | 167 | if (ret == PP_DPM_DISABLED) |
| 168 | goto exit; | 168 | goto exit; |
diff --git a/drivers/gpu/drm/cirrus/cirrus_mode.c b/drivers/gpu/drm/cirrus/cirrus_mode.c index cd23b1b28259..c91b9b054e3f 100644 --- a/drivers/gpu/drm/cirrus/cirrus_mode.c +++ b/drivers/gpu/drm/cirrus/cirrus_mode.c | |||
| @@ -294,22 +294,7 @@ static void cirrus_crtc_prepare(struct drm_crtc *crtc) | |||
| 294 | { | 294 | { |
| 295 | } | 295 | } |
| 296 | 296 | ||
| 297 | /* | 297 | static void cirrus_crtc_load_lut(struct drm_crtc *crtc) |
| 298 | * This is called after a mode is programmed. It should reverse anything done | ||
| 299 | * by the prepare function | ||
| 300 | */ | ||
| 301 | static void cirrus_crtc_commit(struct drm_crtc *crtc) | ||
| 302 | { | ||
| 303 | } | ||
| 304 | |||
| 305 | /* | ||
| 306 | * The core can pass us a set of gamma values to program. We actually only | ||
| 307 | * use this for 8-bit mode so can't perform smooth fades on deeper modes, | ||
| 308 | * but it's a requirement that we provide the function | ||
| 309 | */ | ||
| 310 | static int cirrus_crtc_gamma_set(struct drm_crtc *crtc, u16 *red, u16 *green, | ||
| 311 | u16 *blue, uint32_t size, | ||
| 312 | struct drm_modeset_acquire_ctx *ctx) | ||
| 313 | { | 298 | { |
| 314 | struct drm_device *dev = crtc->dev; | 299 | struct drm_device *dev = crtc->dev; |
| 315 | struct cirrus_device *cdev = dev->dev_private; | 300 | struct cirrus_device *cdev = dev->dev_private; |
| @@ -317,7 +302,7 @@ static int cirrus_crtc_gamma_set(struct drm_crtc *crtc, u16 *red, u16 *green, | |||
| 317 | int i; | 302 | int i; |
| 318 | 303 | ||
| 319 | if (!crtc->enabled) | 304 | if (!crtc->enabled) |
| 320 | return 0; | 305 | return; |
| 321 | 306 | ||
| 322 | r = crtc->gamma_store; | 307 | r = crtc->gamma_store; |
| 323 | g = r + crtc->gamma_size; | 308 | g = r + crtc->gamma_size; |
| @@ -330,6 +315,27 @@ static int cirrus_crtc_gamma_set(struct drm_crtc *crtc, u16 *red, u16 *green, | |||
| 330 | WREG8(PALETTE_DATA, *g++ >> 8); | 315 | WREG8(PALETTE_DATA, *g++ >> 8); |
| 331 | WREG8(PALETTE_DATA, *b++ >> 8); | 316 | WREG8(PALETTE_DATA, *b++ >> 8); |
| 332 | } | 317 | } |
| 318 | } | ||
| 319 | |||
| 320 | /* | ||
| 321 | * This is called after a mode is programmed. It should reverse anything done | ||
| 322 | * by the prepare function | ||
| 323 | */ | ||
| 324 | static void cirrus_crtc_commit(struct drm_crtc *crtc) | ||
| 325 | { | ||
| 326 | cirrus_crtc_load_lut(crtc); | ||
| 327 | } | ||
| 328 | |||
| 329 | /* | ||
| 330 | * The core can pass us a set of gamma values to program. We actually only | ||
| 331 | * use this for 8-bit mode so can't perform smooth fades on deeper modes, | ||
| 332 | * but it's a requirement that we provide the function | ||
| 333 | */ | ||
| 334 | static int cirrus_crtc_gamma_set(struct drm_crtc *crtc, u16 *red, u16 *green, | ||
| 335 | u16 *blue, uint32_t size, | ||
| 336 | struct drm_modeset_acquire_ctx *ctx) | ||
| 337 | { | ||
| 338 | cirrus_crtc_load_lut(crtc); | ||
| 333 | 339 | ||
| 334 | return 0; | 340 | return 0; |
| 335 | } | 341 | } |
diff --git a/drivers/gpu/drm/drm_atomic_helper.c b/drivers/gpu/drm/drm_atomic_helper.c index ab4032167094..ae3cbfe9e01c 100644 --- a/drivers/gpu/drm/drm_atomic_helper.c +++ b/drivers/gpu/drm/drm_atomic_helper.c | |||
| @@ -1878,6 +1878,8 @@ int drm_atomic_helper_setup_commit(struct drm_atomic_state *state, | |||
| 1878 | new_crtc_state->event->base.completion = &commit->flip_done; | 1878 | new_crtc_state->event->base.completion = &commit->flip_done; |
| 1879 | new_crtc_state->event->base.completion_release = release_crtc_commit; | 1879 | new_crtc_state->event->base.completion_release = release_crtc_commit; |
| 1880 | drm_crtc_commit_get(commit); | 1880 | drm_crtc_commit_get(commit); |
| 1881 | |||
| 1882 | commit->abort_completion = true; | ||
| 1881 | } | 1883 | } |
| 1882 | 1884 | ||
| 1883 | for_each_oldnew_connector_in_state(state, conn, old_conn_state, new_conn_state, i) { | 1885 | for_each_oldnew_connector_in_state(state, conn, old_conn_state, new_conn_state, i) { |
| @@ -3421,8 +3423,21 @@ EXPORT_SYMBOL(drm_atomic_helper_crtc_duplicate_state); | |||
| 3421 | void __drm_atomic_helper_crtc_destroy_state(struct drm_crtc_state *state) | 3423 | void __drm_atomic_helper_crtc_destroy_state(struct drm_crtc_state *state) |
| 3422 | { | 3424 | { |
| 3423 | if (state->commit) { | 3425 | if (state->commit) { |
| 3426 | /* | ||
| 3427 | * In the event that a non-blocking commit returns | ||
| 3428 | * -ERESTARTSYS before the commit_tail work is queued, we will | ||
| 3429 | * have an extra reference to the commit object. Release it, if | ||
| 3430 | * the event has not been consumed by the worker. | ||
| 3431 | * | ||
| 3432 | * state->event may be freed, so we can't directly look at | ||
| 3433 | * state->event->base.completion. | ||
| 3434 | */ | ||
| 3435 | if (state->event && state->commit->abort_completion) | ||
| 3436 | drm_crtc_commit_put(state->commit); | ||
| 3437 | |||
| 3424 | kfree(state->commit->event); | 3438 | kfree(state->commit->event); |
| 3425 | state->commit->event = NULL; | 3439 | state->commit->event = NULL; |
| 3440 | |||
| 3426 | drm_crtc_commit_put(state->commit); | 3441 | drm_crtc_commit_put(state->commit); |
| 3427 | } | 3442 | } |
| 3428 | 3443 | ||
diff --git a/drivers/gpu/drm/drm_edid.c b/drivers/gpu/drm/drm_edid.c index ddd537914575..4f751a9d71a3 100644 --- a/drivers/gpu/drm/drm_edid.c +++ b/drivers/gpu/drm/drm_edid.c | |||
| @@ -113,6 +113,9 @@ static const struct edid_quirk { | |||
| 113 | /* AEO model 0 reports 8 bpc, but is a 6 bpc panel */ | 113 | /* AEO model 0 reports 8 bpc, but is a 6 bpc panel */ |
| 114 | { "AEO", 0, EDID_QUIRK_FORCE_6BPC }, | 114 | { "AEO", 0, EDID_QUIRK_FORCE_6BPC }, |
| 115 | 115 | ||
| 116 | /* CPT panel of Asus UX303LA reports 8 bpc, but is a 6 bpc panel */ | ||
| 117 | { "CPT", 0x17df, EDID_QUIRK_FORCE_6BPC }, | ||
| 118 | |||
| 116 | /* Belinea 10 15 55 */ | 119 | /* Belinea 10 15 55 */ |
| 117 | { "MAX", 1516, EDID_QUIRK_PREFER_LARGE_60 }, | 120 | { "MAX", 1516, EDID_QUIRK_PREFER_LARGE_60 }, |
| 118 | { "MAX", 0x77e, EDID_QUIRK_PREFER_LARGE_60 }, | 121 | { "MAX", 0x77e, EDID_QUIRK_PREFER_LARGE_60 }, |
| @@ -162,6 +165,24 @@ static const struct edid_quirk { | |||
| 162 | 165 | ||
| 163 | /* HTC Vive VR Headset */ | 166 | /* HTC Vive VR Headset */ |
| 164 | { "HVR", 0xaa01, EDID_QUIRK_NON_DESKTOP }, | 167 | { "HVR", 0xaa01, EDID_QUIRK_NON_DESKTOP }, |
| 168 | |||
| 169 | /* Oculus Rift DK1, DK2, and CV1 VR Headsets */ | ||
| 170 | { "OVR", 0x0001, EDID_QUIRK_NON_DESKTOP }, | ||
| 171 | { "OVR", 0x0003, EDID_QUIRK_NON_DESKTOP }, | ||
| 172 | { "OVR", 0x0004, EDID_QUIRK_NON_DESKTOP }, | ||
| 173 | |||
| 174 | /* Windows Mixed Reality Headsets */ | ||
| 175 | { "ACR", 0x7fce, EDID_QUIRK_NON_DESKTOP }, | ||
| 176 | { "HPN", 0x3515, EDID_QUIRK_NON_DESKTOP }, | ||
| 177 | { "LEN", 0x0408, EDID_QUIRK_NON_DESKTOP }, | ||
| 178 | { "LEN", 0xb800, EDID_QUIRK_NON_DESKTOP }, | ||
| 179 | { "FUJ", 0x1970, EDID_QUIRK_NON_DESKTOP }, | ||
| 180 | { "DEL", 0x7fce, EDID_QUIRK_NON_DESKTOP }, | ||
| 181 | { "SEC", 0x144a, EDID_QUIRK_NON_DESKTOP }, | ||
| 182 | { "AUS", 0xc102, EDID_QUIRK_NON_DESKTOP }, | ||
| 183 | |||
| 184 | /* Sony PlayStation VR Headset */ | ||
| 185 | { "SNY", 0x0704, EDID_QUIRK_NON_DESKTOP }, | ||
| 165 | }; | 186 | }; |
| 166 | 187 | ||
| 167 | /* | 188 | /* |
diff --git a/drivers/gpu/drm/drm_mm.c b/drivers/gpu/drm/drm_mm.c index 186c4e90cc1c..89eef1bb4ddc 100644 --- a/drivers/gpu/drm/drm_mm.c +++ b/drivers/gpu/drm/drm_mm.c | |||
| @@ -836,9 +836,24 @@ struct drm_mm_node *drm_mm_scan_color_evict(struct drm_mm_scan *scan) | |||
| 836 | if (!mm->color_adjust) | 836 | if (!mm->color_adjust) |
| 837 | return NULL; | 837 | return NULL; |
| 838 | 838 | ||
| 839 | hole = list_first_entry(&mm->hole_stack, typeof(*hole), hole_stack); | 839 | /* |
| 840 | hole_start = __drm_mm_hole_node_start(hole); | 840 | * The hole found during scanning should ideally be the first element |
| 841 | hole_end = hole_start + hole->hole_size; | 841 | * in the hole_stack list, but due to side-effects in the driver it |
| 842 | * may not be. | ||
| 843 | */ | ||
| 844 | list_for_each_entry(hole, &mm->hole_stack, hole_stack) { | ||
| 845 | hole_start = __drm_mm_hole_node_start(hole); | ||
| 846 | hole_end = hole_start + hole->hole_size; | ||
| 847 | |||
| 848 | if (hole_start <= scan->hit_start && | ||
| 849 | hole_end >= scan->hit_end) | ||
| 850 | break; | ||
| 851 | } | ||
| 852 | |||
| 853 | /* We should only be called after we found the hole previously */ | ||
| 854 | DRM_MM_BUG_ON(&hole->hole_stack == &mm->hole_stack); | ||
| 855 | if (unlikely(&hole->hole_stack == &mm->hole_stack)) | ||
| 856 | return NULL; | ||
| 842 | 857 | ||
| 843 | DRM_MM_BUG_ON(hole_start > scan->hit_start); | 858 | DRM_MM_BUG_ON(hole_start > scan->hit_start); |
| 844 | DRM_MM_BUG_ON(hole_end < scan->hit_end); | 859 | DRM_MM_BUG_ON(hole_end < scan->hit_end); |
diff --git a/drivers/gpu/drm/drm_probe_helper.c b/drivers/gpu/drm/drm_probe_helper.c index 555fbe54d6e2..00b8445ba819 100644 --- a/drivers/gpu/drm/drm_probe_helper.c +++ b/drivers/gpu/drm/drm_probe_helper.c | |||
| @@ -654,6 +654,26 @@ out: | |||
| 654 | } | 654 | } |
| 655 | 655 | ||
| 656 | /** | 656 | /** |
| 657 | * drm_kms_helper_is_poll_worker - is %current task an output poll worker? | ||
| 658 | * | ||
| 659 | * Determine if %current task is an output poll worker. This can be used | ||
| 660 | * to select distinct code paths for output polling versus other contexts. | ||
| 661 | * | ||
| 662 | * One use case is to avoid a deadlock between the output poll worker and | ||
| 663 | * the autosuspend worker wherein the latter waits for polling to finish | ||
| 664 | * upon calling drm_kms_helper_poll_disable(), while the former waits for | ||
| 665 | * runtime suspend to finish upon calling pm_runtime_get_sync() in a | ||
| 666 | * connector ->detect hook. | ||
| 667 | */ | ||
| 668 | bool drm_kms_helper_is_poll_worker(void) | ||
| 669 | { | ||
| 670 | struct work_struct *work = current_work(); | ||
| 671 | |||
| 672 | return work && work->func == output_poll_execute; | ||
| 673 | } | ||
| 674 | EXPORT_SYMBOL(drm_kms_helper_is_poll_worker); | ||
| 675 | |||
| 676 | /** | ||
| 657 | * drm_kms_helper_poll_disable - disable output polling | 677 | * drm_kms_helper_poll_disable - disable output polling |
| 658 | * @dev: drm_device | 678 | * @dev: drm_device |
| 659 | * | 679 | * |
diff --git a/drivers/gpu/drm/exynos/exynos_drm_g2d.c b/drivers/gpu/drm/exynos/exynos_drm_g2d.c index 2b8bf2dd6387..f68ef1b3a28c 100644 --- a/drivers/gpu/drm/exynos/exynos_drm_g2d.c +++ b/drivers/gpu/drm/exynos/exynos_drm_g2d.c | |||
| @@ -286,7 +286,6 @@ static int g2d_init_cmdlist(struct g2d_data *g2d) | |||
| 286 | 286 | ||
| 287 | node = kcalloc(G2D_CMDLIST_NUM, sizeof(*node), GFP_KERNEL); | 287 | node = kcalloc(G2D_CMDLIST_NUM, sizeof(*node), GFP_KERNEL); |
| 288 | if (!node) { | 288 | if (!node) { |
| 289 | dev_err(dev, "failed to allocate memory\n"); | ||
| 290 | ret = -ENOMEM; | 289 | ret = -ENOMEM; |
| 291 | goto err; | 290 | goto err; |
| 292 | } | 291 | } |
| @@ -926,7 +925,7 @@ static void g2d_finish_event(struct g2d_data *g2d, u32 cmdlist_no) | |||
| 926 | struct drm_device *drm_dev = g2d->subdrv.drm_dev; | 925 | struct drm_device *drm_dev = g2d->subdrv.drm_dev; |
| 927 | struct g2d_runqueue_node *runqueue_node = g2d->runqueue_node; | 926 | struct g2d_runqueue_node *runqueue_node = g2d->runqueue_node; |
| 928 | struct drm_exynos_pending_g2d_event *e; | 927 | struct drm_exynos_pending_g2d_event *e; |
| 929 | struct timeval now; | 928 | struct timespec64 now; |
| 930 | 929 | ||
| 931 | if (list_empty(&runqueue_node->event_list)) | 930 | if (list_empty(&runqueue_node->event_list)) |
| 932 | return; | 931 | return; |
| @@ -934,9 +933,9 @@ static void g2d_finish_event(struct g2d_data *g2d, u32 cmdlist_no) | |||
| 934 | e = list_first_entry(&runqueue_node->event_list, | 933 | e = list_first_entry(&runqueue_node->event_list, |
| 935 | struct drm_exynos_pending_g2d_event, base.link); | 934 | struct drm_exynos_pending_g2d_event, base.link); |
| 936 | 935 | ||
| 937 | do_gettimeofday(&now); | 936 | ktime_get_ts64(&now); |
| 938 | e->event.tv_sec = now.tv_sec; | 937 | e->event.tv_sec = now.tv_sec; |
| 939 | e->event.tv_usec = now.tv_usec; | 938 | e->event.tv_usec = now.tv_nsec / NSEC_PER_USEC; |
| 940 | e->event.cmdlist_no = cmdlist_no; | 939 | e->event.cmdlist_no = cmdlist_no; |
| 941 | 940 | ||
| 942 | drm_send_event(drm_dev, &e->base); | 941 | drm_send_event(drm_dev, &e->base); |
| @@ -1358,10 +1357,9 @@ int exynos_g2d_exec_ioctl(struct drm_device *drm_dev, void *data, | |||
| 1358 | return -EFAULT; | 1357 | return -EFAULT; |
| 1359 | 1358 | ||
| 1360 | runqueue_node = kmem_cache_alloc(g2d->runqueue_slab, GFP_KERNEL); | 1359 | runqueue_node = kmem_cache_alloc(g2d->runqueue_slab, GFP_KERNEL); |
| 1361 | if (!runqueue_node) { | 1360 | if (!runqueue_node) |
| 1362 | dev_err(dev, "failed to allocate memory\n"); | ||
| 1363 | return -ENOMEM; | 1361 | return -ENOMEM; |
| 1364 | } | 1362 | |
| 1365 | run_cmdlist = &runqueue_node->run_cmdlist; | 1363 | run_cmdlist = &runqueue_node->run_cmdlist; |
| 1366 | event_list = &runqueue_node->event_list; | 1364 | event_list = &runqueue_node->event_list; |
| 1367 | INIT_LIST_HEAD(run_cmdlist); | 1365 | INIT_LIST_HEAD(run_cmdlist); |
diff --git a/drivers/gpu/drm/exynos/exynos_drm_rotator.h b/drivers/gpu/drm/exynos/exynos_drm_rotator.h deleted file mode 100644 index 71a0b4c0c1e8..000000000000 --- a/drivers/gpu/drm/exynos/exynos_drm_rotator.h +++ /dev/null | |||
| @@ -1,19 +0,0 @@ | |||
| 1 | /* | ||
| 2 | * Copyright (c) 2012 Samsung Electronics Co., Ltd. | ||
| 3 | * | ||
| 4 | * Authors: | ||
| 5 | * YoungJun Cho <yj44.cho@samsung.com> | ||
| 6 | * Eunchul Kim <chulspro.kim@samsung.com> | ||
| 7 | * | ||
| 8 | * This program is free software; you can redistribute it and/or modify it | ||
| 9 | * under the terms of the GNU General Public License as published by the | ||
| 10 | * Free Software Foundation; either version 2 of the License, or (at your | ||
| 11 | * option) any later version. | ||
| 12 | */ | ||
| 13 | |||
| 14 | #ifndef _EXYNOS_DRM_ROTATOR_H_ | ||
| 15 | #define _EXYNOS_DRM_ROTATOR_H_ | ||
| 16 | |||
| 17 | /* TODO */ | ||
| 18 | |||
| 19 | #endif | ||
diff --git a/drivers/gpu/drm/exynos/exynos_hdmi.c b/drivers/gpu/drm/exynos/exynos_hdmi.c index a4b75a46f946..abd84cbcf1c2 100644 --- a/drivers/gpu/drm/exynos/exynos_hdmi.c +++ b/drivers/gpu/drm/exynos/exynos_hdmi.c | |||
| @@ -1068,10 +1068,13 @@ static void hdmi_audio_config(struct hdmi_context *hdata) | |||
| 1068 | /* Configuration I2S input ports. Configure I2S_PIN_SEL_0~4 */ | 1068 | /* Configuration I2S input ports. Configure I2S_PIN_SEL_0~4 */ |
| 1069 | hdmi_reg_writeb(hdata, HDMI_I2S_PIN_SEL_0, HDMI_I2S_SEL_SCLK(5) | 1069 | hdmi_reg_writeb(hdata, HDMI_I2S_PIN_SEL_0, HDMI_I2S_SEL_SCLK(5) |
| 1070 | | HDMI_I2S_SEL_LRCK(6)); | 1070 | | HDMI_I2S_SEL_LRCK(6)); |
| 1071 | hdmi_reg_writeb(hdata, HDMI_I2S_PIN_SEL_1, HDMI_I2S_SEL_SDATA1(1) | 1071 | |
| 1072 | | HDMI_I2S_SEL_SDATA2(4)); | 1072 | hdmi_reg_writeb(hdata, HDMI_I2S_PIN_SEL_1, HDMI_I2S_SEL_SDATA1(3) |
| 1073 | | HDMI_I2S_SEL_SDATA0(4)); | ||
| 1074 | |||
| 1073 | hdmi_reg_writeb(hdata, HDMI_I2S_PIN_SEL_2, HDMI_I2S_SEL_SDATA3(1) | 1075 | hdmi_reg_writeb(hdata, HDMI_I2S_PIN_SEL_2, HDMI_I2S_SEL_SDATA3(1) |
| 1074 | | HDMI_I2S_SEL_SDATA2(2)); | 1076 | | HDMI_I2S_SEL_SDATA2(2)); |
| 1077 | |||
| 1075 | hdmi_reg_writeb(hdata, HDMI_I2S_PIN_SEL_3, HDMI_I2S_SEL_DSD(0)); | 1078 | hdmi_reg_writeb(hdata, HDMI_I2S_PIN_SEL_3, HDMI_I2S_SEL_DSD(0)); |
| 1076 | 1079 | ||
| 1077 | /* I2S_CON_1 & 2 */ | 1080 | /* I2S_CON_1 & 2 */ |
diff --git a/drivers/gpu/drm/exynos/regs-fimc.h b/drivers/gpu/drm/exynos/regs-fimc.h index 30496134a3d0..d7cbe53c4c01 100644 --- a/drivers/gpu/drm/exynos/regs-fimc.h +++ b/drivers/gpu/drm/exynos/regs-fimc.h | |||
| @@ -569,7 +569,7 @@ | |||
| 569 | #define EXYNOS_CIIMGEFF_FIN_EMBOSSING (4 << 26) | 569 | #define EXYNOS_CIIMGEFF_FIN_EMBOSSING (4 << 26) |
| 570 | #define EXYNOS_CIIMGEFF_FIN_SILHOUETTE (5 << 26) | 570 | #define EXYNOS_CIIMGEFF_FIN_SILHOUETTE (5 << 26) |
| 571 | #define EXYNOS_CIIMGEFF_FIN_MASK (7 << 26) | 571 | #define EXYNOS_CIIMGEFF_FIN_MASK (7 << 26) |
| 572 | #define EXYNOS_CIIMGEFF_PAT_CBCR_MASK ((0xff < 13) | (0xff < 0)) | 572 | #define EXYNOS_CIIMGEFF_PAT_CBCR_MASK ((0xff << 13) | (0xff << 0)) |
| 573 | 573 | ||
| 574 | /* Real input DMA size register */ | 574 | /* Real input DMA size register */ |
| 575 | #define EXYNOS_CIREAL_ISIZE_AUTOLOAD_ENABLE (1 << 31) | 575 | #define EXYNOS_CIREAL_ISIZE_AUTOLOAD_ENABLE (1 << 31) |
diff --git a/drivers/gpu/drm/exynos/regs-hdmi.h b/drivers/gpu/drm/exynos/regs-hdmi.h index 04be0f7e8193..4420c203ac85 100644 --- a/drivers/gpu/drm/exynos/regs-hdmi.h +++ b/drivers/gpu/drm/exynos/regs-hdmi.h | |||
| @@ -464,7 +464,7 @@ | |||
| 464 | 464 | ||
| 465 | /* I2S_PIN_SEL_1 */ | 465 | /* I2S_PIN_SEL_1 */ |
| 466 | #define HDMI_I2S_SEL_SDATA1(x) (((x) & 0x7) << 4) | 466 | #define HDMI_I2S_SEL_SDATA1(x) (((x) & 0x7) << 4) |
| 467 | #define HDMI_I2S_SEL_SDATA2(x) ((x) & 0x7) | 467 | #define HDMI_I2S_SEL_SDATA0(x) ((x) & 0x7) |
| 468 | 468 | ||
| 469 | /* I2S_PIN_SEL_2 */ | 469 | /* I2S_PIN_SEL_2 */ |
| 470 | #define HDMI_I2S_SEL_SDATA3(x) (((x) & 0x7) << 4) | 470 | #define HDMI_I2S_SEL_SDATA3(x) (((x) & 0x7) << 4) |
diff --git a/drivers/gpu/drm/i915/gvt/kvmgt.c b/drivers/gpu/drm/i915/gvt/kvmgt.c index 909499b73d03..021f722e2481 100644 --- a/drivers/gpu/drm/i915/gvt/kvmgt.c +++ b/drivers/gpu/drm/i915/gvt/kvmgt.c | |||
| @@ -733,6 +733,25 @@ static ssize_t intel_vgpu_rw(struct mdev_device *mdev, char *buf, | |||
| 733 | return ret == 0 ? count : ret; | 733 | return ret == 0 ? count : ret; |
| 734 | } | 734 | } |
| 735 | 735 | ||
| 736 | static bool gtt_entry(struct mdev_device *mdev, loff_t *ppos) | ||
| 737 | { | ||
| 738 | struct intel_vgpu *vgpu = mdev_get_drvdata(mdev); | ||
| 739 | unsigned int index = VFIO_PCI_OFFSET_TO_INDEX(*ppos); | ||
| 740 | struct intel_gvt *gvt = vgpu->gvt; | ||
| 741 | int offset; | ||
| 742 | |||
| 743 | /* Only allow MMIO GGTT entry access */ | ||
| 744 | if (index != PCI_BASE_ADDRESS_0) | ||
| 745 | return false; | ||
| 746 | |||
| 747 | offset = (u64)(*ppos & VFIO_PCI_OFFSET_MASK) - | ||
| 748 | intel_vgpu_get_bar_gpa(vgpu, PCI_BASE_ADDRESS_0); | ||
| 749 | |||
| 750 | return (offset >= gvt->device_info.gtt_start_offset && | ||
| 751 | offset < gvt->device_info.gtt_start_offset + gvt_ggtt_sz(gvt)) ? | ||
| 752 | true : false; | ||
| 753 | } | ||
| 754 | |||
| 736 | static ssize_t intel_vgpu_read(struct mdev_device *mdev, char __user *buf, | 755 | static ssize_t intel_vgpu_read(struct mdev_device *mdev, char __user *buf, |
| 737 | size_t count, loff_t *ppos) | 756 | size_t count, loff_t *ppos) |
| 738 | { | 757 | { |
| @@ -742,7 +761,21 @@ static ssize_t intel_vgpu_read(struct mdev_device *mdev, char __user *buf, | |||
| 742 | while (count) { | 761 | while (count) { |
| 743 | size_t filled; | 762 | size_t filled; |
| 744 | 763 | ||
| 745 | if (count >= 4 && !(*ppos % 4)) { | 764 | /* Only support GGTT entry 8 bytes read */ |
| 765 | if (count >= 8 && !(*ppos % 8) && | ||
| 766 | gtt_entry(mdev, ppos)) { | ||
| 767 | u64 val; | ||
| 768 | |||
| 769 | ret = intel_vgpu_rw(mdev, (char *)&val, sizeof(val), | ||
| 770 | ppos, false); | ||
| 771 | if (ret <= 0) | ||
| 772 | goto read_err; | ||
| 773 | |||
| 774 | if (copy_to_user(buf, &val, sizeof(val))) | ||
| 775 | goto read_err; | ||
| 776 | |||
| 777 | filled = 8; | ||
| 778 | } else if (count >= 4 && !(*ppos % 4)) { | ||
| 746 | u32 val; | 779 | u32 val; |
| 747 | 780 | ||
| 748 | ret = intel_vgpu_rw(mdev, (char *)&val, sizeof(val), | 781 | ret = intel_vgpu_rw(mdev, (char *)&val, sizeof(val), |
| @@ -802,7 +835,21 @@ static ssize_t intel_vgpu_write(struct mdev_device *mdev, | |||
| 802 | while (count) { | 835 | while (count) { |
| 803 | size_t filled; | 836 | size_t filled; |
| 804 | 837 | ||
| 805 | if (count >= 4 && !(*ppos % 4)) { | 838 | /* Only support GGTT entry 8 bytes write */ |
| 839 | if (count >= 8 && !(*ppos % 8) && | ||
| 840 | gtt_entry(mdev, ppos)) { | ||
| 841 | u64 val; | ||
| 842 | |||
| 843 | if (copy_from_user(&val, buf, sizeof(val))) | ||
| 844 | goto write_err; | ||
| 845 | |||
| 846 | ret = intel_vgpu_rw(mdev, (char *)&val, sizeof(val), | ||
| 847 | ppos, true); | ||
| 848 | if (ret <= 0) | ||
| 849 | goto write_err; | ||
| 850 | |||
| 851 | filled = 8; | ||
| 852 | } else if (count >= 4 && !(*ppos % 4)) { | ||
| 806 | u32 val; | 853 | u32 val; |
| 807 | 854 | ||
| 808 | if (copy_from_user(&val, buf, sizeof(val))) | 855 | if (copy_from_user(&val, buf, sizeof(val))) |
diff --git a/drivers/gpu/drm/i915/gvt/mmio_context.c b/drivers/gpu/drm/i915/gvt/mmio_context.c index 73ad6e90e49d..256f1bb522b7 100644 --- a/drivers/gpu/drm/i915/gvt/mmio_context.c +++ b/drivers/gpu/drm/i915/gvt/mmio_context.c | |||
| @@ -118,6 +118,7 @@ static struct engine_mmio gen9_engine_mmio_list[] __cacheline_aligned = { | |||
| 118 | {RCS, HALF_SLICE_CHICKEN3, 0xffff, true}, /* 0xe184 */ | 118 | {RCS, HALF_SLICE_CHICKEN3, 0xffff, true}, /* 0xe184 */ |
| 119 | {RCS, GEN9_HALF_SLICE_CHICKEN5, 0xffff, true}, /* 0xe188 */ | 119 | {RCS, GEN9_HALF_SLICE_CHICKEN5, 0xffff, true}, /* 0xe188 */ |
| 120 | {RCS, GEN9_HALF_SLICE_CHICKEN7, 0xffff, true}, /* 0xe194 */ | 120 | {RCS, GEN9_HALF_SLICE_CHICKEN7, 0xffff, true}, /* 0xe194 */ |
| 121 | {RCS, GEN8_ROW_CHICKEN, 0xffff, true}, /* 0xe4f0 */ | ||
| 121 | {RCS, TRVATTL3PTRDW(0), 0, false}, /* 0x4de0 */ | 122 | {RCS, TRVATTL3PTRDW(0), 0, false}, /* 0x4de0 */ |
| 122 | {RCS, TRVATTL3PTRDW(1), 0, false}, /* 0x4de4 */ | 123 | {RCS, TRVATTL3PTRDW(1), 0, false}, /* 0x4de4 */ |
| 123 | {RCS, TRNULLDETCT, 0, false}, /* 0x4de8 */ | 124 | {RCS, TRNULLDETCT, 0, false}, /* 0x4de8 */ |
diff --git a/drivers/gpu/drm/i915/gvt/trace.h b/drivers/gpu/drm/i915/gvt/trace.h index 7a2511538f34..736bd2bc5127 100644 --- a/drivers/gpu/drm/i915/gvt/trace.h +++ b/drivers/gpu/drm/i915/gvt/trace.h | |||
| @@ -333,7 +333,7 @@ TRACE_EVENT(render_mmio, | |||
| 333 | TP_PROTO(int old_id, int new_id, char *action, unsigned int reg, | 333 | TP_PROTO(int old_id, int new_id, char *action, unsigned int reg, |
| 334 | unsigned int old_val, unsigned int new_val), | 334 | unsigned int old_val, unsigned int new_val), |
| 335 | 335 | ||
| 336 | TP_ARGS(old_id, new_id, action, reg, new_val, old_val), | 336 | TP_ARGS(old_id, new_id, action, reg, old_val, new_val), |
| 337 | 337 | ||
| 338 | TP_STRUCT__entry( | 338 | TP_STRUCT__entry( |
| 339 | __field(int, old_id) | 339 | __field(int, old_id) |
diff --git a/drivers/gpu/drm/i915/i915_drv.c b/drivers/gpu/drm/i915/i915_drv.c index 173d0095e3b2..2f5209de0391 100644 --- a/drivers/gpu/drm/i915/i915_drv.c +++ b/drivers/gpu/drm/i915/i915_drv.c | |||
| @@ -1433,19 +1433,7 @@ void i915_driver_unload(struct drm_device *dev) | |||
| 1433 | 1433 | ||
| 1434 | intel_modeset_cleanup(dev); | 1434 | intel_modeset_cleanup(dev); |
| 1435 | 1435 | ||
| 1436 | /* | 1436 | intel_bios_cleanup(dev_priv); |
| 1437 | * free the memory space allocated for the child device | ||
| 1438 | * config parsed from VBT | ||
| 1439 | */ | ||
| 1440 | if (dev_priv->vbt.child_dev && dev_priv->vbt.child_dev_num) { | ||
| 1441 | kfree(dev_priv->vbt.child_dev); | ||
| 1442 | dev_priv->vbt.child_dev = NULL; | ||
| 1443 | dev_priv->vbt.child_dev_num = 0; | ||
| 1444 | } | ||
| 1445 | kfree(dev_priv->vbt.sdvo_lvds_vbt_mode); | ||
| 1446 | dev_priv->vbt.sdvo_lvds_vbt_mode = NULL; | ||
| 1447 | kfree(dev_priv->vbt.lfp_lvds_vbt_mode); | ||
| 1448 | dev_priv->vbt.lfp_lvds_vbt_mode = NULL; | ||
| 1449 | 1437 | ||
| 1450 | vga_switcheroo_unregister_client(pdev); | 1438 | vga_switcheroo_unregister_client(pdev); |
| 1451 | vga_client_register(pdev, NULL, NULL, NULL); | 1439 | vga_client_register(pdev, NULL, NULL, NULL); |
diff --git a/drivers/gpu/drm/i915/i915_drv.h b/drivers/gpu/drm/i915/i915_drv.h index a42deebedb0f..d307429a5ae0 100644 --- a/drivers/gpu/drm/i915/i915_drv.h +++ b/drivers/gpu/drm/i915/i915_drv.h | |||
| @@ -1349,6 +1349,7 @@ struct intel_vbt_data { | |||
| 1349 | u32 size; | 1349 | u32 size; |
| 1350 | u8 *data; | 1350 | u8 *data; |
| 1351 | const u8 *sequence[MIPI_SEQ_MAX]; | 1351 | const u8 *sequence[MIPI_SEQ_MAX]; |
| 1352 | u8 *deassert_seq; /* Used by fixup_mipi_sequences() */ | ||
| 1352 | } dsi; | 1353 | } dsi; |
| 1353 | 1354 | ||
| 1354 | int crt_ddc_pin; | 1355 | int crt_ddc_pin; |
| @@ -3657,6 +3658,7 @@ extern void intel_i2c_reset(struct drm_i915_private *dev_priv); | |||
| 3657 | 3658 | ||
| 3658 | /* intel_bios.c */ | 3659 | /* intel_bios.c */ |
| 3659 | void intel_bios_init(struct drm_i915_private *dev_priv); | 3660 | void intel_bios_init(struct drm_i915_private *dev_priv); |
| 3661 | void intel_bios_cleanup(struct drm_i915_private *dev_priv); | ||
| 3660 | bool intel_bios_is_valid_vbt(const void *buf, size_t size); | 3662 | bool intel_bios_is_valid_vbt(const void *buf, size_t size); |
| 3661 | bool intel_bios_is_tv_present(struct drm_i915_private *dev_priv); | 3663 | bool intel_bios_is_tv_present(struct drm_i915_private *dev_priv); |
| 3662 | bool intel_bios_is_lvds_present(struct drm_i915_private *dev_priv, u8 *i2c_pin); | 3664 | bool intel_bios_is_lvds_present(struct drm_i915_private *dev_priv, u8 *i2c_pin); |
diff --git a/drivers/gpu/drm/i915/i915_gem_context.c b/drivers/gpu/drm/i915/i915_gem_context.c index 648e7536ff51..0c963fcf31ff 100644 --- a/drivers/gpu/drm/i915/i915_gem_context.c +++ b/drivers/gpu/drm/i915/i915_gem_context.c | |||
| @@ -803,7 +803,7 @@ int i915_gem_context_setparam_ioctl(struct drm_device *dev, void *data, | |||
| 803 | 803 | ||
| 804 | case I915_CONTEXT_PARAM_PRIORITY: | 804 | case I915_CONTEXT_PARAM_PRIORITY: |
| 805 | { | 805 | { |
| 806 | int priority = args->value; | 806 | s64 priority = args->value; |
| 807 | 807 | ||
| 808 | if (args->size) | 808 | if (args->size) |
| 809 | ret = -EINVAL; | 809 | ret = -EINVAL; |
diff --git a/drivers/gpu/drm/i915/i915_oa_cflgt3.c b/drivers/gpu/drm/i915/i915_oa_cflgt3.c index 42ff06fe54a3..792facdb6702 100644 --- a/drivers/gpu/drm/i915/i915_oa_cflgt3.c +++ b/drivers/gpu/drm/i915/i915_oa_cflgt3.c | |||
| @@ -84,9 +84,9 @@ show_test_oa_id(struct device *kdev, struct device_attribute *attr, char *buf) | |||
| 84 | void | 84 | void |
| 85 | i915_perf_load_test_config_cflgt3(struct drm_i915_private *dev_priv) | 85 | i915_perf_load_test_config_cflgt3(struct drm_i915_private *dev_priv) |
| 86 | { | 86 | { |
| 87 | strncpy(dev_priv->perf.oa.test_config.uuid, | 87 | strlcpy(dev_priv->perf.oa.test_config.uuid, |
| 88 | "577e8e2c-3fa0-4875-8743-3538d585e3b0", | 88 | "577e8e2c-3fa0-4875-8743-3538d585e3b0", |
| 89 | UUID_STRING_LEN); | 89 | sizeof(dev_priv->perf.oa.test_config.uuid)); |
| 90 | dev_priv->perf.oa.test_config.id = 1; | 90 | dev_priv->perf.oa.test_config.id = 1; |
| 91 | 91 | ||
| 92 | dev_priv->perf.oa.test_config.mux_regs = mux_config_test_oa; | 92 | dev_priv->perf.oa.test_config.mux_regs = mux_config_test_oa; |
diff --git a/drivers/gpu/drm/i915/i915_oa_cnl.c b/drivers/gpu/drm/i915/i915_oa_cnl.c index ff0ac3627cc4..ba9140c87cc0 100644 --- a/drivers/gpu/drm/i915/i915_oa_cnl.c +++ b/drivers/gpu/drm/i915/i915_oa_cnl.c | |||
| @@ -96,9 +96,9 @@ show_test_oa_id(struct device *kdev, struct device_attribute *attr, char *buf) | |||
| 96 | void | 96 | void |
| 97 | i915_perf_load_test_config_cnl(struct drm_i915_private *dev_priv) | 97 | i915_perf_load_test_config_cnl(struct drm_i915_private *dev_priv) |
| 98 | { | 98 | { |
| 99 | strncpy(dev_priv->perf.oa.test_config.uuid, | 99 | strlcpy(dev_priv->perf.oa.test_config.uuid, |
| 100 | "db41edd4-d8e7-4730-ad11-b9a2d6833503", | 100 | "db41edd4-d8e7-4730-ad11-b9a2d6833503", |
| 101 | UUID_STRING_LEN); | 101 | sizeof(dev_priv->perf.oa.test_config.uuid)); |
| 102 | dev_priv->perf.oa.test_config.id = 1; | 102 | dev_priv->perf.oa.test_config.id = 1; |
| 103 | 103 | ||
| 104 | dev_priv->perf.oa.test_config.mux_regs = mux_config_test_oa; | 104 | dev_priv->perf.oa.test_config.mux_regs = mux_config_test_oa; |
diff --git a/drivers/gpu/drm/i915/i915_pmu.c b/drivers/gpu/drm/i915/i915_pmu.c index 55a8a1e29424..0e9b98c32b62 100644 --- a/drivers/gpu/drm/i915/i915_pmu.c +++ b/drivers/gpu/drm/i915/i915_pmu.c | |||
| @@ -285,26 +285,41 @@ static u64 count_interrupts(struct drm_i915_private *i915) | |||
| 285 | return sum; | 285 | return sum; |
| 286 | } | 286 | } |
| 287 | 287 | ||
| 288 | static void i915_pmu_event_destroy(struct perf_event *event) | 288 | static void engine_event_destroy(struct perf_event *event) |
| 289 | { | 289 | { |
| 290 | WARN_ON(event->parent); | 290 | struct drm_i915_private *i915 = |
| 291 | container_of(event->pmu, typeof(*i915), pmu.base); | ||
| 292 | struct intel_engine_cs *engine; | ||
| 293 | |||
| 294 | engine = intel_engine_lookup_user(i915, | ||
| 295 | engine_event_class(event), | ||
| 296 | engine_event_instance(event)); | ||
| 297 | if (WARN_ON_ONCE(!engine)) | ||
| 298 | return; | ||
| 299 | |||
| 300 | if (engine_event_sample(event) == I915_SAMPLE_BUSY && | ||
| 301 | intel_engine_supports_stats(engine)) | ||
| 302 | intel_disable_engine_stats(engine); | ||
| 291 | } | 303 | } |
| 292 | 304 | ||
| 293 | static int engine_event_init(struct perf_event *event) | 305 | static void i915_pmu_event_destroy(struct perf_event *event) |
| 294 | { | 306 | { |
| 295 | struct drm_i915_private *i915 = | 307 | WARN_ON(event->parent); |
| 296 | container_of(event->pmu, typeof(*i915), pmu.base); | ||
| 297 | 308 | ||
| 298 | if (!intel_engine_lookup_user(i915, engine_event_class(event), | 309 | if (is_engine_event(event)) |
| 299 | engine_event_instance(event))) | 310 | engine_event_destroy(event); |
| 300 | return -ENODEV; | 311 | } |
| 301 | 312 | ||
| 302 | switch (engine_event_sample(event)) { | 313 | static int |
| 314 | engine_event_status(struct intel_engine_cs *engine, | ||
| 315 | enum drm_i915_pmu_engine_sample sample) | ||
| 316 | { | ||
| 317 | switch (sample) { | ||
| 303 | case I915_SAMPLE_BUSY: | 318 | case I915_SAMPLE_BUSY: |
| 304 | case I915_SAMPLE_WAIT: | 319 | case I915_SAMPLE_WAIT: |
| 305 | break; | 320 | break; |
| 306 | case I915_SAMPLE_SEMA: | 321 | case I915_SAMPLE_SEMA: |
| 307 | if (INTEL_GEN(i915) < 6) | 322 | if (INTEL_GEN(engine->i915) < 6) |
| 308 | return -ENODEV; | 323 | return -ENODEV; |
| 309 | break; | 324 | break; |
| 310 | default: | 325 | default: |
| @@ -314,6 +329,30 @@ static int engine_event_init(struct perf_event *event) | |||
| 314 | return 0; | 329 | return 0; |
| 315 | } | 330 | } |
| 316 | 331 | ||
| 332 | static int engine_event_init(struct perf_event *event) | ||
| 333 | { | ||
| 334 | struct drm_i915_private *i915 = | ||
| 335 | container_of(event->pmu, typeof(*i915), pmu.base); | ||
| 336 | struct intel_engine_cs *engine; | ||
| 337 | u8 sample; | ||
| 338 | int ret; | ||
| 339 | |||
| 340 | engine = intel_engine_lookup_user(i915, engine_event_class(event), | ||
| 341 | engine_event_instance(event)); | ||
| 342 | if (!engine) | ||
| 343 | return -ENODEV; | ||
| 344 | |||
| 345 | sample = engine_event_sample(event); | ||
| 346 | ret = engine_event_status(engine, sample); | ||
| 347 | if (ret) | ||
| 348 | return ret; | ||
| 349 | |||
| 350 | if (sample == I915_SAMPLE_BUSY && intel_engine_supports_stats(engine)) | ||
| 351 | ret = intel_enable_engine_stats(engine); | ||
| 352 | |||
| 353 | return ret; | ||
| 354 | } | ||
| 355 | |||
| 317 | static int i915_pmu_event_init(struct perf_event *event) | 356 | static int i915_pmu_event_init(struct perf_event *event) |
| 318 | { | 357 | { |
| 319 | struct drm_i915_private *i915 = | 358 | struct drm_i915_private *i915 = |
| @@ -370,7 +409,94 @@ static int i915_pmu_event_init(struct perf_event *event) | |||
| 370 | return 0; | 409 | return 0; |
| 371 | } | 410 | } |
| 372 | 411 | ||
| 373 | static u64 __i915_pmu_event_read(struct perf_event *event) | 412 | static u64 __get_rc6(struct drm_i915_private *i915) |
| 413 | { | ||
| 414 | u64 val; | ||
| 415 | |||
| 416 | val = intel_rc6_residency_ns(i915, | ||
| 417 | IS_VALLEYVIEW(i915) ? | ||
| 418 | VLV_GT_RENDER_RC6 : | ||
| 419 | GEN6_GT_GFX_RC6); | ||
| 420 | |||
| 421 | if (HAS_RC6p(i915)) | ||
| 422 | val += intel_rc6_residency_ns(i915, GEN6_GT_GFX_RC6p); | ||
| 423 | |||
| 424 | if (HAS_RC6pp(i915)) | ||
| 425 | val += intel_rc6_residency_ns(i915, GEN6_GT_GFX_RC6pp); | ||
| 426 | |||
| 427 | return val; | ||
| 428 | } | ||
| 429 | |||
| 430 | static u64 get_rc6(struct drm_i915_private *i915, bool locked) | ||
| 431 | { | ||
| 432 | #if IS_ENABLED(CONFIG_PM) | ||
| 433 | unsigned long flags; | ||
| 434 | u64 val; | ||
| 435 | |||
| 436 | if (intel_runtime_pm_get_if_in_use(i915)) { | ||
| 437 | val = __get_rc6(i915); | ||
| 438 | intel_runtime_pm_put(i915); | ||
| 439 | |||
| 440 | /* | ||
| 441 | * If we are coming back from being runtime suspended we must | ||
| 442 | * be careful not to report a larger value than returned | ||
| 443 | * previously. | ||
| 444 | */ | ||
| 445 | |||
| 446 | if (!locked) | ||
| 447 | spin_lock_irqsave(&i915->pmu.lock, flags); | ||
| 448 | |||
| 449 | if (val >= i915->pmu.sample[__I915_SAMPLE_RC6_ESTIMATED].cur) { | ||
| 450 | i915->pmu.sample[__I915_SAMPLE_RC6_ESTIMATED].cur = 0; | ||
| 451 | i915->pmu.sample[__I915_SAMPLE_RC6].cur = val; | ||
| 452 | } else { | ||
| 453 | val = i915->pmu.sample[__I915_SAMPLE_RC6_ESTIMATED].cur; | ||
| 454 | } | ||
| 455 | |||
| 456 | if (!locked) | ||
| 457 | spin_unlock_irqrestore(&i915->pmu.lock, flags); | ||
| 458 | } else { | ||
| 459 | struct pci_dev *pdev = i915->drm.pdev; | ||
| 460 | struct device *kdev = &pdev->dev; | ||
| 461 | unsigned long flags2; | ||
| 462 | |||
| 463 | /* | ||
| 464 | * We are runtime suspended. | ||
| 465 | * | ||
| 466 | * Report the delta from when the device was suspended to now, | ||
| 467 | * on top of the last known real value, as the approximated RC6 | ||
| 468 | * counter value. | ||
| 469 | */ | ||
| 470 | if (!locked) | ||
| 471 | spin_lock_irqsave(&i915->pmu.lock, flags); | ||
| 472 | |||
| 473 | spin_lock_irqsave(&kdev->power.lock, flags2); | ||
| 474 | |||
| 475 | if (!i915->pmu.sample[__I915_SAMPLE_RC6_ESTIMATED].cur) | ||
| 476 | i915->pmu.suspended_jiffies_last = | ||
| 477 | kdev->power.suspended_jiffies; | ||
| 478 | |||
| 479 | val = kdev->power.suspended_jiffies - | ||
| 480 | i915->pmu.suspended_jiffies_last; | ||
| 481 | val += jiffies - kdev->power.accounting_timestamp; | ||
| 482 | |||
| 483 | spin_unlock_irqrestore(&kdev->power.lock, flags2); | ||
| 484 | |||
| 485 | val = jiffies_to_nsecs(val); | ||
| 486 | val += i915->pmu.sample[__I915_SAMPLE_RC6].cur; | ||
| 487 | i915->pmu.sample[__I915_SAMPLE_RC6_ESTIMATED].cur = val; | ||
| 488 | |||
| 489 | if (!locked) | ||
| 490 | spin_unlock_irqrestore(&i915->pmu.lock, flags); | ||
| 491 | } | ||
| 492 | |||
| 493 | return val; | ||
| 494 | #else | ||
| 495 | return __get_rc6(i915); | ||
| 496 | #endif | ||
| 497 | } | ||
| 498 | |||
| 499 | static u64 __i915_pmu_event_read(struct perf_event *event, bool locked) | ||
| 374 | { | 500 | { |
| 375 | struct drm_i915_private *i915 = | 501 | struct drm_i915_private *i915 = |
| 376 | container_of(event->pmu, typeof(*i915), pmu.base); | 502 | container_of(event->pmu, typeof(*i915), pmu.base); |
| @@ -387,7 +513,7 @@ static u64 __i915_pmu_event_read(struct perf_event *event) | |||
| 387 | if (WARN_ON_ONCE(!engine)) { | 513 | if (WARN_ON_ONCE(!engine)) { |
| 388 | /* Do nothing */ | 514 | /* Do nothing */ |
| 389 | } else if (sample == I915_SAMPLE_BUSY && | 515 | } else if (sample == I915_SAMPLE_BUSY && |
| 390 | engine->pmu.busy_stats) { | 516 | intel_engine_supports_stats(engine)) { |
| 391 | val = ktime_to_ns(intel_engine_get_busy_time(engine)); | 517 | val = ktime_to_ns(intel_engine_get_busy_time(engine)); |
| 392 | } else { | 518 | } else { |
| 393 | val = engine->pmu.sample[sample].cur; | 519 | val = engine->pmu.sample[sample].cur; |
| @@ -408,18 +534,7 @@ static u64 __i915_pmu_event_read(struct perf_event *event) | |||
| 408 | val = count_interrupts(i915); | 534 | val = count_interrupts(i915); |
| 409 | break; | 535 | break; |
| 410 | case I915_PMU_RC6_RESIDENCY: | 536 | case I915_PMU_RC6_RESIDENCY: |
| 411 | intel_runtime_pm_get(i915); | 537 | val = get_rc6(i915, locked); |
| 412 | val = intel_rc6_residency_ns(i915, | ||
| 413 | IS_VALLEYVIEW(i915) ? | ||
| 414 | VLV_GT_RENDER_RC6 : | ||
| 415 | GEN6_GT_GFX_RC6); | ||
| 416 | if (HAS_RC6p(i915)) | ||
| 417 | val += intel_rc6_residency_ns(i915, | ||
| 418 | GEN6_GT_GFX_RC6p); | ||
| 419 | if (HAS_RC6pp(i915)) | ||
| 420 | val += intel_rc6_residency_ns(i915, | ||
| 421 | GEN6_GT_GFX_RC6pp); | ||
| 422 | intel_runtime_pm_put(i915); | ||
| 423 | break; | 538 | break; |
| 424 | } | 539 | } |
| 425 | } | 540 | } |
| @@ -434,7 +549,7 @@ static void i915_pmu_event_read(struct perf_event *event) | |||
| 434 | 549 | ||
| 435 | again: | 550 | again: |
| 436 | prev = local64_read(&hwc->prev_count); | 551 | prev = local64_read(&hwc->prev_count); |
| 437 | new = __i915_pmu_event_read(event); | 552 | new = __i915_pmu_event_read(event, false); |
| 438 | 553 | ||
| 439 | if (local64_cmpxchg(&hwc->prev_count, prev, new) != prev) | 554 | if (local64_cmpxchg(&hwc->prev_count, prev, new) != prev) |
| 440 | goto again; | 555 | goto again; |
| @@ -442,12 +557,6 @@ again: | |||
| 442 | local64_add(new - prev, &event->count); | 557 | local64_add(new - prev, &event->count); |
| 443 | } | 558 | } |
| 444 | 559 | ||
| 445 | static bool engine_needs_busy_stats(struct intel_engine_cs *engine) | ||
| 446 | { | ||
| 447 | return intel_engine_supports_stats(engine) && | ||
| 448 | (engine->pmu.enable & BIT(I915_SAMPLE_BUSY)); | ||
| 449 | } | ||
| 450 | |||
| 451 | static void i915_pmu_enable(struct perf_event *event) | 560 | static void i915_pmu_enable(struct perf_event *event) |
| 452 | { | 561 | { |
| 453 | struct drm_i915_private *i915 = | 562 | struct drm_i915_private *i915 = |
| @@ -487,21 +596,7 @@ static void i915_pmu_enable(struct perf_event *event) | |||
| 487 | 596 | ||
| 488 | GEM_BUG_ON(sample >= I915_PMU_SAMPLE_BITS); | 597 | GEM_BUG_ON(sample >= I915_PMU_SAMPLE_BITS); |
| 489 | GEM_BUG_ON(engine->pmu.enable_count[sample] == ~0); | 598 | GEM_BUG_ON(engine->pmu.enable_count[sample] == ~0); |
| 490 | if (engine->pmu.enable_count[sample]++ == 0) { | 599 | engine->pmu.enable_count[sample]++; |
| 491 | /* | ||
| 492 | * Enable engine busy stats tracking if needed or | ||
| 493 | * alternatively cancel the scheduled disable. | ||
| 494 | * | ||
| 495 | * If the delayed disable was pending, cancel it and | ||
| 496 | * in this case do not enable since it already is. | ||
| 497 | */ | ||
| 498 | if (engine_needs_busy_stats(engine) && | ||
| 499 | !engine->pmu.busy_stats) { | ||
| 500 | engine->pmu.busy_stats = true; | ||
| 501 | if (!cancel_delayed_work(&engine->pmu.disable_busy_stats)) | ||
| 502 | intel_enable_engine_stats(engine); | ||
| 503 | } | ||
| 504 | } | ||
| 505 | } | 600 | } |
| 506 | 601 | ||
| 507 | /* | 602 | /* |
| @@ -509,19 +604,11 @@ static void i915_pmu_enable(struct perf_event *event) | |||
| 509 | * for all listeners. Even when the event was already enabled and has | 604 | * for all listeners. Even when the event was already enabled and has |
| 510 | * an existing non-zero value. | 605 | * an existing non-zero value. |
| 511 | */ | 606 | */ |
| 512 | local64_set(&event->hw.prev_count, __i915_pmu_event_read(event)); | 607 | local64_set(&event->hw.prev_count, __i915_pmu_event_read(event, true)); |
| 513 | 608 | ||
| 514 | spin_unlock_irqrestore(&i915->pmu.lock, flags); | 609 | spin_unlock_irqrestore(&i915->pmu.lock, flags); |
| 515 | } | 610 | } |
| 516 | 611 | ||
| 517 | static void __disable_busy_stats(struct work_struct *work) | ||
| 518 | { | ||
| 519 | struct intel_engine_cs *engine = | ||
| 520 | container_of(work, typeof(*engine), pmu.disable_busy_stats.work); | ||
| 521 | |||
| 522 | intel_disable_engine_stats(engine); | ||
| 523 | } | ||
| 524 | |||
| 525 | static void i915_pmu_disable(struct perf_event *event) | 612 | static void i915_pmu_disable(struct perf_event *event) |
| 526 | { | 613 | { |
| 527 | struct drm_i915_private *i915 = | 614 | struct drm_i915_private *i915 = |
| @@ -545,26 +632,8 @@ static void i915_pmu_disable(struct perf_event *event) | |||
| 545 | * Decrement the reference count and clear the enabled | 632 | * Decrement the reference count and clear the enabled |
| 546 | * bitmask when the last listener on an event goes away. | 633 | * bitmask when the last listener on an event goes away. |
| 547 | */ | 634 | */ |
| 548 | if (--engine->pmu.enable_count[sample] == 0) { | 635 | if (--engine->pmu.enable_count[sample] == 0) |
| 549 | engine->pmu.enable &= ~BIT(sample); | 636 | engine->pmu.enable &= ~BIT(sample); |
| 550 | if (!engine_needs_busy_stats(engine) && | ||
| 551 | engine->pmu.busy_stats) { | ||
| 552 | engine->pmu.busy_stats = false; | ||
| 553 | /* | ||
| 554 | * We request a delayed disable to handle the | ||
| 555 | * rapid on/off cycles on events, which can | ||
| 556 | * happen when tools like perf stat start, in a | ||
| 557 | * nicer way. | ||
| 558 | * | ||
| 559 | * In addition, this also helps with busy stats | ||
| 560 | * accuracy with background CPU offline/online | ||
| 561 | * migration events. | ||
| 562 | */ | ||
| 563 | queue_delayed_work(system_wq, | ||
| 564 | &engine->pmu.disable_busy_stats, | ||
| 565 | round_jiffies_up_relative(HZ)); | ||
| 566 | } | ||
| 567 | } | ||
| 568 | } | 637 | } |
| 569 | 638 | ||
| 570 | GEM_BUG_ON(bit >= I915_PMU_MASK_BITS); | 639 | GEM_BUG_ON(bit >= I915_PMU_MASK_BITS); |
| @@ -797,8 +866,6 @@ static void i915_pmu_unregister_cpuhp_state(struct drm_i915_private *i915) | |||
| 797 | 866 | ||
| 798 | void i915_pmu_register(struct drm_i915_private *i915) | 867 | void i915_pmu_register(struct drm_i915_private *i915) |
| 799 | { | 868 | { |
| 800 | struct intel_engine_cs *engine; | ||
| 801 | enum intel_engine_id id; | ||
| 802 | int ret; | 869 | int ret; |
| 803 | 870 | ||
| 804 | if (INTEL_GEN(i915) <= 2) { | 871 | if (INTEL_GEN(i915) <= 2) { |
| @@ -820,10 +887,6 @@ void i915_pmu_register(struct drm_i915_private *i915) | |||
| 820 | hrtimer_init(&i915->pmu.timer, CLOCK_MONOTONIC, HRTIMER_MODE_REL); | 887 | hrtimer_init(&i915->pmu.timer, CLOCK_MONOTONIC, HRTIMER_MODE_REL); |
| 821 | i915->pmu.timer.function = i915_sample; | 888 | i915->pmu.timer.function = i915_sample; |
| 822 | 889 | ||
| 823 | for_each_engine(engine, i915, id) | ||
| 824 | INIT_DELAYED_WORK(&engine->pmu.disable_busy_stats, | ||
| 825 | __disable_busy_stats); | ||
| 826 | |||
| 827 | ret = perf_pmu_register(&i915->pmu.base, "i915", -1); | 890 | ret = perf_pmu_register(&i915->pmu.base, "i915", -1); |
| 828 | if (ret) | 891 | if (ret) |
| 829 | goto err; | 892 | goto err; |
| @@ -843,9 +906,6 @@ err: | |||
| 843 | 906 | ||
| 844 | void i915_pmu_unregister(struct drm_i915_private *i915) | 907 | void i915_pmu_unregister(struct drm_i915_private *i915) |
| 845 | { | 908 | { |
| 846 | struct intel_engine_cs *engine; | ||
| 847 | enum intel_engine_id id; | ||
| 848 | |||
| 849 | if (!i915->pmu.base.event_init) | 909 | if (!i915->pmu.base.event_init) |
| 850 | return; | 910 | return; |
| 851 | 911 | ||
| @@ -853,11 +913,6 @@ void i915_pmu_unregister(struct drm_i915_private *i915) | |||
| 853 | 913 | ||
| 854 | hrtimer_cancel(&i915->pmu.timer); | 914 | hrtimer_cancel(&i915->pmu.timer); |
| 855 | 915 | ||
| 856 | for_each_engine(engine, i915, id) { | ||
| 857 | GEM_BUG_ON(engine->pmu.busy_stats); | ||
| 858 | flush_delayed_work(&engine->pmu.disable_busy_stats); | ||
| 859 | } | ||
| 860 | |||
| 861 | i915_pmu_unregister_cpuhp_state(i915); | 916 | i915_pmu_unregister_cpuhp_state(i915); |
| 862 | 917 | ||
| 863 | perf_pmu_unregister(&i915->pmu.base); | 918 | perf_pmu_unregister(&i915->pmu.base); |
diff --git a/drivers/gpu/drm/i915/i915_pmu.h b/drivers/gpu/drm/i915/i915_pmu.h index 40c154d13565..bb62df15afa4 100644 --- a/drivers/gpu/drm/i915/i915_pmu.h +++ b/drivers/gpu/drm/i915/i915_pmu.h | |||
| @@ -27,6 +27,8 @@ | |||
| 27 | enum { | 27 | enum { |
| 28 | __I915_SAMPLE_FREQ_ACT = 0, | 28 | __I915_SAMPLE_FREQ_ACT = 0, |
| 29 | __I915_SAMPLE_FREQ_REQ, | 29 | __I915_SAMPLE_FREQ_REQ, |
| 30 | __I915_SAMPLE_RC6, | ||
| 31 | __I915_SAMPLE_RC6_ESTIMATED, | ||
| 30 | __I915_NUM_PMU_SAMPLERS | 32 | __I915_NUM_PMU_SAMPLERS |
| 31 | }; | 33 | }; |
| 32 | 34 | ||
| @@ -94,6 +96,10 @@ struct i915_pmu { | |||
| 94 | * struct intel_engine_cs. | 96 | * struct intel_engine_cs. |
| 95 | */ | 97 | */ |
| 96 | struct i915_pmu_sample sample[__I915_NUM_PMU_SAMPLERS]; | 98 | struct i915_pmu_sample sample[__I915_NUM_PMU_SAMPLERS]; |
| 99 | /** | ||
| 100 | * @suspended_jiffies_last: Cached suspend time from PM core. | ||
| 101 | */ | ||
| 102 | unsigned long suspended_jiffies_last; | ||
| 97 | }; | 103 | }; |
| 98 | 104 | ||
| 99 | #ifdef CONFIG_PERF_EVENTS | 105 | #ifdef CONFIG_PERF_EVENTS |
diff --git a/drivers/gpu/drm/i915/intel_bios.c b/drivers/gpu/drm/i915/intel_bios.c index f7f771749e48..b49a2df44430 100644 --- a/drivers/gpu/drm/i915/intel_bios.c +++ b/drivers/gpu/drm/i915/intel_bios.c | |||
| @@ -947,6 +947,86 @@ static int goto_next_sequence_v3(const u8 *data, int index, int total) | |||
| 947 | return 0; | 947 | return 0; |
| 948 | } | 948 | } |
| 949 | 949 | ||
| 950 | /* | ||
| 951 | * Get len of pre-fixed deassert fragment from a v1 init OTP sequence, | ||
| 952 | * skip all delay + gpio operands and stop at the first DSI packet op. | ||
| 953 | */ | ||
| 954 | static int get_init_otp_deassert_fragment_len(struct drm_i915_private *dev_priv) | ||
| 955 | { | ||
| 956 | const u8 *data = dev_priv->vbt.dsi.sequence[MIPI_SEQ_INIT_OTP]; | ||
| 957 | int index, len; | ||
| 958 | |||
| 959 | if (WARN_ON(!data || dev_priv->vbt.dsi.seq_version != 1)) | ||
| 960 | return 0; | ||
| 961 | |||
| 962 | /* index = 1 to skip sequence byte */ | ||
| 963 | for (index = 1; data[index] != MIPI_SEQ_ELEM_END; index += len) { | ||
| 964 | switch (data[index]) { | ||
| 965 | case MIPI_SEQ_ELEM_SEND_PKT: | ||
| 966 | return index == 1 ? 0 : index; | ||
| 967 | case MIPI_SEQ_ELEM_DELAY: | ||
| 968 | len = 5; /* 1 byte for operand + uint32 */ | ||
| 969 | break; | ||
| 970 | case MIPI_SEQ_ELEM_GPIO: | ||
| 971 | len = 3; /* 1 byte for op, 1 for gpio_nr, 1 for value */ | ||
| 972 | break; | ||
| 973 | default: | ||
| 974 | return 0; | ||
| 975 | } | ||
| 976 | } | ||
| 977 | |||
| 978 | return 0; | ||
| 979 | } | ||
| 980 | |||
| 981 | /* | ||
| 982 | * Some v1 VBT MIPI sequences do the deassert in the init OTP sequence. | ||
| 983 | * The deassert must be done before calling intel_dsi_device_ready, so for | ||
| 984 | * these devices we split the init OTP sequence into a deassert sequence and | ||
| 985 | * the actual init OTP part. | ||
| 986 | */ | ||
| 987 | static void fixup_mipi_sequences(struct drm_i915_private *dev_priv) | ||
| 988 | { | ||
| 989 | u8 *init_otp; | ||
| 990 | int len; | ||
| 991 | |||
| 992 | /* Limit this to VLV for now. */ | ||
| 993 | if (!IS_VALLEYVIEW(dev_priv)) | ||
| 994 | return; | ||
| 995 | |||
| 996 | /* Limit this to v1 vid-mode sequences */ | ||
| 997 | if (dev_priv->vbt.dsi.config->is_cmd_mode || | ||
| 998 | dev_priv->vbt.dsi.seq_version != 1) | ||
| 999 | return; | ||
| 1000 | |||
| 1001 | /* Only do this if there are otp and assert seqs and no deassert seq */ | ||
| 1002 | if (!dev_priv->vbt.dsi.sequence[MIPI_SEQ_INIT_OTP] || | ||
| 1003 | !dev_priv->vbt.dsi.sequence[MIPI_SEQ_ASSERT_RESET] || | ||
| 1004 | dev_priv->vbt.dsi.sequence[MIPI_SEQ_DEASSERT_RESET]) | ||
| 1005 | return; | ||
| 1006 | |||
| 1007 | /* The deassert-sequence ends at the first DSI packet */ | ||
| 1008 | len = get_init_otp_deassert_fragment_len(dev_priv); | ||
| 1009 | if (!len) | ||
| 1010 | return; | ||
| 1011 | |||
| 1012 | DRM_DEBUG_KMS("Using init OTP fragment to deassert reset\n"); | ||
| 1013 | |||
| 1014 | /* Copy the fragment, update seq byte and terminate it */ | ||
| 1015 | init_otp = (u8 *)dev_priv->vbt.dsi.sequence[MIPI_SEQ_INIT_OTP]; | ||
| 1016 | dev_priv->vbt.dsi.deassert_seq = kmemdup(init_otp, len + 1, GFP_KERNEL); | ||
| 1017 | if (!dev_priv->vbt.dsi.deassert_seq) | ||
| 1018 | return; | ||
| 1019 | dev_priv->vbt.dsi.deassert_seq[0] = MIPI_SEQ_DEASSERT_RESET; | ||
| 1020 | dev_priv->vbt.dsi.deassert_seq[len] = MIPI_SEQ_ELEM_END; | ||
| 1021 | /* Use the copy for deassert */ | ||
| 1022 | dev_priv->vbt.dsi.sequence[MIPI_SEQ_DEASSERT_RESET] = | ||
| 1023 | dev_priv->vbt.dsi.deassert_seq; | ||
| 1024 | /* Replace the last byte of the fragment with init OTP seq byte */ | ||
| 1025 | init_otp[len - 1] = MIPI_SEQ_INIT_OTP; | ||
| 1026 | /* And make MIPI_MIPI_SEQ_INIT_OTP point to it */ | ||
| 1027 | dev_priv->vbt.dsi.sequence[MIPI_SEQ_INIT_OTP] = init_otp + len - 1; | ||
| 1028 | } | ||
| 1029 | |||
| 950 | static void | 1030 | static void |
| 951 | parse_mipi_sequence(struct drm_i915_private *dev_priv, | 1031 | parse_mipi_sequence(struct drm_i915_private *dev_priv, |
| 952 | const struct bdb_header *bdb) | 1032 | const struct bdb_header *bdb) |
| @@ -1016,6 +1096,8 @@ parse_mipi_sequence(struct drm_i915_private *dev_priv, | |||
| 1016 | dev_priv->vbt.dsi.size = seq_size; | 1096 | dev_priv->vbt.dsi.size = seq_size; |
| 1017 | dev_priv->vbt.dsi.seq_version = sequence->version; | 1097 | dev_priv->vbt.dsi.seq_version = sequence->version; |
| 1018 | 1098 | ||
| 1099 | fixup_mipi_sequences(dev_priv); | ||
| 1100 | |||
| 1019 | DRM_DEBUG_DRIVER("MIPI related VBT parsing complete\n"); | 1101 | DRM_DEBUG_DRIVER("MIPI related VBT parsing complete\n"); |
| 1020 | return; | 1102 | return; |
| 1021 | 1103 | ||
| @@ -1589,6 +1671,29 @@ out: | |||
| 1589 | } | 1671 | } |
| 1590 | 1672 | ||
| 1591 | /** | 1673 | /** |
| 1674 | * intel_bios_cleanup - Free any resources allocated by intel_bios_init() | ||
| 1675 | * @dev_priv: i915 device instance | ||
| 1676 | */ | ||
| 1677 | void intel_bios_cleanup(struct drm_i915_private *dev_priv) | ||
| 1678 | { | ||
| 1679 | kfree(dev_priv->vbt.child_dev); | ||
| 1680 | dev_priv->vbt.child_dev = NULL; | ||
| 1681 | dev_priv->vbt.child_dev_num = 0; | ||
| 1682 | kfree(dev_priv->vbt.sdvo_lvds_vbt_mode); | ||
| 1683 | dev_priv->vbt.sdvo_lvds_vbt_mode = NULL; | ||
| 1684 | kfree(dev_priv->vbt.lfp_lvds_vbt_mode); | ||
| 1685 | dev_priv->vbt.lfp_lvds_vbt_mode = NULL; | ||
| 1686 | kfree(dev_priv->vbt.dsi.data); | ||
| 1687 | dev_priv->vbt.dsi.data = NULL; | ||
| 1688 | kfree(dev_priv->vbt.dsi.pps); | ||
| 1689 | dev_priv->vbt.dsi.pps = NULL; | ||
| 1690 | kfree(dev_priv->vbt.dsi.config); | ||
| 1691 | dev_priv->vbt.dsi.config = NULL; | ||
| 1692 | kfree(dev_priv->vbt.dsi.deassert_seq); | ||
| 1693 | dev_priv->vbt.dsi.deassert_seq = NULL; | ||
| 1694 | } | ||
| 1695 | |||
| 1696 | /** | ||
| 1592 | * intel_bios_is_tv_present - is integrated TV present in VBT | 1697 | * intel_bios_is_tv_present - is integrated TV present in VBT |
| 1593 | * @dev_priv: i915 device instance | 1698 | * @dev_priv: i915 device instance |
| 1594 | * | 1699 | * |
diff --git a/drivers/gpu/drm/i915/intel_breadcrumbs.c b/drivers/gpu/drm/i915/intel_breadcrumbs.c index bd40fea16b4f..f54ddda9fdad 100644 --- a/drivers/gpu/drm/i915/intel_breadcrumbs.c +++ b/drivers/gpu/drm/i915/intel_breadcrumbs.c | |||
| @@ -594,29 +594,16 @@ void intel_engine_remove_wait(struct intel_engine_cs *engine, | |||
| 594 | spin_unlock_irq(&b->rb_lock); | 594 | spin_unlock_irq(&b->rb_lock); |
| 595 | } | 595 | } |
| 596 | 596 | ||
| 597 | static bool signal_valid(const struct drm_i915_gem_request *request) | ||
| 598 | { | ||
| 599 | return intel_wait_check_request(&request->signaling.wait, request); | ||
| 600 | } | ||
| 601 | |||
| 602 | static bool signal_complete(const struct drm_i915_gem_request *request) | 597 | static bool signal_complete(const struct drm_i915_gem_request *request) |
| 603 | { | 598 | { |
| 604 | if (!request) | 599 | if (!request) |
| 605 | return false; | 600 | return false; |
| 606 | 601 | ||
| 607 | /* If another process served as the bottom-half it may have already | 602 | /* |
| 608 | * signalled that this wait is already completed. | 603 | * Carefully check if the request is complete, giving time for the |
| 609 | */ | ||
| 610 | if (intel_wait_complete(&request->signaling.wait)) | ||
| 611 | return signal_valid(request); | ||
| 612 | |||
| 613 | /* Carefully check if the request is complete, giving time for the | ||
| 614 | * seqno to be visible or if the GPU hung. | 604 | * seqno to be visible or if the GPU hung. |
| 615 | */ | 605 | */ |
| 616 | if (__i915_request_irq_complete(request)) | 606 | return __i915_request_irq_complete(request); |
| 617 | return true; | ||
| 618 | |||
| 619 | return false; | ||
| 620 | } | 607 | } |
| 621 | 608 | ||
| 622 | static struct drm_i915_gem_request *to_signaler(struct rb_node *rb) | 609 | static struct drm_i915_gem_request *to_signaler(struct rb_node *rb) |
| @@ -659,9 +646,13 @@ static int intel_breadcrumbs_signaler(void *arg) | |||
| 659 | request = i915_gem_request_get_rcu(request); | 646 | request = i915_gem_request_get_rcu(request); |
| 660 | rcu_read_unlock(); | 647 | rcu_read_unlock(); |
| 661 | if (signal_complete(request)) { | 648 | if (signal_complete(request)) { |
| 662 | local_bh_disable(); | 649 | if (!test_bit(DMA_FENCE_FLAG_SIGNALED_BIT, |
| 663 | dma_fence_signal(&request->fence); | 650 | &request->fence.flags)) { |
| 664 | local_bh_enable(); /* kick start the tasklets */ | 651 | local_bh_disable(); |
| 652 | dma_fence_signal(&request->fence); | ||
| 653 | GEM_BUG_ON(!i915_gem_request_completed(request)); | ||
| 654 | local_bh_enable(); /* kick start the tasklets */ | ||
| 655 | } | ||
| 665 | 656 | ||
| 666 | spin_lock_irq(&b->rb_lock); | 657 | spin_lock_irq(&b->rb_lock); |
| 667 | 658 | ||
diff --git a/drivers/gpu/drm/i915/intel_cdclk.c b/drivers/gpu/drm/i915/intel_cdclk.c index 5dc118f26b51..1704c8897afd 100644 --- a/drivers/gpu/drm/i915/intel_cdclk.c +++ b/drivers/gpu/drm/i915/intel_cdclk.c | |||
| @@ -1952,6 +1952,14 @@ int intel_crtc_compute_min_cdclk(const struct intel_crtc_state *crtc_state) | |||
| 1952 | if (crtc_state->has_audio && INTEL_GEN(dev_priv) >= 9) | 1952 | if (crtc_state->has_audio && INTEL_GEN(dev_priv) >= 9) |
| 1953 | min_cdclk = max(2 * 96000, min_cdclk); | 1953 | min_cdclk = max(2 * 96000, min_cdclk); |
| 1954 | 1954 | ||
| 1955 | /* | ||
| 1956 | * On Valleyview some DSI panels lose (v|h)sync when the clock is lower | ||
| 1957 | * than 320000KHz. | ||
| 1958 | */ | ||
| 1959 | if (intel_crtc_has_type(crtc_state, INTEL_OUTPUT_DSI) && | ||
| 1960 | IS_VALLEYVIEW(dev_priv)) | ||
| 1961 | min_cdclk = max(320000, min_cdclk); | ||
| 1962 | |||
| 1955 | if (min_cdclk > dev_priv->max_cdclk_freq) { | 1963 | if (min_cdclk > dev_priv->max_cdclk_freq) { |
| 1956 | DRM_DEBUG_KMS("required cdclk (%d kHz) exceeds max (%d kHz)\n", | 1964 | DRM_DEBUG_KMS("required cdclk (%d kHz) exceeds max (%d kHz)\n", |
| 1957 | min_cdclk, dev_priv->max_cdclk_freq); | 1965 | min_cdclk, dev_priv->max_cdclk_freq); |
diff --git a/drivers/gpu/drm/i915/intel_engine_cs.c b/drivers/gpu/drm/i915/intel_engine_cs.c index d790bdc227ff..fa960cfd2764 100644 --- a/drivers/gpu/drm/i915/intel_engine_cs.c +++ b/drivers/gpu/drm/i915/intel_engine_cs.c | |||
| @@ -1458,7 +1458,9 @@ static bool ring_is_idle(struct intel_engine_cs *engine) | |||
| 1458 | struct drm_i915_private *dev_priv = engine->i915; | 1458 | struct drm_i915_private *dev_priv = engine->i915; |
| 1459 | bool idle = true; | 1459 | bool idle = true; |
| 1460 | 1460 | ||
| 1461 | intel_runtime_pm_get(dev_priv); | 1461 | /* If the whole device is asleep, the engine must be idle */ |
| 1462 | if (!intel_runtime_pm_get_if_in_use(dev_priv)) | ||
| 1463 | return true; | ||
| 1462 | 1464 | ||
| 1463 | /* First check that no commands are left in the ring */ | 1465 | /* First check that no commands are left in the ring */ |
| 1464 | if ((I915_READ_HEAD(engine) & HEAD_ADDR) != | 1466 | if ((I915_READ_HEAD(engine) & HEAD_ADDR) != |
| @@ -1943,16 +1945,22 @@ intel_engine_lookup_user(struct drm_i915_private *i915, u8 class, u8 instance) | |||
| 1943 | */ | 1945 | */ |
| 1944 | int intel_enable_engine_stats(struct intel_engine_cs *engine) | 1946 | int intel_enable_engine_stats(struct intel_engine_cs *engine) |
| 1945 | { | 1947 | { |
| 1948 | struct intel_engine_execlists *execlists = &engine->execlists; | ||
| 1946 | unsigned long flags; | 1949 | unsigned long flags; |
| 1950 | int err = 0; | ||
| 1947 | 1951 | ||
| 1948 | if (!intel_engine_supports_stats(engine)) | 1952 | if (!intel_engine_supports_stats(engine)) |
| 1949 | return -ENODEV; | 1953 | return -ENODEV; |
| 1950 | 1954 | ||
| 1955 | tasklet_disable(&execlists->tasklet); | ||
| 1951 | spin_lock_irqsave(&engine->stats.lock, flags); | 1956 | spin_lock_irqsave(&engine->stats.lock, flags); |
| 1952 | if (engine->stats.enabled == ~0) | 1957 | |
| 1953 | goto busy; | 1958 | if (unlikely(engine->stats.enabled == ~0)) { |
| 1959 | err = -EBUSY; | ||
| 1960 | goto unlock; | ||
| 1961 | } | ||
| 1962 | |||
| 1954 | if (engine->stats.enabled++ == 0) { | 1963 | if (engine->stats.enabled++ == 0) { |
| 1955 | struct intel_engine_execlists *execlists = &engine->execlists; | ||
| 1956 | const struct execlist_port *port = execlists->port; | 1964 | const struct execlist_port *port = execlists->port; |
| 1957 | unsigned int num_ports = execlists_num_ports(execlists); | 1965 | unsigned int num_ports = execlists_num_ports(execlists); |
| 1958 | 1966 | ||
| @@ -1967,14 +1975,12 @@ int intel_enable_engine_stats(struct intel_engine_cs *engine) | |||
| 1967 | if (engine->stats.active) | 1975 | if (engine->stats.active) |
| 1968 | engine->stats.start = engine->stats.enabled_at; | 1976 | engine->stats.start = engine->stats.enabled_at; |
| 1969 | } | 1977 | } |
| 1970 | spin_unlock_irqrestore(&engine->stats.lock, flags); | ||
| 1971 | |||
| 1972 | return 0; | ||
| 1973 | 1978 | ||
| 1974 | busy: | 1979 | unlock: |
| 1975 | spin_unlock_irqrestore(&engine->stats.lock, flags); | 1980 | spin_unlock_irqrestore(&engine->stats.lock, flags); |
| 1981 | tasklet_enable(&execlists->tasklet); | ||
| 1976 | 1982 | ||
| 1977 | return -EBUSY; | 1983 | return err; |
| 1978 | } | 1984 | } |
| 1979 | 1985 | ||
| 1980 | static ktime_t __intel_engine_get_busy_time(struct intel_engine_cs *engine) | 1986 | static ktime_t __intel_engine_get_busy_time(struct intel_engine_cs *engine) |
diff --git a/drivers/gpu/drm/i915/intel_ringbuffer.h b/drivers/gpu/drm/i915/intel_ringbuffer.h index c5ff203e42d6..a0e7a6c2a57c 100644 --- a/drivers/gpu/drm/i915/intel_ringbuffer.h +++ b/drivers/gpu/drm/i915/intel_ringbuffer.h | |||
| @@ -366,20 +366,6 @@ struct intel_engine_cs { | |||
| 366 | */ | 366 | */ |
| 367 | #define I915_ENGINE_SAMPLE_MAX (I915_SAMPLE_SEMA + 1) | 367 | #define I915_ENGINE_SAMPLE_MAX (I915_SAMPLE_SEMA + 1) |
| 368 | struct i915_pmu_sample sample[I915_ENGINE_SAMPLE_MAX]; | 368 | struct i915_pmu_sample sample[I915_ENGINE_SAMPLE_MAX]; |
| 369 | /** | ||
| 370 | * @busy_stats: Has enablement of engine stats tracking been | ||
| 371 | * requested. | ||
| 372 | */ | ||
| 373 | bool busy_stats; | ||
| 374 | /** | ||
| 375 | * @disable_busy_stats: Work item for busy stats disabling. | ||
| 376 | * | ||
| 377 | * Same as with @enable_busy_stats action, with the difference | ||
| 378 | * that we delay it in case there are rapid enable-disable | ||
| 379 | * actions, which can happen during tool startup (like perf | ||
| 380 | * stat). | ||
| 381 | */ | ||
| 382 | struct delayed_work disable_busy_stats; | ||
| 383 | } pmu; | 369 | } pmu; |
| 384 | 370 | ||
| 385 | /* | 371 | /* |
diff --git a/drivers/gpu/drm/meson/meson_crtc.c b/drivers/gpu/drm/meson/meson_crtc.c index 5155f0179b61..05520202c967 100644 --- a/drivers/gpu/drm/meson/meson_crtc.c +++ b/drivers/gpu/drm/meson/meson_crtc.c | |||
| @@ -36,6 +36,7 @@ | |||
| 36 | #include "meson_venc.h" | 36 | #include "meson_venc.h" |
| 37 | #include "meson_vpp.h" | 37 | #include "meson_vpp.h" |
| 38 | #include "meson_viu.h" | 38 | #include "meson_viu.h" |
| 39 | #include "meson_canvas.h" | ||
| 39 | #include "meson_registers.h" | 40 | #include "meson_registers.h" |
| 40 | 41 | ||
| 41 | /* CRTC definition */ | 42 | /* CRTC definition */ |
| @@ -192,6 +193,11 @@ void meson_crtc_irq(struct meson_drm *priv) | |||
| 192 | } else | 193 | } else |
| 193 | meson_vpp_disable_interlace_vscaler_osd1(priv); | 194 | meson_vpp_disable_interlace_vscaler_osd1(priv); |
| 194 | 195 | ||
| 196 | meson_canvas_setup(priv, MESON_CANVAS_ID_OSD1, | ||
| 197 | priv->viu.osd1_addr, priv->viu.osd1_stride, | ||
| 198 | priv->viu.osd1_height, MESON_CANVAS_WRAP_NONE, | ||
| 199 | MESON_CANVAS_BLKMODE_LINEAR); | ||
| 200 | |||
| 195 | /* Enable OSD1 */ | 201 | /* Enable OSD1 */ |
| 196 | writel_bits_relaxed(VPP_OSD1_POSTBLEND, VPP_OSD1_POSTBLEND, | 202 | writel_bits_relaxed(VPP_OSD1_POSTBLEND, VPP_OSD1_POSTBLEND, |
| 197 | priv->io_base + _REG(VPP_MISC)); | 203 | priv->io_base + _REG(VPP_MISC)); |
diff --git a/drivers/gpu/drm/meson/meson_drv.h b/drivers/gpu/drm/meson/meson_drv.h index 5e8b392b9d1f..8450d6ac8c9b 100644 --- a/drivers/gpu/drm/meson/meson_drv.h +++ b/drivers/gpu/drm/meson/meson_drv.h | |||
| @@ -43,6 +43,9 @@ struct meson_drm { | |||
| 43 | bool osd1_commit; | 43 | bool osd1_commit; |
| 44 | uint32_t osd1_ctrl_stat; | 44 | uint32_t osd1_ctrl_stat; |
| 45 | uint32_t osd1_blk0_cfg[5]; | 45 | uint32_t osd1_blk0_cfg[5]; |
| 46 | uint32_t osd1_addr; | ||
| 47 | uint32_t osd1_stride; | ||
| 48 | uint32_t osd1_height; | ||
| 46 | } viu; | 49 | } viu; |
| 47 | 50 | ||
| 48 | struct { | 51 | struct { |
diff --git a/drivers/gpu/drm/meson/meson_plane.c b/drivers/gpu/drm/meson/meson_plane.c index d0a6ac8390f3..27bd3503e1e4 100644 --- a/drivers/gpu/drm/meson/meson_plane.c +++ b/drivers/gpu/drm/meson/meson_plane.c | |||
| @@ -164,10 +164,9 @@ static void meson_plane_atomic_update(struct drm_plane *plane, | |||
| 164 | /* Update Canvas with buffer address */ | 164 | /* Update Canvas with buffer address */ |
| 165 | gem = drm_fb_cma_get_gem_obj(fb, 0); | 165 | gem = drm_fb_cma_get_gem_obj(fb, 0); |
| 166 | 166 | ||
| 167 | meson_canvas_setup(priv, MESON_CANVAS_ID_OSD1, | 167 | priv->viu.osd1_addr = gem->paddr; |
| 168 | gem->paddr, fb->pitches[0], | 168 | priv->viu.osd1_stride = fb->pitches[0]; |
| 169 | fb->height, MESON_CANVAS_WRAP_NONE, | 169 | priv->viu.osd1_height = fb->height; |
| 170 | MESON_CANVAS_BLKMODE_LINEAR); | ||
| 171 | 170 | ||
| 172 | spin_unlock_irqrestore(&priv->drm->event_lock, flags); | 171 | spin_unlock_irqrestore(&priv->drm->event_lock, flags); |
| 173 | } | 172 | } |
diff --git a/drivers/gpu/drm/msm/mdp/mdp5/mdp5_kms.c b/drivers/gpu/drm/msm/mdp/mdp5/mdp5_kms.c index 3e9bba4d6624..6d8e3a9a6fc0 100644 --- a/drivers/gpu/drm/msm/mdp/mdp5/mdp5_kms.c +++ b/drivers/gpu/drm/msm/mdp/mdp5/mdp5_kms.c | |||
| @@ -680,7 +680,7 @@ struct msm_kms *mdp5_kms_init(struct drm_device *dev) | |||
| 680 | } else { | 680 | } else { |
| 681 | dev_info(&pdev->dev, | 681 | dev_info(&pdev->dev, |
| 682 | "no iommu, fallback to phys contig buffers for scanout\n"); | 682 | "no iommu, fallback to phys contig buffers for scanout\n"); |
| 683 | aspace = NULL;; | 683 | aspace = NULL; |
| 684 | } | 684 | } |
| 685 | 685 | ||
| 686 | pm_runtime_put_sync(&pdev->dev); | 686 | pm_runtime_put_sync(&pdev->dev); |
diff --git a/drivers/gpu/drm/nouveau/nouveau_connector.c b/drivers/gpu/drm/nouveau/nouveau_connector.c index 69d6e61a01ec..6ed9cb053dfa 100644 --- a/drivers/gpu/drm/nouveau/nouveau_connector.c +++ b/drivers/gpu/drm/nouveau/nouveau_connector.c | |||
| @@ -570,9 +570,15 @@ nouveau_connector_detect(struct drm_connector *connector, bool force) | |||
| 570 | nv_connector->edid = NULL; | 570 | nv_connector->edid = NULL; |
| 571 | } | 571 | } |
| 572 | 572 | ||
| 573 | ret = pm_runtime_get_sync(connector->dev->dev); | 573 | /* Outputs are only polled while runtime active, so acquiring a |
| 574 | if (ret < 0 && ret != -EACCES) | 574 | * runtime PM ref here is unnecessary (and would deadlock upon |
| 575 | return conn_status; | 575 | * runtime suspend because it waits for polling to finish). |
| 576 | */ | ||
| 577 | if (!drm_kms_helper_is_poll_worker()) { | ||
| 578 | ret = pm_runtime_get_sync(connector->dev->dev); | ||
| 579 | if (ret < 0 && ret != -EACCES) | ||
| 580 | return conn_status; | ||
| 581 | } | ||
| 576 | 582 | ||
| 577 | nv_encoder = nouveau_connector_ddc_detect(connector); | 583 | nv_encoder = nouveau_connector_ddc_detect(connector); |
| 578 | if (nv_encoder && (i2c = nv_encoder->i2c) != NULL) { | 584 | if (nv_encoder && (i2c = nv_encoder->i2c) != NULL) { |
| @@ -647,8 +653,10 @@ detect_analog: | |||
| 647 | 653 | ||
| 648 | out: | 654 | out: |
| 649 | 655 | ||
| 650 | pm_runtime_mark_last_busy(connector->dev->dev); | 656 | if (!drm_kms_helper_is_poll_worker()) { |
| 651 | pm_runtime_put_autosuspend(connector->dev->dev); | 657 | pm_runtime_mark_last_busy(connector->dev->dev); |
| 658 | pm_runtime_put_autosuspend(connector->dev->dev); | ||
| 659 | } | ||
| 652 | 660 | ||
| 653 | return conn_status; | 661 | return conn_status; |
| 654 | } | 662 | } |
diff --git a/drivers/gpu/drm/nouveau/nvkm/subdev/therm/base.c b/drivers/gpu/drm/nouveau/nvkm/subdev/therm/base.c index bf62303571b3..3695cde669f8 100644 --- a/drivers/gpu/drm/nouveau/nvkm/subdev/therm/base.c +++ b/drivers/gpu/drm/nouveau/nvkm/subdev/therm/base.c | |||
| @@ -301,7 +301,7 @@ nvkm_therm_attr_set(struct nvkm_therm *therm, | |||
| 301 | void | 301 | void |
| 302 | nvkm_therm_clkgate_enable(struct nvkm_therm *therm) | 302 | nvkm_therm_clkgate_enable(struct nvkm_therm *therm) |
| 303 | { | 303 | { |
| 304 | if (!therm->func->clkgate_enable || !therm->clkgating_enabled) | 304 | if (!therm || !therm->func->clkgate_enable || !therm->clkgating_enabled) |
| 305 | return; | 305 | return; |
| 306 | 306 | ||
| 307 | nvkm_debug(&therm->subdev, | 307 | nvkm_debug(&therm->subdev, |
| @@ -312,7 +312,7 @@ nvkm_therm_clkgate_enable(struct nvkm_therm *therm) | |||
| 312 | void | 312 | void |
| 313 | nvkm_therm_clkgate_fini(struct nvkm_therm *therm, bool suspend) | 313 | nvkm_therm_clkgate_fini(struct nvkm_therm *therm, bool suspend) |
| 314 | { | 314 | { |
| 315 | if (!therm->func->clkgate_fini || !therm->clkgating_enabled) | 315 | if (!therm || !therm->func->clkgate_fini || !therm->clkgating_enabled) |
| 316 | return; | 316 | return; |
| 317 | 317 | ||
| 318 | nvkm_debug(&therm->subdev, | 318 | nvkm_debug(&therm->subdev, |
| @@ -395,7 +395,7 @@ void | |||
| 395 | nvkm_therm_clkgate_init(struct nvkm_therm *therm, | 395 | nvkm_therm_clkgate_init(struct nvkm_therm *therm, |
| 396 | const struct nvkm_therm_clkgate_pack *p) | 396 | const struct nvkm_therm_clkgate_pack *p) |
| 397 | { | 397 | { |
| 398 | if (!therm->func->clkgate_init || !therm->clkgating_enabled) | 398 | if (!therm || !therm->func->clkgate_init || !therm->clkgating_enabled) |
| 399 | return; | 399 | return; |
| 400 | 400 | ||
| 401 | therm->func->clkgate_init(therm, p); | 401 | therm->func->clkgate_init(therm, p); |
diff --git a/drivers/gpu/drm/radeon/radeon_connectors.c b/drivers/gpu/drm/radeon/radeon_connectors.c index 5012f5e47a1e..2e2ca3c6b47d 100644 --- a/drivers/gpu/drm/radeon/radeon_connectors.c +++ b/drivers/gpu/drm/radeon/radeon_connectors.c | |||
| @@ -899,9 +899,11 @@ radeon_lvds_detect(struct drm_connector *connector, bool force) | |||
| 899 | enum drm_connector_status ret = connector_status_disconnected; | 899 | enum drm_connector_status ret = connector_status_disconnected; |
| 900 | int r; | 900 | int r; |
| 901 | 901 | ||
| 902 | r = pm_runtime_get_sync(connector->dev->dev); | 902 | if (!drm_kms_helper_is_poll_worker()) { |
| 903 | if (r < 0) | 903 | r = pm_runtime_get_sync(connector->dev->dev); |
| 904 | return connector_status_disconnected; | 904 | if (r < 0) |
| 905 | return connector_status_disconnected; | ||
| 906 | } | ||
| 905 | 907 | ||
| 906 | if (encoder) { | 908 | if (encoder) { |
| 907 | struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); | 909 | struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); |
| @@ -924,8 +926,12 @@ radeon_lvds_detect(struct drm_connector *connector, bool force) | |||
| 924 | /* check acpi lid status ??? */ | 926 | /* check acpi lid status ??? */ |
| 925 | 927 | ||
| 926 | radeon_connector_update_scratch_regs(connector, ret); | 928 | radeon_connector_update_scratch_regs(connector, ret); |
| 927 | pm_runtime_mark_last_busy(connector->dev->dev); | 929 | |
| 928 | pm_runtime_put_autosuspend(connector->dev->dev); | 930 | if (!drm_kms_helper_is_poll_worker()) { |
| 931 | pm_runtime_mark_last_busy(connector->dev->dev); | ||
| 932 | pm_runtime_put_autosuspend(connector->dev->dev); | ||
| 933 | } | ||
| 934 | |||
| 929 | return ret; | 935 | return ret; |
| 930 | } | 936 | } |
| 931 | 937 | ||
| @@ -1039,9 +1045,11 @@ radeon_vga_detect(struct drm_connector *connector, bool force) | |||
| 1039 | enum drm_connector_status ret = connector_status_disconnected; | 1045 | enum drm_connector_status ret = connector_status_disconnected; |
| 1040 | int r; | 1046 | int r; |
| 1041 | 1047 | ||
| 1042 | r = pm_runtime_get_sync(connector->dev->dev); | 1048 | if (!drm_kms_helper_is_poll_worker()) { |
| 1043 | if (r < 0) | 1049 | r = pm_runtime_get_sync(connector->dev->dev); |
| 1044 | return connector_status_disconnected; | 1050 | if (r < 0) |
| 1051 | return connector_status_disconnected; | ||
| 1052 | } | ||
| 1045 | 1053 | ||
| 1046 | encoder = radeon_best_single_encoder(connector); | 1054 | encoder = radeon_best_single_encoder(connector); |
| 1047 | if (!encoder) | 1055 | if (!encoder) |
| @@ -1108,8 +1116,10 @@ radeon_vga_detect(struct drm_connector *connector, bool force) | |||
| 1108 | radeon_connector_update_scratch_regs(connector, ret); | 1116 | radeon_connector_update_scratch_regs(connector, ret); |
| 1109 | 1117 | ||
| 1110 | out: | 1118 | out: |
| 1111 | pm_runtime_mark_last_busy(connector->dev->dev); | 1119 | if (!drm_kms_helper_is_poll_worker()) { |
| 1112 | pm_runtime_put_autosuspend(connector->dev->dev); | 1120 | pm_runtime_mark_last_busy(connector->dev->dev); |
| 1121 | pm_runtime_put_autosuspend(connector->dev->dev); | ||
| 1122 | } | ||
| 1113 | 1123 | ||
| 1114 | return ret; | 1124 | return ret; |
| 1115 | } | 1125 | } |
| @@ -1173,9 +1183,11 @@ radeon_tv_detect(struct drm_connector *connector, bool force) | |||
| 1173 | if (!radeon_connector->dac_load_detect) | 1183 | if (!radeon_connector->dac_load_detect) |
| 1174 | return ret; | 1184 | return ret; |
| 1175 | 1185 | ||
| 1176 | r = pm_runtime_get_sync(connector->dev->dev); | 1186 | if (!drm_kms_helper_is_poll_worker()) { |
| 1177 | if (r < 0) | 1187 | r = pm_runtime_get_sync(connector->dev->dev); |
| 1178 | return connector_status_disconnected; | 1188 | if (r < 0) |
| 1189 | return connector_status_disconnected; | ||
| 1190 | } | ||
| 1179 | 1191 | ||
| 1180 | encoder = radeon_best_single_encoder(connector); | 1192 | encoder = radeon_best_single_encoder(connector); |
| 1181 | if (!encoder) | 1193 | if (!encoder) |
| @@ -1187,8 +1199,12 @@ radeon_tv_detect(struct drm_connector *connector, bool force) | |||
| 1187 | if (ret == connector_status_connected) | 1199 | if (ret == connector_status_connected) |
| 1188 | ret = radeon_connector_analog_encoder_conflict_solve(connector, encoder, ret, false); | 1200 | ret = radeon_connector_analog_encoder_conflict_solve(connector, encoder, ret, false); |
| 1189 | radeon_connector_update_scratch_regs(connector, ret); | 1201 | radeon_connector_update_scratch_regs(connector, ret); |
| 1190 | pm_runtime_mark_last_busy(connector->dev->dev); | 1202 | |
| 1191 | pm_runtime_put_autosuspend(connector->dev->dev); | 1203 | if (!drm_kms_helper_is_poll_worker()) { |
| 1204 | pm_runtime_mark_last_busy(connector->dev->dev); | ||
| 1205 | pm_runtime_put_autosuspend(connector->dev->dev); | ||
| 1206 | } | ||
| 1207 | |||
| 1192 | return ret; | 1208 | return ret; |
| 1193 | } | 1209 | } |
| 1194 | 1210 | ||
| @@ -1251,9 +1267,11 @@ radeon_dvi_detect(struct drm_connector *connector, bool force) | |||
| 1251 | enum drm_connector_status ret = connector_status_disconnected; | 1267 | enum drm_connector_status ret = connector_status_disconnected; |
| 1252 | bool dret = false, broken_edid = false; | 1268 | bool dret = false, broken_edid = false; |
| 1253 | 1269 | ||
| 1254 | r = pm_runtime_get_sync(connector->dev->dev); | 1270 | if (!drm_kms_helper_is_poll_worker()) { |
| 1255 | if (r < 0) | 1271 | r = pm_runtime_get_sync(connector->dev->dev); |
| 1256 | return connector_status_disconnected; | 1272 | if (r < 0) |
| 1273 | return connector_status_disconnected; | ||
| 1274 | } | ||
| 1257 | 1275 | ||
| 1258 | if (radeon_connector->detected_hpd_without_ddc) { | 1276 | if (radeon_connector->detected_hpd_without_ddc) { |
| 1259 | force = true; | 1277 | force = true; |
| @@ -1436,8 +1454,10 @@ out: | |||
| 1436 | } | 1454 | } |
| 1437 | 1455 | ||
| 1438 | exit: | 1456 | exit: |
| 1439 | pm_runtime_mark_last_busy(connector->dev->dev); | 1457 | if (!drm_kms_helper_is_poll_worker()) { |
| 1440 | pm_runtime_put_autosuspend(connector->dev->dev); | 1458 | pm_runtime_mark_last_busy(connector->dev->dev); |
| 1459 | pm_runtime_put_autosuspend(connector->dev->dev); | ||
| 1460 | } | ||
| 1441 | 1461 | ||
| 1442 | return ret; | 1462 | return ret; |
| 1443 | } | 1463 | } |
| @@ -1688,9 +1708,11 @@ radeon_dp_detect(struct drm_connector *connector, bool force) | |||
| 1688 | if (radeon_dig_connector->is_mst) | 1708 | if (radeon_dig_connector->is_mst) |
| 1689 | return connector_status_disconnected; | 1709 | return connector_status_disconnected; |
| 1690 | 1710 | ||
| 1691 | r = pm_runtime_get_sync(connector->dev->dev); | 1711 | if (!drm_kms_helper_is_poll_worker()) { |
| 1692 | if (r < 0) | 1712 | r = pm_runtime_get_sync(connector->dev->dev); |
| 1693 | return connector_status_disconnected; | 1713 | if (r < 0) |
| 1714 | return connector_status_disconnected; | ||
| 1715 | } | ||
| 1694 | 1716 | ||
| 1695 | if (!force && radeon_check_hpd_status_unchanged(connector)) { | 1717 | if (!force && radeon_check_hpd_status_unchanged(connector)) { |
| 1696 | ret = connector->status; | 1718 | ret = connector->status; |
| @@ -1777,8 +1799,10 @@ radeon_dp_detect(struct drm_connector *connector, bool force) | |||
| 1777 | } | 1799 | } |
| 1778 | 1800 | ||
| 1779 | out: | 1801 | out: |
| 1780 | pm_runtime_mark_last_busy(connector->dev->dev); | 1802 | if (!drm_kms_helper_is_poll_worker()) { |
| 1781 | pm_runtime_put_autosuspend(connector->dev->dev); | 1803 | pm_runtime_mark_last_busy(connector->dev->dev); |
| 1804 | pm_runtime_put_autosuspend(connector->dev->dev); | ||
| 1805 | } | ||
| 1782 | 1806 | ||
| 1783 | return ret; | 1807 | return ret; |
| 1784 | } | 1808 | } |
diff --git a/drivers/gpu/drm/scheduler/gpu_scheduler.c b/drivers/gpu/drm/scheduler/gpu_scheduler.c index 2c18996d59c5..0d95888ccc3e 100644 --- a/drivers/gpu/drm/scheduler/gpu_scheduler.c +++ b/drivers/gpu/drm/scheduler/gpu_scheduler.c | |||
| @@ -461,7 +461,7 @@ void drm_sched_hw_job_reset(struct drm_gpu_scheduler *sched, struct drm_sched_jo | |||
| 461 | { | 461 | { |
| 462 | struct drm_sched_job *s_job; | 462 | struct drm_sched_job *s_job; |
| 463 | struct drm_sched_entity *entity, *tmp; | 463 | struct drm_sched_entity *entity, *tmp; |
| 464 | int i;; | 464 | int i; |
| 465 | 465 | ||
| 466 | spin_lock(&sched->job_list_lock); | 466 | spin_lock(&sched->job_list_lock); |
| 467 | list_for_each_entry_reverse(s_job, &sched->ring_mirror_list, node) { | 467 | list_for_each_entry_reverse(s_job, &sched->ring_mirror_list, node) { |
diff --git a/drivers/gpu/ipu-v3/ipu-common.c b/drivers/gpu/ipu-v3/ipu-common.c index 658fa2d3e40c..48685cddbad1 100644 --- a/drivers/gpu/ipu-v3/ipu-common.c +++ b/drivers/gpu/ipu-v3/ipu-common.c | |||
| @@ -1089,7 +1089,7 @@ static void ipu_irq_handler(struct irq_desc *desc) | |||
| 1089 | { | 1089 | { |
| 1090 | struct ipu_soc *ipu = irq_desc_get_handler_data(desc); | 1090 | struct ipu_soc *ipu = irq_desc_get_handler_data(desc); |
| 1091 | struct irq_chip *chip = irq_desc_get_chip(desc); | 1091 | struct irq_chip *chip = irq_desc_get_chip(desc); |
| 1092 | const int int_reg[] = { 0, 1, 2, 3, 10, 11, 12, 13, 14}; | 1092 | static const int int_reg[] = { 0, 1, 2, 3, 10, 11, 12, 13, 14}; |
| 1093 | 1093 | ||
| 1094 | chained_irq_enter(chip, desc); | 1094 | chained_irq_enter(chip, desc); |
| 1095 | 1095 | ||
| @@ -1102,7 +1102,7 @@ static void ipu_err_irq_handler(struct irq_desc *desc) | |||
| 1102 | { | 1102 | { |
| 1103 | struct ipu_soc *ipu = irq_desc_get_handler_data(desc); | 1103 | struct ipu_soc *ipu = irq_desc_get_handler_data(desc); |
| 1104 | struct irq_chip *chip = irq_desc_get_chip(desc); | 1104 | struct irq_chip *chip = irq_desc_get_chip(desc); |
| 1105 | const int int_reg[] = { 4, 5, 8, 9}; | 1105 | static const int int_reg[] = { 4, 5, 8, 9}; |
| 1106 | 1106 | ||
| 1107 | chained_irq_enter(chip, desc); | 1107 | chained_irq_enter(chip, desc); |
| 1108 | 1108 | ||
diff --git a/drivers/gpu/ipu-v3/ipu-cpmem.c b/drivers/gpu/ipu-v3/ipu-cpmem.c index bb9c087e6c0d..9f2d9ec42add 100644 --- a/drivers/gpu/ipu-v3/ipu-cpmem.c +++ b/drivers/gpu/ipu-v3/ipu-cpmem.c | |||
| @@ -788,12 +788,14 @@ int ipu_cpmem_set_image(struct ipuv3_channel *ch, struct ipu_image *image) | |||
| 788 | case V4L2_PIX_FMT_SGBRG8: | 788 | case V4L2_PIX_FMT_SGBRG8: |
| 789 | case V4L2_PIX_FMT_SGRBG8: | 789 | case V4L2_PIX_FMT_SGRBG8: |
| 790 | case V4L2_PIX_FMT_SRGGB8: | 790 | case V4L2_PIX_FMT_SRGGB8: |
| 791 | case V4L2_PIX_FMT_GREY: | ||
| 791 | offset = image->rect.left + image->rect.top * pix->bytesperline; | 792 | offset = image->rect.left + image->rect.top * pix->bytesperline; |
| 792 | break; | 793 | break; |
| 793 | case V4L2_PIX_FMT_SBGGR16: | 794 | case V4L2_PIX_FMT_SBGGR16: |
| 794 | case V4L2_PIX_FMT_SGBRG16: | 795 | case V4L2_PIX_FMT_SGBRG16: |
| 795 | case V4L2_PIX_FMT_SGRBG16: | 796 | case V4L2_PIX_FMT_SGRBG16: |
| 796 | case V4L2_PIX_FMT_SRGGB16: | 797 | case V4L2_PIX_FMT_SRGGB16: |
| 798 | case V4L2_PIX_FMT_Y16: | ||
| 797 | offset = image->rect.left * 2 + | 799 | offset = image->rect.left * 2 + |
| 798 | image->rect.top * pix->bytesperline; | 800 | image->rect.top * pix->bytesperline; |
| 799 | break; | 801 | break; |
diff --git a/drivers/gpu/ipu-v3/ipu-csi.c b/drivers/gpu/ipu-v3/ipu-csi.c index 24e12b87a0cb..caa05b0702e1 100644 --- a/drivers/gpu/ipu-v3/ipu-csi.c +++ b/drivers/gpu/ipu-v3/ipu-csi.c | |||
| @@ -288,6 +288,7 @@ static int mbus_code_to_bus_cfg(struct ipu_csi_bus_config *cfg, u32 mbus_code) | |||
| 288 | case MEDIA_BUS_FMT_SGBRG10_1X10: | 288 | case MEDIA_BUS_FMT_SGBRG10_1X10: |
| 289 | case MEDIA_BUS_FMT_SGRBG10_1X10: | 289 | case MEDIA_BUS_FMT_SGRBG10_1X10: |
| 290 | case MEDIA_BUS_FMT_SRGGB10_1X10: | 290 | case MEDIA_BUS_FMT_SRGGB10_1X10: |
| 291 | case MEDIA_BUS_FMT_Y10_1X10: | ||
| 291 | cfg->data_fmt = CSI_SENS_CONF_DATA_FMT_BAYER; | 292 | cfg->data_fmt = CSI_SENS_CONF_DATA_FMT_BAYER; |
| 292 | cfg->mipi_dt = MIPI_DT_RAW10; | 293 | cfg->mipi_dt = MIPI_DT_RAW10; |
| 293 | cfg->data_width = IPU_CSI_DATA_WIDTH_10; | 294 | cfg->data_width = IPU_CSI_DATA_WIDTH_10; |
| @@ -296,6 +297,7 @@ static int mbus_code_to_bus_cfg(struct ipu_csi_bus_config *cfg, u32 mbus_code) | |||
| 296 | case MEDIA_BUS_FMT_SGBRG12_1X12: | 297 | case MEDIA_BUS_FMT_SGBRG12_1X12: |
| 297 | case MEDIA_BUS_FMT_SGRBG12_1X12: | 298 | case MEDIA_BUS_FMT_SGRBG12_1X12: |
| 298 | case MEDIA_BUS_FMT_SRGGB12_1X12: | 299 | case MEDIA_BUS_FMT_SRGGB12_1X12: |
| 300 | case MEDIA_BUS_FMT_Y12_1X12: | ||
| 299 | cfg->data_fmt = CSI_SENS_CONF_DATA_FMT_BAYER; | 301 | cfg->data_fmt = CSI_SENS_CONF_DATA_FMT_BAYER; |
| 300 | cfg->mipi_dt = MIPI_DT_RAW12; | 302 | cfg->mipi_dt = MIPI_DT_RAW12; |
| 301 | cfg->data_width = IPU_CSI_DATA_WIDTH_12; | 303 | cfg->data_width = IPU_CSI_DATA_WIDTH_12; |
diff --git a/drivers/gpu/ipu-v3/ipu-pre.c b/drivers/gpu/ipu-v3/ipu-pre.c index f1cec3d70498..0f70e8847540 100644 --- a/drivers/gpu/ipu-v3/ipu-pre.c +++ b/drivers/gpu/ipu-v3/ipu-pre.c | |||
| @@ -129,11 +129,14 @@ ipu_pre_lookup_by_phandle(struct device *dev, const char *name, int index) | |||
| 129 | if (pre_node == pre->dev->of_node) { | 129 | if (pre_node == pre->dev->of_node) { |
| 130 | mutex_unlock(&ipu_pre_list_mutex); | 130 | mutex_unlock(&ipu_pre_list_mutex); |
| 131 | device_link_add(dev, pre->dev, DL_FLAG_AUTOREMOVE); | 131 | device_link_add(dev, pre->dev, DL_FLAG_AUTOREMOVE); |
| 132 | of_node_put(pre_node); | ||
| 132 | return pre; | 133 | return pre; |
| 133 | } | 134 | } |
| 134 | } | 135 | } |
| 135 | mutex_unlock(&ipu_pre_list_mutex); | 136 | mutex_unlock(&ipu_pre_list_mutex); |
| 136 | 137 | ||
| 138 | of_node_put(pre_node); | ||
| 139 | |||
| 137 | return NULL; | 140 | return NULL; |
| 138 | } | 141 | } |
| 139 | 142 | ||
diff --git a/drivers/gpu/ipu-v3/ipu-prg.c b/drivers/gpu/ipu-v3/ipu-prg.c index 067365c733c6..97b99500153d 100644 --- a/drivers/gpu/ipu-v3/ipu-prg.c +++ b/drivers/gpu/ipu-v3/ipu-prg.c | |||
| @@ -102,11 +102,14 @@ ipu_prg_lookup_by_phandle(struct device *dev, const char *name, int ipu_id) | |||
| 102 | mutex_unlock(&ipu_prg_list_mutex); | 102 | mutex_unlock(&ipu_prg_list_mutex); |
| 103 | device_link_add(dev, prg->dev, DL_FLAG_AUTOREMOVE); | 103 | device_link_add(dev, prg->dev, DL_FLAG_AUTOREMOVE); |
| 104 | prg->id = ipu_id; | 104 | prg->id = ipu_id; |
| 105 | of_node_put(prg_node); | ||
| 105 | return prg; | 106 | return prg; |
| 106 | } | 107 | } |
| 107 | } | 108 | } |
| 108 | mutex_unlock(&ipu_prg_list_mutex); | 109 | mutex_unlock(&ipu_prg_list_mutex); |
| 109 | 110 | ||
| 111 | of_node_put(prg_node); | ||
| 112 | |||
| 110 | return NULL; | 113 | return NULL; |
| 111 | } | 114 | } |
| 112 | 115 | ||
diff --git a/drivers/hid/hid-ids.h b/drivers/hid/hid-ids.h index 43ddcdfbd0da..9454ac134ce2 100644 --- a/drivers/hid/hid-ids.h +++ b/drivers/hid/hid-ids.h | |||
| @@ -645,6 +645,9 @@ | |||
| 645 | #define USB_DEVICE_ID_LD_MICROCASSYTIME 0x1033 | 645 | #define USB_DEVICE_ID_LD_MICROCASSYTIME 0x1033 |
| 646 | #define USB_DEVICE_ID_LD_MICROCASSYTEMPERATURE 0x1035 | 646 | #define USB_DEVICE_ID_LD_MICROCASSYTEMPERATURE 0x1035 |
| 647 | #define USB_DEVICE_ID_LD_MICROCASSYPH 0x1038 | 647 | #define USB_DEVICE_ID_LD_MICROCASSYPH 0x1038 |
| 648 | #define USB_DEVICE_ID_LD_POWERANALYSERCASSY 0x1040 | ||
| 649 | #define USB_DEVICE_ID_LD_CONVERTERCONTROLLERCASSY 0x1042 | ||
| 650 | #define USB_DEVICE_ID_LD_MACHINETESTCASSY 0x1043 | ||
| 648 | #define USB_DEVICE_ID_LD_JWM 0x1080 | 651 | #define USB_DEVICE_ID_LD_JWM 0x1080 |
| 649 | #define USB_DEVICE_ID_LD_DMMP 0x1081 | 652 | #define USB_DEVICE_ID_LD_DMMP 0x1081 |
| 650 | #define USB_DEVICE_ID_LD_UMIP 0x1090 | 653 | #define USB_DEVICE_ID_LD_UMIP 0x1090 |
diff --git a/drivers/hid/hid-quirks.c b/drivers/hid/hid-quirks.c index 5f6035a5ce36..e92b77fa574a 100644 --- a/drivers/hid/hid-quirks.c +++ b/drivers/hid/hid-quirks.c | |||
| @@ -809,6 +809,9 @@ static const struct hid_device_id hid_ignore_list[] = { | |||
| 809 | { HID_USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_MICROCASSYTIME) }, | 809 | { HID_USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_MICROCASSYTIME) }, |
| 810 | { HID_USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_MICROCASSYTEMPERATURE) }, | 810 | { HID_USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_MICROCASSYTEMPERATURE) }, |
| 811 | { HID_USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_MICROCASSYPH) }, | 811 | { HID_USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_MICROCASSYPH) }, |
| 812 | { HID_USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_POWERANALYSERCASSY) }, | ||
| 813 | { HID_USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_CONVERTERCONTROLLERCASSY) }, | ||
| 814 | { HID_USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_MACHINETESTCASSY) }, | ||
| 812 | { HID_USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_JWM) }, | 815 | { HID_USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_JWM) }, |
| 813 | { HID_USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_DMMP) }, | 816 | { HID_USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_DMMP) }, |
| 814 | { HID_USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_UMIP) }, | 817 | { HID_USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_UMIP) }, |
diff --git a/drivers/hwmon/coretemp.c b/drivers/hwmon/coretemp.c index 4bdbf77f7197..72c338eb5fae 100644 --- a/drivers/hwmon/coretemp.c +++ b/drivers/hwmon/coretemp.c | |||
| @@ -269,13 +269,13 @@ static int adjust_tjmax(struct cpuinfo_x86 *c, u32 id, struct device *dev) | |||
| 269 | for (i = 0; i < ARRAY_SIZE(tjmax_model_table); i++) { | 269 | for (i = 0; i < ARRAY_SIZE(tjmax_model_table); i++) { |
| 270 | const struct tjmax_model *tm = &tjmax_model_table[i]; | 270 | const struct tjmax_model *tm = &tjmax_model_table[i]; |
| 271 | if (c->x86_model == tm->model && | 271 | if (c->x86_model == tm->model && |
| 272 | (tm->mask == ANY || c->x86_mask == tm->mask)) | 272 | (tm->mask == ANY || c->x86_stepping == tm->mask)) |
| 273 | return tm->tjmax; | 273 | return tm->tjmax; |
| 274 | } | 274 | } |
| 275 | 275 | ||
| 276 | /* Early chips have no MSR for TjMax */ | 276 | /* Early chips have no MSR for TjMax */ |
| 277 | 277 | ||
| 278 | if (c->x86_model == 0xf && c->x86_mask < 4) | 278 | if (c->x86_model == 0xf && c->x86_stepping < 4) |
| 279 | usemsr_ee = 0; | 279 | usemsr_ee = 0; |
| 280 | 280 | ||
| 281 | if (c->x86_model > 0xe && usemsr_ee) { | 281 | if (c->x86_model > 0xe && usemsr_ee) { |
| @@ -426,7 +426,7 @@ static int chk_ucode_version(unsigned int cpu) | |||
| 426 | * Readings might stop update when processor visited too deep sleep, | 426 | * Readings might stop update when processor visited too deep sleep, |
| 427 | * fixed for stepping D0 (6EC). | 427 | * fixed for stepping D0 (6EC). |
| 428 | */ | 428 | */ |
| 429 | if (c->x86_model == 0xe && c->x86_mask < 0xc && c->microcode < 0x39) { | 429 | if (c->x86_model == 0xe && c->x86_stepping < 0xc && c->microcode < 0x39) { |
| 430 | pr_err("Errata AE18 not fixed, update BIOS or microcode of the CPU!\n"); | 430 | pr_err("Errata AE18 not fixed, update BIOS or microcode of the CPU!\n"); |
| 431 | return -ENODEV; | 431 | return -ENODEV; |
| 432 | } | 432 | } |
diff --git a/drivers/hwmon/hwmon-vid.c b/drivers/hwmon/hwmon-vid.c index ef91b8a67549..84e91286fc4f 100644 --- a/drivers/hwmon/hwmon-vid.c +++ b/drivers/hwmon/hwmon-vid.c | |||
| @@ -293,7 +293,7 @@ u8 vid_which_vrm(void) | |||
| 293 | if (c->x86 < 6) /* Any CPU with family lower than 6 */ | 293 | if (c->x86 < 6) /* Any CPU with family lower than 6 */ |
| 294 | return 0; /* doesn't have VID */ | 294 | return 0; /* doesn't have VID */ |
| 295 | 295 | ||
| 296 | vrm_ret = find_vrm(c->x86, c->x86_model, c->x86_mask, c->x86_vendor); | 296 | vrm_ret = find_vrm(c->x86, c->x86_model, c->x86_stepping, c->x86_vendor); |
| 297 | if (vrm_ret == 134) | 297 | if (vrm_ret == 134) |
| 298 | vrm_ret = get_via_model_d_vrm(); | 298 | vrm_ret = get_via_model_d_vrm(); |
| 299 | if (vrm_ret == 0) | 299 | if (vrm_ret == 0) |
diff --git a/drivers/hwmon/k10temp.c b/drivers/hwmon/k10temp.c index 06b4e1c78bd8..051a72eecb24 100644 --- a/drivers/hwmon/k10temp.c +++ b/drivers/hwmon/k10temp.c | |||
| @@ -129,7 +129,10 @@ static ssize_t temp1_input_show(struct device *dev, | |||
| 129 | 129 | ||
| 130 | data->read_tempreg(data->pdev, ®val); | 130 | data->read_tempreg(data->pdev, ®val); |
| 131 | temp = (regval >> 21) * 125; | 131 | temp = (regval >> 21) * 125; |
| 132 | temp -= data->temp_offset; | 132 | if (temp > data->temp_offset) |
| 133 | temp -= data->temp_offset; | ||
| 134 | else | ||
| 135 | temp = 0; | ||
| 133 | 136 | ||
| 134 | return sprintf(buf, "%u\n", temp); | 137 | return sprintf(buf, "%u\n", temp); |
| 135 | } | 138 | } |
| @@ -227,7 +230,7 @@ static bool has_erratum_319(struct pci_dev *pdev) | |||
| 227 | * and AM3 formats, but that's the best we can do. | 230 | * and AM3 formats, but that's the best we can do. |
| 228 | */ | 231 | */ |
| 229 | return boot_cpu_data.x86_model < 4 || | 232 | return boot_cpu_data.x86_model < 4 || |
| 230 | (boot_cpu_data.x86_model == 4 && boot_cpu_data.x86_mask <= 2); | 233 | (boot_cpu_data.x86_model == 4 && boot_cpu_data.x86_stepping <= 2); |
| 231 | } | 234 | } |
| 232 | 235 | ||
| 233 | static int k10temp_probe(struct pci_dev *pdev, | 236 | static int k10temp_probe(struct pci_dev *pdev, |
diff --git a/drivers/hwmon/k8temp.c b/drivers/hwmon/k8temp.c index 5a632bcf869b..e59f9113fb93 100644 --- a/drivers/hwmon/k8temp.c +++ b/drivers/hwmon/k8temp.c | |||
| @@ -187,7 +187,7 @@ static int k8temp_probe(struct pci_dev *pdev, | |||
| 187 | return -ENOMEM; | 187 | return -ENOMEM; |
| 188 | 188 | ||
| 189 | model = boot_cpu_data.x86_model; | 189 | model = boot_cpu_data.x86_model; |
| 190 | stepping = boot_cpu_data.x86_mask; | 190 | stepping = boot_cpu_data.x86_stepping; |
| 191 | 191 | ||
| 192 | /* feature available since SH-C0, exclude older revisions */ | 192 | /* feature available since SH-C0, exclude older revisions */ |
| 193 | if ((model == 4 && stepping == 0) || | 193 | if ((model == 4 && stepping == 0) || |
diff --git a/drivers/i2c/busses/Kconfig b/drivers/i2c/busses/Kconfig index a9805c7cb305..e2954fb86d65 100644 --- a/drivers/i2c/busses/Kconfig +++ b/drivers/i2c/busses/Kconfig | |||
| @@ -123,8 +123,10 @@ config I2C_I801 | |||
| 123 | Wildcat Point (PCH) | 123 | Wildcat Point (PCH) |
| 124 | Wildcat Point-LP (PCH) | 124 | Wildcat Point-LP (PCH) |
| 125 | BayTrail (SOC) | 125 | BayTrail (SOC) |
| 126 | Braswell (SOC) | ||
| 126 | Sunrise Point-H (PCH) | 127 | Sunrise Point-H (PCH) |
| 127 | Sunrise Point-LP (PCH) | 128 | Sunrise Point-LP (PCH) |
| 129 | Kaby Lake-H (PCH) | ||
| 128 | DNV (SOC) | 130 | DNV (SOC) |
| 129 | Broxton (SOC) | 131 | Broxton (SOC) |
| 130 | Lewisburg (PCH) | 132 | Lewisburg (PCH) |
diff --git a/drivers/i2c/busses/i2c-bcm2835.c b/drivers/i2c/busses/i2c-bcm2835.c index cd07a69e2e93..44deae78913e 100644 --- a/drivers/i2c/busses/i2c-bcm2835.c +++ b/drivers/i2c/busses/i2c-bcm2835.c | |||
| @@ -50,6 +50,9 @@ | |||
| 50 | #define BCM2835_I2C_S_CLKT BIT(9) | 50 | #define BCM2835_I2C_S_CLKT BIT(9) |
| 51 | #define BCM2835_I2C_S_LEN BIT(10) /* Fake bit for SW error reporting */ | 51 | #define BCM2835_I2C_S_LEN BIT(10) /* Fake bit for SW error reporting */ |
| 52 | 52 | ||
| 53 | #define BCM2835_I2C_FEDL_SHIFT 16 | ||
| 54 | #define BCM2835_I2C_REDL_SHIFT 0 | ||
| 55 | |||
| 53 | #define BCM2835_I2C_CDIV_MIN 0x0002 | 56 | #define BCM2835_I2C_CDIV_MIN 0x0002 |
| 54 | #define BCM2835_I2C_CDIV_MAX 0xFFFE | 57 | #define BCM2835_I2C_CDIV_MAX 0xFFFE |
| 55 | 58 | ||
| @@ -81,7 +84,7 @@ static inline u32 bcm2835_i2c_readl(struct bcm2835_i2c_dev *i2c_dev, u32 reg) | |||
| 81 | 84 | ||
| 82 | static int bcm2835_i2c_set_divider(struct bcm2835_i2c_dev *i2c_dev) | 85 | static int bcm2835_i2c_set_divider(struct bcm2835_i2c_dev *i2c_dev) |
| 83 | { | 86 | { |
| 84 | u32 divider; | 87 | u32 divider, redl, fedl; |
| 85 | 88 | ||
| 86 | divider = DIV_ROUND_UP(clk_get_rate(i2c_dev->clk), | 89 | divider = DIV_ROUND_UP(clk_get_rate(i2c_dev->clk), |
| 87 | i2c_dev->bus_clk_rate); | 90 | i2c_dev->bus_clk_rate); |
| @@ -100,6 +103,22 @@ static int bcm2835_i2c_set_divider(struct bcm2835_i2c_dev *i2c_dev) | |||
| 100 | 103 | ||
| 101 | bcm2835_i2c_writel(i2c_dev, BCM2835_I2C_DIV, divider); | 104 | bcm2835_i2c_writel(i2c_dev, BCM2835_I2C_DIV, divider); |
| 102 | 105 | ||
| 106 | /* | ||
| 107 | * Number of core clocks to wait after falling edge before | ||
| 108 | * outputting the next data bit. Note that both FEDL and REDL | ||
| 109 | * can't be greater than CDIV/2. | ||
| 110 | */ | ||
| 111 | fedl = max(divider / 16, 1u); | ||
| 112 | |||
| 113 | /* | ||
| 114 | * Number of core clocks to wait after rising edge before | ||
| 115 | * sampling the next incoming data bit. | ||
| 116 | */ | ||
| 117 | redl = max(divider / 4, 1u); | ||
| 118 | |||
| 119 | bcm2835_i2c_writel(i2c_dev, BCM2835_I2C_DEL, | ||
| 120 | (fedl << BCM2835_I2C_FEDL_SHIFT) | | ||
| 121 | (redl << BCM2835_I2C_REDL_SHIFT)); | ||
| 103 | return 0; | 122 | return 0; |
| 104 | } | 123 | } |
| 105 | 124 | ||
diff --git a/drivers/i2c/busses/i2c-designware-master.c b/drivers/i2c/busses/i2c-designware-master.c index ae691884d071..05732531829f 100644 --- a/drivers/i2c/busses/i2c-designware-master.c +++ b/drivers/i2c/busses/i2c-designware-master.c | |||
| @@ -209,7 +209,7 @@ static void i2c_dw_xfer_init(struct dw_i2c_dev *dev) | |||
| 209 | i2c_dw_disable_int(dev); | 209 | i2c_dw_disable_int(dev); |
| 210 | 210 | ||
| 211 | /* Enable the adapter */ | 211 | /* Enable the adapter */ |
| 212 | __i2c_dw_enable(dev, true); | 212 | __i2c_dw_enable_and_wait(dev, true); |
| 213 | 213 | ||
| 214 | /* Clear and enable interrupts */ | 214 | /* Clear and enable interrupts */ |
| 215 | dw_readl(dev, DW_IC_CLR_INTR); | 215 | dw_readl(dev, DW_IC_CLR_INTR); |
| @@ -644,7 +644,7 @@ static int i2c_dw_init_recovery_info(struct dw_i2c_dev *dev) | |||
| 644 | gpio = devm_gpiod_get(dev->dev, "scl", GPIOD_OUT_HIGH); | 644 | gpio = devm_gpiod_get(dev->dev, "scl", GPIOD_OUT_HIGH); |
| 645 | if (IS_ERR(gpio)) { | 645 | if (IS_ERR(gpio)) { |
| 646 | r = PTR_ERR(gpio); | 646 | r = PTR_ERR(gpio); |
| 647 | if (r == -ENOENT) | 647 | if (r == -ENOENT || r == -ENOSYS) |
| 648 | return 0; | 648 | return 0; |
| 649 | return r; | 649 | return r; |
| 650 | } | 650 | } |
diff --git a/drivers/i2c/busses/i2c-i801.c b/drivers/i2c/busses/i2c-i801.c index 8eac00efadc1..692b34125866 100644 --- a/drivers/i2c/busses/i2c-i801.c +++ b/drivers/i2c/busses/i2c-i801.c | |||
| @@ -58,6 +58,7 @@ | |||
| 58 | * Wildcat Point (PCH) 0x8ca2 32 hard yes yes yes | 58 | * Wildcat Point (PCH) 0x8ca2 32 hard yes yes yes |
| 59 | * Wildcat Point-LP (PCH) 0x9ca2 32 hard yes yes yes | 59 | * Wildcat Point-LP (PCH) 0x9ca2 32 hard yes yes yes |
| 60 | * BayTrail (SOC) 0x0f12 32 hard yes yes yes | 60 | * BayTrail (SOC) 0x0f12 32 hard yes yes yes |
| 61 | * Braswell (SOC) 0x2292 32 hard yes yes yes | ||
| 61 | * Sunrise Point-H (PCH) 0xa123 32 hard yes yes yes | 62 | * Sunrise Point-H (PCH) 0xa123 32 hard yes yes yes |
| 62 | * Sunrise Point-LP (PCH) 0x9d23 32 hard yes yes yes | 63 | * Sunrise Point-LP (PCH) 0x9d23 32 hard yes yes yes |
| 63 | * DNV (SOC) 0x19df 32 hard yes yes yes | 64 | * DNV (SOC) 0x19df 32 hard yes yes yes |
diff --git a/drivers/i2c/busses/i2c-sirf.c b/drivers/i2c/busses/i2c-sirf.c index 2fd8b6d00391..87197ece0f90 100644 --- a/drivers/i2c/busses/i2c-sirf.c +++ b/drivers/i2c/busses/i2c-sirf.c | |||
| @@ -341,7 +341,7 @@ static int i2c_sirfsoc_probe(struct platform_device *pdev) | |||
| 341 | platform_set_drvdata(pdev, adap); | 341 | platform_set_drvdata(pdev, adap); |
| 342 | init_completion(&siic->done); | 342 | init_completion(&siic->done); |
| 343 | 343 | ||
| 344 | /* Controller Initalisation */ | 344 | /* Controller initialisation */ |
| 345 | 345 | ||
| 346 | writel(SIRFSOC_I2C_RESET, siic->base + SIRFSOC_I2C_CTRL); | 346 | writel(SIRFSOC_I2C_RESET, siic->base + SIRFSOC_I2C_CTRL); |
| 347 | while (readl(siic->base + SIRFSOC_I2C_CTRL) & SIRFSOC_I2C_RESET) | 347 | while (readl(siic->base + SIRFSOC_I2C_CTRL) & SIRFSOC_I2C_RESET) |
| @@ -369,7 +369,7 @@ static int i2c_sirfsoc_probe(struct platform_device *pdev) | |||
| 369 | * but they start to affect the speed when clock is set to faster | 369 | * but they start to affect the speed when clock is set to faster |
| 370 | * frequencies. | 370 | * frequencies. |
| 371 | * Through the actual tests, use the different user_div value(which | 371 | * Through the actual tests, use the different user_div value(which |
| 372 | * in the divider formular 'Fio / (Fi2c * user_div)') to adapt | 372 | * in the divider formula 'Fio / (Fi2c * user_div)') to adapt |
| 373 | * the different ranges of i2c bus clock frequency, to make the SCL | 373 | * the different ranges of i2c bus clock frequency, to make the SCL |
| 374 | * more accurate. | 374 | * more accurate. |
| 375 | */ | 375 | */ |
diff --git a/drivers/iio/adc/aspeed_adc.c b/drivers/iio/adc/aspeed_adc.c index 327a49ba1991..9515ca165dfd 100644 --- a/drivers/iio/adc/aspeed_adc.c +++ b/drivers/iio/adc/aspeed_adc.c | |||
| @@ -243,7 +243,7 @@ static int aspeed_adc_probe(struct platform_device *pdev) | |||
| 243 | ASPEED_ADC_INIT_POLLING_TIME, | 243 | ASPEED_ADC_INIT_POLLING_TIME, |
| 244 | ASPEED_ADC_INIT_TIMEOUT); | 244 | ASPEED_ADC_INIT_TIMEOUT); |
| 245 | if (ret) | 245 | if (ret) |
| 246 | goto scaler_error; | 246 | goto poll_timeout_error; |
| 247 | } | 247 | } |
| 248 | 248 | ||
| 249 | /* Start all channels in normal mode. */ | 249 | /* Start all channels in normal mode. */ |
| @@ -274,9 +274,10 @@ iio_register_error: | |||
| 274 | writel(ASPEED_OPERATION_MODE_POWER_DOWN, | 274 | writel(ASPEED_OPERATION_MODE_POWER_DOWN, |
| 275 | data->base + ASPEED_REG_ENGINE_CONTROL); | 275 | data->base + ASPEED_REG_ENGINE_CONTROL); |
| 276 | clk_disable_unprepare(data->clk_scaler->clk); | 276 | clk_disable_unprepare(data->clk_scaler->clk); |
| 277 | reset_error: | ||
| 278 | reset_control_assert(data->rst); | ||
| 279 | clk_enable_error: | 277 | clk_enable_error: |
| 278 | poll_timeout_error: | ||
| 279 | reset_control_assert(data->rst); | ||
| 280 | reset_error: | ||
| 280 | clk_hw_unregister_divider(data->clk_scaler); | 281 | clk_hw_unregister_divider(data->clk_scaler); |
| 281 | scaler_error: | 282 | scaler_error: |
| 282 | clk_hw_unregister_divider(data->clk_prescaler); | 283 | clk_hw_unregister_divider(data->clk_prescaler); |
diff --git a/drivers/iio/adc/stm32-adc.c b/drivers/iio/adc/stm32-adc.c index 7f5def465340..9a2583caedaa 100644 --- a/drivers/iio/adc/stm32-adc.c +++ b/drivers/iio/adc/stm32-adc.c | |||
| @@ -722,8 +722,6 @@ static int stm32h7_adc_enable(struct stm32_adc *adc) | |||
| 722 | int ret; | 722 | int ret; |
| 723 | u32 val; | 723 | u32 val; |
| 724 | 724 | ||
| 725 | /* Clear ADRDY by writing one, then enable ADC */ | ||
| 726 | stm32_adc_set_bits(adc, STM32H7_ADC_ISR, STM32H7_ADRDY); | ||
| 727 | stm32_adc_set_bits(adc, STM32H7_ADC_CR, STM32H7_ADEN); | 725 | stm32_adc_set_bits(adc, STM32H7_ADC_CR, STM32H7_ADEN); |
| 728 | 726 | ||
| 729 | /* Poll for ADRDY to be set (after adc startup time) */ | 727 | /* Poll for ADRDY to be set (after adc startup time) */ |
| @@ -731,8 +729,11 @@ static int stm32h7_adc_enable(struct stm32_adc *adc) | |||
| 731 | val & STM32H7_ADRDY, | 729 | val & STM32H7_ADRDY, |
| 732 | 100, STM32_ADC_TIMEOUT_US); | 730 | 100, STM32_ADC_TIMEOUT_US); |
| 733 | if (ret) { | 731 | if (ret) { |
| 734 | stm32_adc_clr_bits(adc, STM32H7_ADC_CR, STM32H7_ADEN); | 732 | stm32_adc_set_bits(adc, STM32H7_ADC_CR, STM32H7_ADDIS); |
| 735 | dev_err(&indio_dev->dev, "Failed to enable ADC\n"); | 733 | dev_err(&indio_dev->dev, "Failed to enable ADC\n"); |
| 734 | } else { | ||
| 735 | /* Clear ADRDY by writing one */ | ||
| 736 | stm32_adc_set_bits(adc, STM32H7_ADC_ISR, STM32H7_ADRDY); | ||
| 736 | } | 737 | } |
| 737 | 738 | ||
| 738 | return ret; | 739 | return ret; |
diff --git a/drivers/iio/imu/adis_trigger.c b/drivers/iio/imu/adis_trigger.c index 0dd5a381be64..457372f36791 100644 --- a/drivers/iio/imu/adis_trigger.c +++ b/drivers/iio/imu/adis_trigger.c | |||
| @@ -46,6 +46,10 @@ int adis_probe_trigger(struct adis *adis, struct iio_dev *indio_dev) | |||
| 46 | if (adis->trig == NULL) | 46 | if (adis->trig == NULL) |
| 47 | return -ENOMEM; | 47 | return -ENOMEM; |
| 48 | 48 | ||
| 49 | adis->trig->dev.parent = &adis->spi->dev; | ||
| 50 | adis->trig->ops = &adis_trigger_ops; | ||
| 51 | iio_trigger_set_drvdata(adis->trig, adis); | ||
| 52 | |||
| 49 | ret = request_irq(adis->spi->irq, | 53 | ret = request_irq(adis->spi->irq, |
| 50 | &iio_trigger_generic_data_rdy_poll, | 54 | &iio_trigger_generic_data_rdy_poll, |
| 51 | IRQF_TRIGGER_RISING, | 55 | IRQF_TRIGGER_RISING, |
| @@ -54,9 +58,6 @@ int adis_probe_trigger(struct adis *adis, struct iio_dev *indio_dev) | |||
| 54 | if (ret) | 58 | if (ret) |
| 55 | goto error_free_trig; | 59 | goto error_free_trig; |
| 56 | 60 | ||
| 57 | adis->trig->dev.parent = &adis->spi->dev; | ||
| 58 | adis->trig->ops = &adis_trigger_ops; | ||
| 59 | iio_trigger_set_drvdata(adis->trig, adis); | ||
| 60 | ret = iio_trigger_register(adis->trig); | 61 | ret = iio_trigger_register(adis->trig); |
| 61 | 62 | ||
| 62 | indio_dev->trig = iio_trigger_get(adis->trig); | 63 | indio_dev->trig = iio_trigger_get(adis->trig); |
diff --git a/drivers/iio/industrialio-buffer.c b/drivers/iio/industrialio-buffer.c index 79abf70a126d..cd5bfe39591b 100644 --- a/drivers/iio/industrialio-buffer.c +++ b/drivers/iio/industrialio-buffer.c | |||
| @@ -175,7 +175,7 @@ __poll_t iio_buffer_poll(struct file *filp, | |||
| 175 | struct iio_dev *indio_dev = filp->private_data; | 175 | struct iio_dev *indio_dev = filp->private_data; |
| 176 | struct iio_buffer *rb = indio_dev->buffer; | 176 | struct iio_buffer *rb = indio_dev->buffer; |
| 177 | 177 | ||
| 178 | if (!indio_dev->info) | 178 | if (!indio_dev->info || rb == NULL) |
| 179 | return 0; | 179 | return 0; |
| 180 | 180 | ||
| 181 | poll_wait(filp, &rb->pollq, wait); | 181 | poll_wait(filp, &rb->pollq, wait); |
diff --git a/drivers/iio/proximity/Kconfig b/drivers/iio/proximity/Kconfig index fcb1c4ba5e41..f726f9427602 100644 --- a/drivers/iio/proximity/Kconfig +++ b/drivers/iio/proximity/Kconfig | |||
| @@ -68,6 +68,8 @@ config SX9500 | |||
| 68 | 68 | ||
| 69 | config SRF08 | 69 | config SRF08 |
| 70 | tristate "Devantech SRF02/SRF08/SRF10 ultrasonic ranger sensor" | 70 | tristate "Devantech SRF02/SRF08/SRF10 ultrasonic ranger sensor" |
| 71 | select IIO_BUFFER | ||
| 72 | select IIO_TRIGGERED_BUFFER | ||
| 71 | depends on I2C | 73 | depends on I2C |
| 72 | help | 74 | help |
| 73 | Say Y here to build a driver for Devantech SRF02/SRF08/SRF10 | 75 | Say Y here to build a driver for Devantech SRF02/SRF08/SRF10 |
diff --git a/drivers/infiniband/core/core_priv.h b/drivers/infiniband/core/core_priv.h index c4560d84dfae..25bb178f6074 100644 --- a/drivers/infiniband/core/core_priv.h +++ b/drivers/infiniband/core/core_priv.h | |||
| @@ -305,16 +305,21 @@ void nldev_exit(void); | |||
| 305 | static inline struct ib_qp *_ib_create_qp(struct ib_device *dev, | 305 | static inline struct ib_qp *_ib_create_qp(struct ib_device *dev, |
| 306 | struct ib_pd *pd, | 306 | struct ib_pd *pd, |
| 307 | struct ib_qp_init_attr *attr, | 307 | struct ib_qp_init_attr *attr, |
| 308 | struct ib_udata *udata) | 308 | struct ib_udata *udata, |
| 309 | struct ib_uobject *uobj) | ||
| 309 | { | 310 | { |
| 310 | struct ib_qp *qp; | 311 | struct ib_qp *qp; |
| 311 | 312 | ||
| 313 | if (!dev->create_qp) | ||
| 314 | return ERR_PTR(-EOPNOTSUPP); | ||
| 315 | |||
| 312 | qp = dev->create_qp(pd, attr, udata); | 316 | qp = dev->create_qp(pd, attr, udata); |
| 313 | if (IS_ERR(qp)) | 317 | if (IS_ERR(qp)) |
| 314 | return qp; | 318 | return qp; |
| 315 | 319 | ||
| 316 | qp->device = dev; | 320 | qp->device = dev; |
| 317 | qp->pd = pd; | 321 | qp->pd = pd; |
| 322 | qp->uobject = uobj; | ||
| 318 | /* | 323 | /* |
| 319 | * We don't track XRC QPs for now, because they don't have PD | 324 | * We don't track XRC QPs for now, because they don't have PD |
| 320 | * and more importantly they are created internaly by driver, | 325 | * and more importantly they are created internaly by driver, |
diff --git a/drivers/infiniband/core/rdma_core.c b/drivers/infiniband/core/rdma_core.c index 85b5ee4defa4..d8eead5d106d 100644 --- a/drivers/infiniband/core/rdma_core.c +++ b/drivers/infiniband/core/rdma_core.c | |||
| @@ -141,7 +141,12 @@ static struct ib_uobject *alloc_uobj(struct ib_ucontext *context, | |||
| 141 | */ | 141 | */ |
| 142 | uobj->context = context; | 142 | uobj->context = context; |
| 143 | uobj->type = type; | 143 | uobj->type = type; |
| 144 | atomic_set(&uobj->usecnt, 0); | 144 | /* |
| 145 | * Allocated objects start out as write locked to deny any other | ||
| 146 | * syscalls from accessing them until they are committed. See | ||
| 147 | * rdma_alloc_commit_uobject | ||
| 148 | */ | ||
| 149 | atomic_set(&uobj->usecnt, -1); | ||
| 145 | kref_init(&uobj->ref); | 150 | kref_init(&uobj->ref); |
| 146 | 151 | ||
| 147 | return uobj; | 152 | return uobj; |
| @@ -196,7 +201,15 @@ static struct ib_uobject *lookup_get_idr_uobject(const struct uverbs_obj_type *t | |||
| 196 | goto free; | 201 | goto free; |
| 197 | } | 202 | } |
| 198 | 203 | ||
| 199 | uverbs_uobject_get(uobj); | 204 | /* |
| 205 | * The idr_find is guaranteed to return a pointer to something that | ||
| 206 | * isn't freed yet, or NULL, as the free after idr_remove goes through | ||
| 207 | * kfree_rcu(). However the object may still have been released and | ||
| 208 | * kfree() could be called at any time. | ||
| 209 | */ | ||
| 210 | if (!kref_get_unless_zero(&uobj->ref)) | ||
| 211 | uobj = ERR_PTR(-ENOENT); | ||
| 212 | |||
| 200 | free: | 213 | free: |
| 201 | rcu_read_unlock(); | 214 | rcu_read_unlock(); |
| 202 | return uobj; | 215 | return uobj; |
| @@ -399,13 +412,13 @@ static int __must_check remove_commit_fd_uobject(struct ib_uobject *uobj, | |||
| 399 | return ret; | 412 | return ret; |
| 400 | } | 413 | } |
| 401 | 414 | ||
| 402 | static void lockdep_check(struct ib_uobject *uobj, bool exclusive) | 415 | static void assert_uverbs_usecnt(struct ib_uobject *uobj, bool exclusive) |
| 403 | { | 416 | { |
| 404 | #ifdef CONFIG_LOCKDEP | 417 | #ifdef CONFIG_LOCKDEP |
| 405 | if (exclusive) | 418 | if (exclusive) |
| 406 | WARN_ON(atomic_read(&uobj->usecnt) > 0); | 419 | WARN_ON(atomic_read(&uobj->usecnt) != -1); |
| 407 | else | 420 | else |
| 408 | WARN_ON(atomic_read(&uobj->usecnt) == -1); | 421 | WARN_ON(atomic_read(&uobj->usecnt) <= 0); |
| 409 | #endif | 422 | #endif |
| 410 | } | 423 | } |
| 411 | 424 | ||
| @@ -444,7 +457,7 @@ int __must_check rdma_remove_commit_uobject(struct ib_uobject *uobj) | |||
| 444 | WARN(true, "ib_uverbs: Cleanup is running while removing an uobject\n"); | 457 | WARN(true, "ib_uverbs: Cleanup is running while removing an uobject\n"); |
| 445 | return 0; | 458 | return 0; |
| 446 | } | 459 | } |
| 447 | lockdep_check(uobj, true); | 460 | assert_uverbs_usecnt(uobj, true); |
| 448 | ret = _rdma_remove_commit_uobject(uobj, RDMA_REMOVE_DESTROY); | 461 | ret = _rdma_remove_commit_uobject(uobj, RDMA_REMOVE_DESTROY); |
| 449 | 462 | ||
| 450 | up_read(&ucontext->cleanup_rwsem); | 463 | up_read(&ucontext->cleanup_rwsem); |
| @@ -474,16 +487,17 @@ int rdma_explicit_destroy(struct ib_uobject *uobject) | |||
| 474 | WARN(true, "ib_uverbs: Cleanup is running while removing an uobject\n"); | 487 | WARN(true, "ib_uverbs: Cleanup is running while removing an uobject\n"); |
| 475 | return 0; | 488 | return 0; |
| 476 | } | 489 | } |
| 477 | lockdep_check(uobject, true); | 490 | assert_uverbs_usecnt(uobject, true); |
| 478 | ret = uobject->type->type_class->remove_commit(uobject, | 491 | ret = uobject->type->type_class->remove_commit(uobject, |
| 479 | RDMA_REMOVE_DESTROY); | 492 | RDMA_REMOVE_DESTROY); |
| 480 | if (ret) | 493 | if (ret) |
| 481 | return ret; | 494 | goto out; |
| 482 | 495 | ||
| 483 | uobject->type = &null_obj_type; | 496 | uobject->type = &null_obj_type; |
| 484 | 497 | ||
| 498 | out: | ||
| 485 | up_read(&ucontext->cleanup_rwsem); | 499 | up_read(&ucontext->cleanup_rwsem); |
| 486 | return 0; | 500 | return ret; |
| 487 | } | 501 | } |
| 488 | 502 | ||
| 489 | static void alloc_commit_idr_uobject(struct ib_uobject *uobj) | 503 | static void alloc_commit_idr_uobject(struct ib_uobject *uobj) |
| @@ -527,6 +541,10 @@ int rdma_alloc_commit_uobject(struct ib_uobject *uobj) | |||
| 527 | return ret; | 541 | return ret; |
| 528 | } | 542 | } |
| 529 | 543 | ||
| 544 | /* matches atomic_set(-1) in alloc_uobj */ | ||
| 545 | assert_uverbs_usecnt(uobj, true); | ||
| 546 | atomic_set(&uobj->usecnt, 0); | ||
| 547 | |||
| 530 | uobj->type->type_class->alloc_commit(uobj); | 548 | uobj->type->type_class->alloc_commit(uobj); |
| 531 | up_read(&uobj->context->cleanup_rwsem); | 549 | up_read(&uobj->context->cleanup_rwsem); |
| 532 | 550 | ||
| @@ -561,7 +579,7 @@ static void lookup_put_fd_uobject(struct ib_uobject *uobj, bool exclusive) | |||
| 561 | 579 | ||
| 562 | void rdma_lookup_put_uobject(struct ib_uobject *uobj, bool exclusive) | 580 | void rdma_lookup_put_uobject(struct ib_uobject *uobj, bool exclusive) |
| 563 | { | 581 | { |
| 564 | lockdep_check(uobj, exclusive); | 582 | assert_uverbs_usecnt(uobj, exclusive); |
| 565 | uobj->type->type_class->lookup_put(uobj, exclusive); | 583 | uobj->type->type_class->lookup_put(uobj, exclusive); |
| 566 | /* | 584 | /* |
| 567 | * In order to unlock an object, either decrease its usecnt for | 585 | * In order to unlock an object, either decrease its usecnt for |
diff --git a/drivers/infiniband/core/restrack.c b/drivers/infiniband/core/restrack.c index 857637bf46da..3dbc4e4cca41 100644 --- a/drivers/infiniband/core/restrack.c +++ b/drivers/infiniband/core/restrack.c | |||
| @@ -7,7 +7,6 @@ | |||
| 7 | #include <rdma/restrack.h> | 7 | #include <rdma/restrack.h> |
| 8 | #include <linux/mutex.h> | 8 | #include <linux/mutex.h> |
| 9 | #include <linux/sched/task.h> | 9 | #include <linux/sched/task.h> |
| 10 | #include <linux/uaccess.h> | ||
| 11 | #include <linux/pid_namespace.h> | 10 | #include <linux/pid_namespace.h> |
| 12 | 11 | ||
| 13 | void rdma_restrack_init(struct rdma_restrack_root *res) | 12 | void rdma_restrack_init(struct rdma_restrack_root *res) |
| @@ -63,7 +62,6 @@ static struct ib_device *res_to_dev(struct rdma_restrack_entry *res) | |||
| 63 | { | 62 | { |
| 64 | enum rdma_restrack_type type = res->type; | 63 | enum rdma_restrack_type type = res->type; |
| 65 | struct ib_device *dev; | 64 | struct ib_device *dev; |
| 66 | struct ib_xrcd *xrcd; | ||
| 67 | struct ib_pd *pd; | 65 | struct ib_pd *pd; |
| 68 | struct ib_cq *cq; | 66 | struct ib_cq *cq; |
| 69 | struct ib_qp *qp; | 67 | struct ib_qp *qp; |
| @@ -81,10 +79,6 @@ static struct ib_device *res_to_dev(struct rdma_restrack_entry *res) | |||
| 81 | qp = container_of(res, struct ib_qp, res); | 79 | qp = container_of(res, struct ib_qp, res); |
| 82 | dev = qp->device; | 80 | dev = qp->device; |
| 83 | break; | 81 | break; |
| 84 | case RDMA_RESTRACK_XRCD: | ||
| 85 | xrcd = container_of(res, struct ib_xrcd, res); | ||
| 86 | dev = xrcd->device; | ||
| 87 | break; | ||
| 88 | default: | 82 | default: |
| 89 | WARN_ONCE(true, "Wrong resource tracking type %u\n", type); | 83 | WARN_ONCE(true, "Wrong resource tracking type %u\n", type); |
| 90 | return NULL; | 84 | return NULL; |
| @@ -93,6 +87,21 @@ static struct ib_device *res_to_dev(struct rdma_restrack_entry *res) | |||
| 93 | return dev; | 87 | return dev; |
| 94 | } | 88 | } |
| 95 | 89 | ||
| 90 | static bool res_is_user(struct rdma_restrack_entry *res) | ||
| 91 | { | ||
| 92 | switch (res->type) { | ||
| 93 | case RDMA_RESTRACK_PD: | ||
| 94 | return container_of(res, struct ib_pd, res)->uobject; | ||
| 95 | case RDMA_RESTRACK_CQ: | ||
| 96 | return container_of(res, struct ib_cq, res)->uobject; | ||
| 97 | case RDMA_RESTRACK_QP: | ||
| 98 | return container_of(res, struct ib_qp, res)->uobject; | ||
| 99 | default: | ||
| 100 | WARN_ONCE(true, "Wrong resource tracking type %u\n", res->type); | ||
| 101 | return false; | ||
| 102 | } | ||
| 103 | } | ||
| 104 | |||
| 96 | void rdma_restrack_add(struct rdma_restrack_entry *res) | 105 | void rdma_restrack_add(struct rdma_restrack_entry *res) |
| 97 | { | 106 | { |
| 98 | struct ib_device *dev = res_to_dev(res); | 107 | struct ib_device *dev = res_to_dev(res); |
| @@ -100,7 +109,7 @@ void rdma_restrack_add(struct rdma_restrack_entry *res) | |||
| 100 | if (!dev) | 109 | if (!dev) |
| 101 | return; | 110 | return; |
| 102 | 111 | ||
| 103 | if (!uaccess_kernel()) { | 112 | if (res_is_user(res)) { |
| 104 | get_task_struct(current); | 113 | get_task_struct(current); |
| 105 | res->task = current; | 114 | res->task = current; |
| 106 | res->kern_name = NULL; | 115 | res->kern_name = NULL; |
diff --git a/drivers/infiniband/core/uverbs_cmd.c b/drivers/infiniband/core/uverbs_cmd.c index 256934d1f64f..a148de35df8d 100644 --- a/drivers/infiniband/core/uverbs_cmd.c +++ b/drivers/infiniband/core/uverbs_cmd.c | |||
| @@ -562,9 +562,10 @@ ssize_t ib_uverbs_open_xrcd(struct ib_uverbs_file *file, | |||
| 562 | if (f.file) | 562 | if (f.file) |
| 563 | fdput(f); | 563 | fdput(f); |
| 564 | 564 | ||
| 565 | mutex_unlock(&file->device->xrcd_tree_mutex); | ||
| 566 | |||
| 565 | uobj_alloc_commit(&obj->uobject); | 567 | uobj_alloc_commit(&obj->uobject); |
| 566 | 568 | ||
| 567 | mutex_unlock(&file->device->xrcd_tree_mutex); | ||
| 568 | return in_len; | 569 | return in_len; |
| 569 | 570 | ||
| 570 | err_copy: | 571 | err_copy: |
| @@ -603,10 +604,8 @@ ssize_t ib_uverbs_close_xrcd(struct ib_uverbs_file *file, | |||
| 603 | 604 | ||
| 604 | uobj = uobj_get_write(uobj_get_type(xrcd), cmd.xrcd_handle, | 605 | uobj = uobj_get_write(uobj_get_type(xrcd), cmd.xrcd_handle, |
| 605 | file->ucontext); | 606 | file->ucontext); |
| 606 | if (IS_ERR(uobj)) { | 607 | if (IS_ERR(uobj)) |
| 607 | mutex_unlock(&file->device->xrcd_tree_mutex); | ||
| 608 | return PTR_ERR(uobj); | 608 | return PTR_ERR(uobj); |
| 609 | } | ||
| 610 | 609 | ||
| 611 | ret = uobj_remove_commit(uobj); | 610 | ret = uobj_remove_commit(uobj); |
| 612 | return ret ?: in_len; | 611 | return ret ?: in_len; |
| @@ -979,6 +978,9 @@ static struct ib_ucq_object *create_cq(struct ib_uverbs_file *file, | |||
| 979 | struct ib_uverbs_ex_create_cq_resp resp; | 978 | struct ib_uverbs_ex_create_cq_resp resp; |
| 980 | struct ib_cq_init_attr attr = {}; | 979 | struct ib_cq_init_attr attr = {}; |
| 981 | 980 | ||
| 981 | if (!ib_dev->create_cq) | ||
| 982 | return ERR_PTR(-EOPNOTSUPP); | ||
| 983 | |||
| 982 | if (cmd->comp_vector >= file->device->num_comp_vectors) | 984 | if (cmd->comp_vector >= file->device->num_comp_vectors) |
| 983 | return ERR_PTR(-EINVAL); | 985 | return ERR_PTR(-EINVAL); |
| 984 | 986 | ||
| @@ -1030,14 +1032,14 @@ static struct ib_ucq_object *create_cq(struct ib_uverbs_file *file, | |||
| 1030 | resp.response_length = offsetof(typeof(resp), response_length) + | 1032 | resp.response_length = offsetof(typeof(resp), response_length) + |
| 1031 | sizeof(resp.response_length); | 1033 | sizeof(resp.response_length); |
| 1032 | 1034 | ||
| 1035 | cq->res.type = RDMA_RESTRACK_CQ; | ||
| 1036 | rdma_restrack_add(&cq->res); | ||
| 1037 | |||
| 1033 | ret = cb(file, obj, &resp, ucore, context); | 1038 | ret = cb(file, obj, &resp, ucore, context); |
| 1034 | if (ret) | 1039 | if (ret) |
| 1035 | goto err_cb; | 1040 | goto err_cb; |
| 1036 | 1041 | ||
| 1037 | uobj_alloc_commit(&obj->uobject); | 1042 | uobj_alloc_commit(&obj->uobject); |
| 1038 | cq->res.type = RDMA_RESTRACK_CQ; | ||
| 1039 | rdma_restrack_add(&cq->res); | ||
| 1040 | |||
| 1041 | return obj; | 1043 | return obj; |
| 1042 | 1044 | ||
| 1043 | err_cb: | 1045 | err_cb: |
| @@ -1518,7 +1520,8 @@ static int create_qp(struct ib_uverbs_file *file, | |||
| 1518 | if (cmd->qp_type == IB_QPT_XRC_TGT) | 1520 | if (cmd->qp_type == IB_QPT_XRC_TGT) |
| 1519 | qp = ib_create_qp(pd, &attr); | 1521 | qp = ib_create_qp(pd, &attr); |
| 1520 | else | 1522 | else |
| 1521 | qp = _ib_create_qp(device, pd, &attr, uhw); | 1523 | qp = _ib_create_qp(device, pd, &attr, uhw, |
| 1524 | &obj->uevent.uobject); | ||
| 1522 | 1525 | ||
| 1523 | if (IS_ERR(qp)) { | 1526 | if (IS_ERR(qp)) { |
| 1524 | ret = PTR_ERR(qp); | 1527 | ret = PTR_ERR(qp); |
| @@ -1550,8 +1553,10 @@ static int create_qp(struct ib_uverbs_file *file, | |||
| 1550 | atomic_inc(&attr.srq->usecnt); | 1553 | atomic_inc(&attr.srq->usecnt); |
| 1551 | if (ind_tbl) | 1554 | if (ind_tbl) |
| 1552 | atomic_inc(&ind_tbl->usecnt); | 1555 | atomic_inc(&ind_tbl->usecnt); |
| 1556 | } else { | ||
| 1557 | /* It is done in _ib_create_qp for other QP types */ | ||
| 1558 | qp->uobject = &obj->uevent.uobject; | ||
| 1553 | } | 1559 | } |
| 1554 | qp->uobject = &obj->uevent.uobject; | ||
| 1555 | 1560 | ||
| 1556 | obj->uevent.uobject.object = qp; | 1561 | obj->uevent.uobject.object = qp; |
| 1557 | 1562 | ||
| @@ -1971,8 +1976,15 @@ static int modify_qp(struct ib_uverbs_file *file, | |||
| 1971 | goto release_qp; | 1976 | goto release_qp; |
| 1972 | } | 1977 | } |
| 1973 | 1978 | ||
| 1979 | if ((cmd->base.attr_mask & IB_QP_AV) && | ||
| 1980 | !rdma_is_port_valid(qp->device, cmd->base.dest.port_num)) { | ||
| 1981 | ret = -EINVAL; | ||
| 1982 | goto release_qp; | ||
| 1983 | } | ||
| 1984 | |||
| 1974 | if ((cmd->base.attr_mask & IB_QP_ALT_PATH) && | 1985 | if ((cmd->base.attr_mask & IB_QP_ALT_PATH) && |
| 1975 | !rdma_is_port_valid(qp->device, cmd->base.alt_port_num)) { | 1986 | (!rdma_is_port_valid(qp->device, cmd->base.alt_port_num) || |
| 1987 | !rdma_is_port_valid(qp->device, cmd->base.alt_dest.port_num))) { | ||
| 1976 | ret = -EINVAL; | 1988 | ret = -EINVAL; |
| 1977 | goto release_qp; | 1989 | goto release_qp; |
| 1978 | } | 1990 | } |
| @@ -2941,6 +2953,11 @@ int ib_uverbs_ex_create_wq(struct ib_uverbs_file *file, | |||
| 2941 | wq_init_attr.create_flags = cmd.create_flags; | 2953 | wq_init_attr.create_flags = cmd.create_flags; |
| 2942 | obj->uevent.events_reported = 0; | 2954 | obj->uevent.events_reported = 0; |
| 2943 | INIT_LIST_HEAD(&obj->uevent.event_list); | 2955 | INIT_LIST_HEAD(&obj->uevent.event_list); |
| 2956 | |||
| 2957 | if (!pd->device->create_wq) { | ||
| 2958 | err = -EOPNOTSUPP; | ||
| 2959 | goto err_put_cq; | ||
| 2960 | } | ||
| 2944 | wq = pd->device->create_wq(pd, &wq_init_attr, uhw); | 2961 | wq = pd->device->create_wq(pd, &wq_init_attr, uhw); |
| 2945 | if (IS_ERR(wq)) { | 2962 | if (IS_ERR(wq)) { |
| 2946 | err = PTR_ERR(wq); | 2963 | err = PTR_ERR(wq); |
| @@ -3084,7 +3101,12 @@ int ib_uverbs_ex_modify_wq(struct ib_uverbs_file *file, | |||
| 3084 | wq_attr.flags = cmd.flags; | 3101 | wq_attr.flags = cmd.flags; |
| 3085 | wq_attr.flags_mask = cmd.flags_mask; | 3102 | wq_attr.flags_mask = cmd.flags_mask; |
| 3086 | } | 3103 | } |
| 3104 | if (!wq->device->modify_wq) { | ||
| 3105 | ret = -EOPNOTSUPP; | ||
| 3106 | goto out; | ||
| 3107 | } | ||
| 3087 | ret = wq->device->modify_wq(wq, &wq_attr, cmd.attr_mask, uhw); | 3108 | ret = wq->device->modify_wq(wq, &wq_attr, cmd.attr_mask, uhw); |
| 3109 | out: | ||
| 3088 | uobj_put_obj_read(wq); | 3110 | uobj_put_obj_read(wq); |
| 3089 | return ret; | 3111 | return ret; |
| 3090 | } | 3112 | } |
| @@ -3181,6 +3203,11 @@ int ib_uverbs_ex_create_rwq_ind_table(struct ib_uverbs_file *file, | |||
| 3181 | 3203 | ||
| 3182 | init_attr.log_ind_tbl_size = cmd.log_ind_tbl_size; | 3204 | init_attr.log_ind_tbl_size = cmd.log_ind_tbl_size; |
| 3183 | init_attr.ind_tbl = wqs; | 3205 | init_attr.ind_tbl = wqs; |
| 3206 | |||
| 3207 | if (!ib_dev->create_rwq_ind_table) { | ||
| 3208 | err = -EOPNOTSUPP; | ||
| 3209 | goto err_uobj; | ||
| 3210 | } | ||
| 3184 | rwq_ind_tbl = ib_dev->create_rwq_ind_table(ib_dev, &init_attr, uhw); | 3211 | rwq_ind_tbl = ib_dev->create_rwq_ind_table(ib_dev, &init_attr, uhw); |
| 3185 | 3212 | ||
| 3186 | if (IS_ERR(rwq_ind_tbl)) { | 3213 | if (IS_ERR(rwq_ind_tbl)) { |
| @@ -3770,6 +3797,9 @@ int ib_uverbs_ex_query_device(struct ib_uverbs_file *file, | |||
| 3770 | struct ib_device_attr attr = {0}; | 3797 | struct ib_device_attr attr = {0}; |
| 3771 | int err; | 3798 | int err; |
| 3772 | 3799 | ||
| 3800 | if (!ib_dev->query_device) | ||
| 3801 | return -EOPNOTSUPP; | ||
| 3802 | |||
| 3773 | if (ucore->inlen < sizeof(cmd)) | 3803 | if (ucore->inlen < sizeof(cmd)) |
| 3774 | return -EINVAL; | 3804 | return -EINVAL; |
| 3775 | 3805 | ||
diff --git a/drivers/infiniband/core/uverbs_ioctl.c b/drivers/infiniband/core/uverbs_ioctl.c index d96dc1d17be1..339b85145044 100644 --- a/drivers/infiniband/core/uverbs_ioctl.c +++ b/drivers/infiniband/core/uverbs_ioctl.c | |||
| @@ -59,6 +59,9 @@ static int uverbs_process_attr(struct ib_device *ibdev, | |||
| 59 | return 0; | 59 | return 0; |
| 60 | } | 60 | } |
| 61 | 61 | ||
| 62 | if (test_bit(attr_id, attr_bundle_h->valid_bitmap)) | ||
| 63 | return -EINVAL; | ||
| 64 | |||
| 62 | spec = &attr_spec_bucket->attrs[attr_id]; | 65 | spec = &attr_spec_bucket->attrs[attr_id]; |
| 63 | e = &elements[attr_id]; | 66 | e = &elements[attr_id]; |
| 64 | e->uattr = uattr_ptr; | 67 | e->uattr = uattr_ptr; |
diff --git a/drivers/infiniband/core/uverbs_ioctl_merge.c b/drivers/infiniband/core/uverbs_ioctl_merge.c index 062485f9300d..62e1eb1d2a28 100644 --- a/drivers/infiniband/core/uverbs_ioctl_merge.c +++ b/drivers/infiniband/core/uverbs_ioctl_merge.c | |||
| @@ -114,6 +114,7 @@ static size_t get_elements_above_id(const void **iters, | |||
| 114 | short min = SHRT_MAX; | 114 | short min = SHRT_MAX; |
| 115 | const void *elem; | 115 | const void *elem; |
| 116 | int i, j, last_stored = -1; | 116 | int i, j, last_stored = -1; |
| 117 | unsigned int equal_min = 0; | ||
| 117 | 118 | ||
| 118 | for_each_element(elem, i, j, elements, num_elements, num_offset, | 119 | for_each_element(elem, i, j, elements, num_elements, num_offset, |
| 119 | data_offset) { | 120 | data_offset) { |
| @@ -136,6 +137,10 @@ static size_t get_elements_above_id(const void **iters, | |||
| 136 | */ | 137 | */ |
| 137 | iters[last_stored == i ? num_iters - 1 : num_iters++] = elem; | 138 | iters[last_stored == i ? num_iters - 1 : num_iters++] = elem; |
| 138 | last_stored = i; | 139 | last_stored = i; |
| 140 | if (min == GET_ID(id)) | ||
| 141 | equal_min++; | ||
| 142 | else | ||
| 143 | equal_min = 1; | ||
| 139 | min = GET_ID(id); | 144 | min = GET_ID(id); |
| 140 | } | 145 | } |
| 141 | 146 | ||
| @@ -146,15 +151,10 @@ static size_t get_elements_above_id(const void **iters, | |||
| 146 | * Therefore, we need to clean the beginning of the array to make sure | 151 | * Therefore, we need to clean the beginning of the array to make sure |
| 147 | * all ids of final elements are equal to min. | 152 | * all ids of final elements are equal to min. |
| 148 | */ | 153 | */ |
| 149 | for (i = num_iters - 1; i >= 0 && | 154 | memmove(iters, iters + num_iters - equal_min, sizeof(*iters) * equal_min); |
| 150 | GET_ID(*(u16 *)(iters[i] + id_offset)) == min; i--) | ||
| 151 | ; | ||
| 152 | |||
| 153 | num_iters -= i + 1; | ||
| 154 | memmove(iters, iters + i + 1, sizeof(*iters) * num_iters); | ||
| 155 | 155 | ||
| 156 | *min_id = min; | 156 | *min_id = min; |
| 157 | return num_iters; | 157 | return equal_min; |
| 158 | } | 158 | } |
| 159 | 159 | ||
| 160 | #define find_max_element_entry_id(num_elements, elements, num_objects_fld, \ | 160 | #define find_max_element_entry_id(num_elements, elements, num_objects_fld, \ |
| @@ -322,7 +322,7 @@ static struct uverbs_method_spec *build_method_with_attrs(const struct uverbs_me | |||
| 322 | hash = kzalloc(sizeof(*hash) + | 322 | hash = kzalloc(sizeof(*hash) + |
| 323 | ALIGN(sizeof(*hash->attrs) * (attr_max_bucket + 1), | 323 | ALIGN(sizeof(*hash->attrs) * (attr_max_bucket + 1), |
| 324 | sizeof(long)) + | 324 | sizeof(long)) + |
| 325 | BITS_TO_LONGS(attr_max_bucket) * sizeof(long), | 325 | BITS_TO_LONGS(attr_max_bucket + 1) * sizeof(long), |
| 326 | GFP_KERNEL); | 326 | GFP_KERNEL); |
| 327 | if (!hash) { | 327 | if (!hash) { |
| 328 | res = -ENOMEM; | 328 | res = -ENOMEM; |
| @@ -509,7 +509,7 @@ static struct uverbs_object_spec *build_object_with_methods(const struct uverbs_ | |||
| 509 | * first handler which != NULL. This also defines the | 509 | * first handler which != NULL. This also defines the |
| 510 | * set of flags used for this handler. | 510 | * set of flags used for this handler. |
| 511 | */ | 511 | */ |
| 512 | for (i = num_object_defs - 1; | 512 | for (i = num_method_defs - 1; |
| 513 | i >= 0 && !method_defs[i]->handler; i--) | 513 | i >= 0 && !method_defs[i]->handler; i--) |
| 514 | ; | 514 | ; |
| 515 | hash->methods[min_id++] = method; | 515 | hash->methods[min_id++] = method; |
diff --git a/drivers/infiniband/core/uverbs_main.c b/drivers/infiniband/core/uverbs_main.c index 395a3b091229..b1ca223aa380 100644 --- a/drivers/infiniband/core/uverbs_main.c +++ b/drivers/infiniband/core/uverbs_main.c | |||
| @@ -650,12 +650,21 @@ static int verify_command_mask(struct ib_device *ib_dev, __u32 command) | |||
| 650 | return -1; | 650 | return -1; |
| 651 | } | 651 | } |
| 652 | 652 | ||
| 653 | static bool verify_command_idx(u32 command, bool extended) | ||
| 654 | { | ||
| 655 | if (extended) | ||
| 656 | return command < ARRAY_SIZE(uverbs_ex_cmd_table); | ||
| 657 | |||
| 658 | return command < ARRAY_SIZE(uverbs_cmd_table); | ||
| 659 | } | ||
| 660 | |||
| 653 | static ssize_t ib_uverbs_write(struct file *filp, const char __user *buf, | 661 | static ssize_t ib_uverbs_write(struct file *filp, const char __user *buf, |
| 654 | size_t count, loff_t *pos) | 662 | size_t count, loff_t *pos) |
| 655 | { | 663 | { |
| 656 | struct ib_uverbs_file *file = filp->private_data; | 664 | struct ib_uverbs_file *file = filp->private_data; |
| 657 | struct ib_device *ib_dev; | 665 | struct ib_device *ib_dev; |
| 658 | struct ib_uverbs_cmd_hdr hdr; | 666 | struct ib_uverbs_cmd_hdr hdr; |
| 667 | bool extended_command; | ||
| 659 | __u32 command; | 668 | __u32 command; |
| 660 | __u32 flags; | 669 | __u32 flags; |
| 661 | int srcu_key; | 670 | int srcu_key; |
| @@ -688,6 +697,15 @@ static ssize_t ib_uverbs_write(struct file *filp, const char __user *buf, | |||
| 688 | } | 697 | } |
| 689 | 698 | ||
| 690 | command = hdr.command & IB_USER_VERBS_CMD_COMMAND_MASK; | 699 | command = hdr.command & IB_USER_VERBS_CMD_COMMAND_MASK; |
| 700 | flags = (hdr.command & | ||
| 701 | IB_USER_VERBS_CMD_FLAGS_MASK) >> IB_USER_VERBS_CMD_FLAGS_SHIFT; | ||
| 702 | |||
| 703 | extended_command = flags & IB_USER_VERBS_CMD_FLAG_EXTENDED; | ||
| 704 | if (!verify_command_idx(command, extended_command)) { | ||
| 705 | ret = -EINVAL; | ||
| 706 | goto out; | ||
| 707 | } | ||
| 708 | |||
| 691 | if (verify_command_mask(ib_dev, command)) { | 709 | if (verify_command_mask(ib_dev, command)) { |
| 692 | ret = -EOPNOTSUPP; | 710 | ret = -EOPNOTSUPP; |
| 693 | goto out; | 711 | goto out; |
| @@ -699,12 +717,8 @@ static ssize_t ib_uverbs_write(struct file *filp, const char __user *buf, | |||
| 699 | goto out; | 717 | goto out; |
| 700 | } | 718 | } |
| 701 | 719 | ||
| 702 | flags = (hdr.command & | ||
| 703 | IB_USER_VERBS_CMD_FLAGS_MASK) >> IB_USER_VERBS_CMD_FLAGS_SHIFT; | ||
| 704 | |||
| 705 | if (!flags) { | 720 | if (!flags) { |
| 706 | if (command >= ARRAY_SIZE(uverbs_cmd_table) || | 721 | if (!uverbs_cmd_table[command]) { |
| 707 | !uverbs_cmd_table[command]) { | ||
| 708 | ret = -EINVAL; | 722 | ret = -EINVAL; |
| 709 | goto out; | 723 | goto out; |
| 710 | } | 724 | } |
| @@ -725,8 +739,7 @@ static ssize_t ib_uverbs_write(struct file *filp, const char __user *buf, | |||
| 725 | struct ib_udata uhw; | 739 | struct ib_udata uhw; |
| 726 | size_t written_count = count; | 740 | size_t written_count = count; |
| 727 | 741 | ||
| 728 | if (command >= ARRAY_SIZE(uverbs_ex_cmd_table) || | 742 | if (!uverbs_ex_cmd_table[command]) { |
| 729 | !uverbs_ex_cmd_table[command]) { | ||
| 730 | ret = -ENOSYS; | 743 | ret = -ENOSYS; |
| 731 | goto out; | 744 | goto out; |
| 732 | } | 745 | } |
| @@ -942,6 +955,7 @@ static const struct file_operations uverbs_fops = { | |||
| 942 | .llseek = no_llseek, | 955 | .llseek = no_llseek, |
| 943 | #if IS_ENABLED(CONFIG_INFINIBAND_EXP_USER_ACCESS) | 956 | #if IS_ENABLED(CONFIG_INFINIBAND_EXP_USER_ACCESS) |
| 944 | .unlocked_ioctl = ib_uverbs_ioctl, | 957 | .unlocked_ioctl = ib_uverbs_ioctl, |
| 958 | .compat_ioctl = ib_uverbs_ioctl, | ||
| 945 | #endif | 959 | #endif |
| 946 | }; | 960 | }; |
| 947 | 961 | ||
| @@ -954,6 +968,7 @@ static const struct file_operations uverbs_mmap_fops = { | |||
| 954 | .llseek = no_llseek, | 968 | .llseek = no_llseek, |
| 955 | #if IS_ENABLED(CONFIG_INFINIBAND_EXP_USER_ACCESS) | 969 | #if IS_ENABLED(CONFIG_INFINIBAND_EXP_USER_ACCESS) |
| 956 | .unlocked_ioctl = ib_uverbs_ioctl, | 970 | .unlocked_ioctl = ib_uverbs_ioctl, |
| 971 | .compat_ioctl = ib_uverbs_ioctl, | ||
| 957 | #endif | 972 | #endif |
| 958 | }; | 973 | }; |
| 959 | 974 | ||
diff --git a/drivers/infiniband/core/uverbs_std_types.c b/drivers/infiniband/core/uverbs_std_types.c index cab0ac3556eb..df1360e6774f 100644 --- a/drivers/infiniband/core/uverbs_std_types.c +++ b/drivers/infiniband/core/uverbs_std_types.c | |||
| @@ -234,15 +234,18 @@ static void create_udata(struct uverbs_attr_bundle *ctx, | |||
| 234 | uverbs_attr_get(ctx, UVERBS_UHW_OUT); | 234 | uverbs_attr_get(ctx, UVERBS_UHW_OUT); |
| 235 | 235 | ||
| 236 | if (!IS_ERR(uhw_in)) { | 236 | if (!IS_ERR(uhw_in)) { |
| 237 | udata->inbuf = uhw_in->ptr_attr.ptr; | ||
| 238 | udata->inlen = uhw_in->ptr_attr.len; | 237 | udata->inlen = uhw_in->ptr_attr.len; |
| 238 | if (uverbs_attr_ptr_is_inline(uhw_in)) | ||
| 239 | udata->inbuf = &uhw_in->uattr->data; | ||
| 240 | else | ||
| 241 | udata->inbuf = u64_to_user_ptr(uhw_in->ptr_attr.data); | ||
| 239 | } else { | 242 | } else { |
| 240 | udata->inbuf = NULL; | 243 | udata->inbuf = NULL; |
| 241 | udata->inlen = 0; | 244 | udata->inlen = 0; |
| 242 | } | 245 | } |
| 243 | 246 | ||
| 244 | if (!IS_ERR(uhw_out)) { | 247 | if (!IS_ERR(uhw_out)) { |
| 245 | udata->outbuf = uhw_out->ptr_attr.ptr; | 248 | udata->outbuf = u64_to_user_ptr(uhw_out->ptr_attr.data); |
| 246 | udata->outlen = uhw_out->ptr_attr.len; | 249 | udata->outlen = uhw_out->ptr_attr.len; |
| 247 | } else { | 250 | } else { |
| 248 | udata->outbuf = NULL; | 251 | udata->outbuf = NULL; |
| @@ -323,7 +326,8 @@ static int uverbs_create_cq_handler(struct ib_device *ib_dev, | |||
| 323 | cq->res.type = RDMA_RESTRACK_CQ; | 326 | cq->res.type = RDMA_RESTRACK_CQ; |
| 324 | rdma_restrack_add(&cq->res); | 327 | rdma_restrack_add(&cq->res); |
| 325 | 328 | ||
| 326 | ret = uverbs_copy_to(attrs, CREATE_CQ_RESP_CQE, &cq->cqe); | 329 | ret = uverbs_copy_to(attrs, CREATE_CQ_RESP_CQE, &cq->cqe, |
| 330 | sizeof(cq->cqe)); | ||
| 327 | if (ret) | 331 | if (ret) |
| 328 | goto err_cq; | 332 | goto err_cq; |
| 329 | 333 | ||
| @@ -375,7 +379,7 @@ static int uverbs_destroy_cq_handler(struct ib_device *ib_dev, | |||
| 375 | resp.comp_events_reported = obj->comp_events_reported; | 379 | resp.comp_events_reported = obj->comp_events_reported; |
| 376 | resp.async_events_reported = obj->async_events_reported; | 380 | resp.async_events_reported = obj->async_events_reported; |
| 377 | 381 | ||
| 378 | return uverbs_copy_to(attrs, DESTROY_CQ_RESP, &resp); | 382 | return uverbs_copy_to(attrs, DESTROY_CQ_RESP, &resp, sizeof(resp)); |
| 379 | } | 383 | } |
| 380 | 384 | ||
| 381 | static DECLARE_UVERBS_METHOD( | 385 | static DECLARE_UVERBS_METHOD( |
diff --git a/drivers/infiniband/core/verbs.c b/drivers/infiniband/core/verbs.c index 16ebc6372c31..93025d2009b8 100644 --- a/drivers/infiniband/core/verbs.c +++ b/drivers/infiniband/core/verbs.c | |||
| @@ -887,7 +887,7 @@ struct ib_qp *ib_create_qp(struct ib_pd *pd, | |||
| 887 | if (qp_init_attr->cap.max_rdma_ctxs) | 887 | if (qp_init_attr->cap.max_rdma_ctxs) |
| 888 | rdma_rw_init_qp(device, qp_init_attr); | 888 | rdma_rw_init_qp(device, qp_init_attr); |
| 889 | 889 | ||
| 890 | qp = _ib_create_qp(device, pd, qp_init_attr, NULL); | 890 | qp = _ib_create_qp(device, pd, qp_init_attr, NULL, NULL); |
| 891 | if (IS_ERR(qp)) | 891 | if (IS_ERR(qp)) |
| 892 | return qp; | 892 | return qp; |
| 893 | 893 | ||
| @@ -898,7 +898,6 @@ struct ib_qp *ib_create_qp(struct ib_pd *pd, | |||
| 898 | } | 898 | } |
| 899 | 899 | ||
| 900 | qp->real_qp = qp; | 900 | qp->real_qp = qp; |
| 901 | qp->uobject = NULL; | ||
| 902 | qp->qp_type = qp_init_attr->qp_type; | 901 | qp->qp_type = qp_init_attr->qp_type; |
| 903 | qp->rwq_ind_tbl = qp_init_attr->rwq_ind_tbl; | 902 | qp->rwq_ind_tbl = qp_init_attr->rwq_ind_tbl; |
| 904 | 903 | ||
diff --git a/drivers/infiniband/hw/bnxt_re/bnxt_re.h b/drivers/infiniband/hw/bnxt_re/bnxt_re.h index ca32057e886f..3eb7a8387116 100644 --- a/drivers/infiniband/hw/bnxt_re/bnxt_re.h +++ b/drivers/infiniband/hw/bnxt_re/bnxt_re.h | |||
| @@ -120,7 +120,6 @@ struct bnxt_re_dev { | |||
| 120 | #define BNXT_RE_FLAG_HAVE_L2_REF 3 | 120 | #define BNXT_RE_FLAG_HAVE_L2_REF 3 |
| 121 | #define BNXT_RE_FLAG_RCFW_CHANNEL_EN 4 | 121 | #define BNXT_RE_FLAG_RCFW_CHANNEL_EN 4 |
| 122 | #define BNXT_RE_FLAG_QOS_WORK_REG 5 | 122 | #define BNXT_RE_FLAG_QOS_WORK_REG 5 |
| 123 | #define BNXT_RE_FLAG_TASK_IN_PROG 6 | ||
| 124 | #define BNXT_RE_FLAG_ISSUE_ROCE_STATS 29 | 123 | #define BNXT_RE_FLAG_ISSUE_ROCE_STATS 29 |
| 125 | struct net_device *netdev; | 124 | struct net_device *netdev; |
| 126 | unsigned int version, major, minor; | 125 | unsigned int version, major, minor; |
| @@ -158,6 +157,7 @@ struct bnxt_re_dev { | |||
| 158 | atomic_t srq_count; | 157 | atomic_t srq_count; |
| 159 | atomic_t mr_count; | 158 | atomic_t mr_count; |
| 160 | atomic_t mw_count; | 159 | atomic_t mw_count; |
| 160 | atomic_t sched_count; | ||
| 161 | /* Max of 2 lossless traffic class supported per port */ | 161 | /* Max of 2 lossless traffic class supported per port */ |
| 162 | u16 cosq[2]; | 162 | u16 cosq[2]; |
| 163 | 163 | ||
diff --git a/drivers/infiniband/hw/bnxt_re/ib_verbs.c b/drivers/infiniband/hw/bnxt_re/ib_verbs.c index ae9e9ff54826..643174d949a8 100644 --- a/drivers/infiniband/hw/bnxt_re/ib_verbs.c +++ b/drivers/infiniband/hw/bnxt_re/ib_verbs.c | |||
| @@ -174,10 +174,8 @@ int bnxt_re_query_device(struct ib_device *ibdev, | |||
| 174 | ib_attr->max_pd = dev_attr->max_pd; | 174 | ib_attr->max_pd = dev_attr->max_pd; |
| 175 | ib_attr->max_qp_rd_atom = dev_attr->max_qp_rd_atom; | 175 | ib_attr->max_qp_rd_atom = dev_attr->max_qp_rd_atom; |
| 176 | ib_attr->max_qp_init_rd_atom = dev_attr->max_qp_init_rd_atom; | 176 | ib_attr->max_qp_init_rd_atom = dev_attr->max_qp_init_rd_atom; |
| 177 | if (dev_attr->is_atomic) { | 177 | ib_attr->atomic_cap = IB_ATOMIC_NONE; |
| 178 | ib_attr->atomic_cap = IB_ATOMIC_HCA; | 178 | ib_attr->masked_atomic_cap = IB_ATOMIC_NONE; |
| 179 | ib_attr->masked_atomic_cap = IB_ATOMIC_HCA; | ||
| 180 | } | ||
| 181 | 179 | ||
| 182 | ib_attr->max_ee_rd_atom = 0; | 180 | ib_attr->max_ee_rd_atom = 0; |
| 183 | ib_attr->max_res_rd_atom = 0; | 181 | ib_attr->max_res_rd_atom = 0; |
| @@ -787,20 +785,51 @@ int bnxt_re_query_ah(struct ib_ah *ib_ah, struct rdma_ah_attr *ah_attr) | |||
| 787 | return 0; | 785 | return 0; |
| 788 | } | 786 | } |
| 789 | 787 | ||
| 788 | static unsigned long bnxt_re_lock_cqs(struct bnxt_re_qp *qp) | ||
| 789 | __acquires(&qp->scq->cq_lock) __acquires(&qp->rcq->cq_lock) | ||
| 790 | { | ||
| 791 | unsigned long flags; | ||
| 792 | |||
| 793 | spin_lock_irqsave(&qp->scq->cq_lock, flags); | ||
| 794 | if (qp->rcq != qp->scq) | ||
| 795 | spin_lock(&qp->rcq->cq_lock); | ||
| 796 | else | ||
| 797 | __acquire(&qp->rcq->cq_lock); | ||
| 798 | |||
| 799 | return flags; | ||
| 800 | } | ||
| 801 | |||
| 802 | static void bnxt_re_unlock_cqs(struct bnxt_re_qp *qp, | ||
| 803 | unsigned long flags) | ||
| 804 | __releases(&qp->scq->cq_lock) __releases(&qp->rcq->cq_lock) | ||
| 805 | { | ||
| 806 | if (qp->rcq != qp->scq) | ||
| 807 | spin_unlock(&qp->rcq->cq_lock); | ||
| 808 | else | ||
| 809 | __release(&qp->rcq->cq_lock); | ||
| 810 | spin_unlock_irqrestore(&qp->scq->cq_lock, flags); | ||
| 811 | } | ||
| 812 | |||
| 790 | /* Queue Pairs */ | 813 | /* Queue Pairs */ |
| 791 | int bnxt_re_destroy_qp(struct ib_qp *ib_qp) | 814 | int bnxt_re_destroy_qp(struct ib_qp *ib_qp) |
| 792 | { | 815 | { |
| 793 | struct bnxt_re_qp *qp = container_of(ib_qp, struct bnxt_re_qp, ib_qp); | 816 | struct bnxt_re_qp *qp = container_of(ib_qp, struct bnxt_re_qp, ib_qp); |
| 794 | struct bnxt_re_dev *rdev = qp->rdev; | 817 | struct bnxt_re_dev *rdev = qp->rdev; |
| 795 | int rc; | 818 | int rc; |
| 819 | unsigned int flags; | ||
| 796 | 820 | ||
| 797 | bnxt_qplib_flush_cqn_wq(&qp->qplib_qp); | 821 | bnxt_qplib_flush_cqn_wq(&qp->qplib_qp); |
| 798 | bnxt_qplib_del_flush_qp(&qp->qplib_qp); | ||
| 799 | rc = bnxt_qplib_destroy_qp(&rdev->qplib_res, &qp->qplib_qp); | 822 | rc = bnxt_qplib_destroy_qp(&rdev->qplib_res, &qp->qplib_qp); |
| 800 | if (rc) { | 823 | if (rc) { |
| 801 | dev_err(rdev_to_dev(rdev), "Failed to destroy HW QP"); | 824 | dev_err(rdev_to_dev(rdev), "Failed to destroy HW QP"); |
| 802 | return rc; | 825 | return rc; |
| 803 | } | 826 | } |
| 827 | |||
| 828 | flags = bnxt_re_lock_cqs(qp); | ||
| 829 | bnxt_qplib_clean_qp(&qp->qplib_qp); | ||
| 830 | bnxt_re_unlock_cqs(qp, flags); | ||
| 831 | bnxt_qplib_free_qp_res(&rdev->qplib_res, &qp->qplib_qp); | ||
| 832 | |||
| 804 | if (ib_qp->qp_type == IB_QPT_GSI && rdev->qp1_sqp) { | 833 | if (ib_qp->qp_type == IB_QPT_GSI && rdev->qp1_sqp) { |
| 805 | rc = bnxt_qplib_destroy_ah(&rdev->qplib_res, | 834 | rc = bnxt_qplib_destroy_ah(&rdev->qplib_res, |
| 806 | &rdev->sqp_ah->qplib_ah); | 835 | &rdev->sqp_ah->qplib_ah); |
| @@ -810,7 +839,7 @@ int bnxt_re_destroy_qp(struct ib_qp *ib_qp) | |||
| 810 | return rc; | 839 | return rc; |
| 811 | } | 840 | } |
| 812 | 841 | ||
| 813 | bnxt_qplib_del_flush_qp(&qp->qplib_qp); | 842 | bnxt_qplib_clean_qp(&qp->qplib_qp); |
| 814 | rc = bnxt_qplib_destroy_qp(&rdev->qplib_res, | 843 | rc = bnxt_qplib_destroy_qp(&rdev->qplib_res, |
| 815 | &rdev->qp1_sqp->qplib_qp); | 844 | &rdev->qp1_sqp->qplib_qp); |
| 816 | if (rc) { | 845 | if (rc) { |
| @@ -1069,6 +1098,7 @@ struct ib_qp *bnxt_re_create_qp(struct ib_pd *ib_pd, | |||
| 1069 | goto fail; | 1098 | goto fail; |
| 1070 | } | 1099 | } |
| 1071 | qp->qplib_qp.scq = &cq->qplib_cq; | 1100 | qp->qplib_qp.scq = &cq->qplib_cq; |
| 1101 | qp->scq = cq; | ||
| 1072 | } | 1102 | } |
| 1073 | 1103 | ||
| 1074 | if (qp_init_attr->recv_cq) { | 1104 | if (qp_init_attr->recv_cq) { |
| @@ -1080,6 +1110,7 @@ struct ib_qp *bnxt_re_create_qp(struct ib_pd *ib_pd, | |||
| 1080 | goto fail; | 1110 | goto fail; |
| 1081 | } | 1111 | } |
| 1082 | qp->qplib_qp.rcq = &cq->qplib_cq; | 1112 | qp->qplib_qp.rcq = &cq->qplib_cq; |
| 1113 | qp->rcq = cq; | ||
| 1083 | } | 1114 | } |
| 1084 | 1115 | ||
| 1085 | if (qp_init_attr->srq) { | 1116 | if (qp_init_attr->srq) { |
| @@ -1185,7 +1216,7 @@ struct ib_qp *bnxt_re_create_qp(struct ib_pd *ib_pd, | |||
| 1185 | rc = bnxt_qplib_create_qp(&rdev->qplib_res, &qp->qplib_qp); | 1216 | rc = bnxt_qplib_create_qp(&rdev->qplib_res, &qp->qplib_qp); |
| 1186 | if (rc) { | 1217 | if (rc) { |
| 1187 | dev_err(rdev_to_dev(rdev), "Failed to create HW QP"); | 1218 | dev_err(rdev_to_dev(rdev), "Failed to create HW QP"); |
| 1188 | goto fail; | 1219 | goto free_umem; |
| 1189 | } | 1220 | } |
| 1190 | } | 1221 | } |
| 1191 | 1222 | ||
| @@ -1213,6 +1244,13 @@ struct ib_qp *bnxt_re_create_qp(struct ib_pd *ib_pd, | |||
| 1213 | return &qp->ib_qp; | 1244 | return &qp->ib_qp; |
| 1214 | qp_destroy: | 1245 | qp_destroy: |
| 1215 | bnxt_qplib_destroy_qp(&rdev->qplib_res, &qp->qplib_qp); | 1246 | bnxt_qplib_destroy_qp(&rdev->qplib_res, &qp->qplib_qp); |
| 1247 | free_umem: | ||
| 1248 | if (udata) { | ||
| 1249 | if (qp->rumem) | ||
| 1250 | ib_umem_release(qp->rumem); | ||
| 1251 | if (qp->sumem) | ||
| 1252 | ib_umem_release(qp->sumem); | ||
| 1253 | } | ||
| 1216 | fail: | 1254 | fail: |
| 1217 | kfree(qp); | 1255 | kfree(qp); |
| 1218 | return ERR_PTR(rc); | 1256 | return ERR_PTR(rc); |
| @@ -1603,7 +1641,7 @@ int bnxt_re_modify_qp(struct ib_qp *ib_qp, struct ib_qp_attr *qp_attr, | |||
| 1603 | dev_dbg(rdev_to_dev(rdev), | 1641 | dev_dbg(rdev_to_dev(rdev), |
| 1604 | "Move QP = %p out of flush list\n", | 1642 | "Move QP = %p out of flush list\n", |
| 1605 | qp); | 1643 | qp); |
| 1606 | bnxt_qplib_del_flush_qp(&qp->qplib_qp); | 1644 | bnxt_qplib_clean_qp(&qp->qplib_qp); |
| 1607 | } | 1645 | } |
| 1608 | } | 1646 | } |
| 1609 | if (qp_attr_mask & IB_QP_EN_SQD_ASYNC_NOTIFY) { | 1647 | if (qp_attr_mask & IB_QP_EN_SQD_ASYNC_NOTIFY) { |
diff --git a/drivers/infiniband/hw/bnxt_re/ib_verbs.h b/drivers/infiniband/hw/bnxt_re/ib_verbs.h index 423ebe012f95..b88a48d43a9d 100644 --- a/drivers/infiniband/hw/bnxt_re/ib_verbs.h +++ b/drivers/infiniband/hw/bnxt_re/ib_verbs.h | |||
| @@ -89,6 +89,8 @@ struct bnxt_re_qp { | |||
| 89 | /* QP1 */ | 89 | /* QP1 */ |
| 90 | u32 send_psn; | 90 | u32 send_psn; |
| 91 | struct ib_ud_header qp1_hdr; | 91 | struct ib_ud_header qp1_hdr; |
| 92 | struct bnxt_re_cq *scq; | ||
| 93 | struct bnxt_re_cq *rcq; | ||
| 92 | }; | 94 | }; |
| 93 | 95 | ||
| 94 | struct bnxt_re_cq { | 96 | struct bnxt_re_cq { |
diff --git a/drivers/infiniband/hw/bnxt_re/main.c b/drivers/infiniband/hw/bnxt_re/main.c index 508d00a5a106..33a448036c2e 100644 --- a/drivers/infiniband/hw/bnxt_re/main.c +++ b/drivers/infiniband/hw/bnxt_re/main.c | |||
| @@ -656,7 +656,6 @@ static void bnxt_re_dev_remove(struct bnxt_re_dev *rdev) | |||
| 656 | mutex_unlock(&bnxt_re_dev_lock); | 656 | mutex_unlock(&bnxt_re_dev_lock); |
| 657 | 657 | ||
| 658 | synchronize_rcu(); | 658 | synchronize_rcu(); |
| 659 | flush_workqueue(bnxt_re_wq); | ||
| 660 | 659 | ||
| 661 | ib_dealloc_device(&rdev->ibdev); | 660 | ib_dealloc_device(&rdev->ibdev); |
| 662 | /* rdev is gone */ | 661 | /* rdev is gone */ |
| @@ -1441,7 +1440,7 @@ static void bnxt_re_task(struct work_struct *work) | |||
| 1441 | break; | 1440 | break; |
| 1442 | } | 1441 | } |
| 1443 | smp_mb__before_atomic(); | 1442 | smp_mb__before_atomic(); |
| 1444 | clear_bit(BNXT_RE_FLAG_TASK_IN_PROG, &rdev->flags); | 1443 | atomic_dec(&rdev->sched_count); |
| 1445 | kfree(re_work); | 1444 | kfree(re_work); |
| 1446 | } | 1445 | } |
| 1447 | 1446 | ||
| @@ -1503,7 +1502,7 @@ static int bnxt_re_netdev_event(struct notifier_block *notifier, | |||
| 1503 | /* netdev notifier will call NETDEV_UNREGISTER again later since | 1502 | /* netdev notifier will call NETDEV_UNREGISTER again later since |
| 1504 | * we are still holding the reference to the netdev | 1503 | * we are still holding the reference to the netdev |
| 1505 | */ | 1504 | */ |
| 1506 | if (test_bit(BNXT_RE_FLAG_TASK_IN_PROG, &rdev->flags)) | 1505 | if (atomic_read(&rdev->sched_count) > 0) |
| 1507 | goto exit; | 1506 | goto exit; |
| 1508 | bnxt_re_ib_unreg(rdev, false); | 1507 | bnxt_re_ib_unreg(rdev, false); |
| 1509 | bnxt_re_remove_one(rdev); | 1508 | bnxt_re_remove_one(rdev); |
| @@ -1523,7 +1522,7 @@ static int bnxt_re_netdev_event(struct notifier_block *notifier, | |||
| 1523 | re_work->vlan_dev = (real_dev == netdev ? | 1522 | re_work->vlan_dev = (real_dev == netdev ? |
| 1524 | NULL : netdev); | 1523 | NULL : netdev); |
| 1525 | INIT_WORK(&re_work->work, bnxt_re_task); | 1524 | INIT_WORK(&re_work->work, bnxt_re_task); |
| 1526 | set_bit(BNXT_RE_FLAG_TASK_IN_PROG, &rdev->flags); | 1525 | atomic_inc(&rdev->sched_count); |
| 1527 | queue_work(bnxt_re_wq, &re_work->work); | 1526 | queue_work(bnxt_re_wq, &re_work->work); |
| 1528 | } | 1527 | } |
| 1529 | } | 1528 | } |
| @@ -1578,6 +1577,11 @@ static void __exit bnxt_re_mod_exit(void) | |||
| 1578 | */ | 1577 | */ |
| 1579 | list_for_each_entry_safe_reverse(rdev, next, &to_be_deleted, list) { | 1578 | list_for_each_entry_safe_reverse(rdev, next, &to_be_deleted, list) { |
| 1580 | dev_info(rdev_to_dev(rdev), "Unregistering Device"); | 1579 | dev_info(rdev_to_dev(rdev), "Unregistering Device"); |
| 1580 | /* | ||
| 1581 | * Flush out any scheduled tasks before destroying the | ||
| 1582 | * resources | ||
| 1583 | */ | ||
| 1584 | flush_workqueue(bnxt_re_wq); | ||
| 1581 | bnxt_re_dev_stop(rdev); | 1585 | bnxt_re_dev_stop(rdev); |
| 1582 | bnxt_re_ib_unreg(rdev, true); | 1586 | bnxt_re_ib_unreg(rdev, true); |
| 1583 | bnxt_re_remove_one(rdev); | 1587 | bnxt_re_remove_one(rdev); |
diff --git a/drivers/infiniband/hw/bnxt_re/qplib_fp.c b/drivers/infiniband/hw/bnxt_re/qplib_fp.c index 1b0e94697fe3..3ea5b9624f6b 100644 --- a/drivers/infiniband/hw/bnxt_re/qplib_fp.c +++ b/drivers/infiniband/hw/bnxt_re/qplib_fp.c | |||
| @@ -173,7 +173,7 @@ static void __bnxt_qplib_del_flush_qp(struct bnxt_qplib_qp *qp) | |||
| 173 | } | 173 | } |
| 174 | } | 174 | } |
| 175 | 175 | ||
| 176 | void bnxt_qplib_del_flush_qp(struct bnxt_qplib_qp *qp) | 176 | void bnxt_qplib_clean_qp(struct bnxt_qplib_qp *qp) |
| 177 | { | 177 | { |
| 178 | unsigned long flags; | 178 | unsigned long flags; |
| 179 | 179 | ||
| @@ -1419,7 +1419,6 @@ int bnxt_qplib_destroy_qp(struct bnxt_qplib_res *res, | |||
| 1419 | struct bnxt_qplib_rcfw *rcfw = res->rcfw; | 1419 | struct bnxt_qplib_rcfw *rcfw = res->rcfw; |
| 1420 | struct cmdq_destroy_qp req; | 1420 | struct cmdq_destroy_qp req; |
| 1421 | struct creq_destroy_qp_resp resp; | 1421 | struct creq_destroy_qp_resp resp; |
| 1422 | unsigned long flags; | ||
| 1423 | u16 cmd_flags = 0; | 1422 | u16 cmd_flags = 0; |
| 1424 | int rc; | 1423 | int rc; |
| 1425 | 1424 | ||
| @@ -1437,19 +1436,12 @@ int bnxt_qplib_destroy_qp(struct bnxt_qplib_res *res, | |||
| 1437 | return rc; | 1436 | return rc; |
| 1438 | } | 1437 | } |
| 1439 | 1438 | ||
| 1440 | /* Must walk the associated CQs to nullified the QP ptr */ | 1439 | return 0; |
| 1441 | spin_lock_irqsave(&qp->scq->hwq.lock, flags); | 1440 | } |
| 1442 | |||
| 1443 | __clean_cq(qp->scq, (u64)(unsigned long)qp); | ||
| 1444 | |||
| 1445 | if (qp->rcq && qp->rcq != qp->scq) { | ||
| 1446 | spin_lock(&qp->rcq->hwq.lock); | ||
| 1447 | __clean_cq(qp->rcq, (u64)(unsigned long)qp); | ||
| 1448 | spin_unlock(&qp->rcq->hwq.lock); | ||
| 1449 | } | ||
| 1450 | |||
| 1451 | spin_unlock_irqrestore(&qp->scq->hwq.lock, flags); | ||
| 1452 | 1441 | ||
| 1442 | void bnxt_qplib_free_qp_res(struct bnxt_qplib_res *res, | ||
| 1443 | struct bnxt_qplib_qp *qp) | ||
| 1444 | { | ||
| 1453 | bnxt_qplib_free_qp_hdr_buf(res, qp); | 1445 | bnxt_qplib_free_qp_hdr_buf(res, qp); |
| 1454 | bnxt_qplib_free_hwq(res->pdev, &qp->sq.hwq); | 1446 | bnxt_qplib_free_hwq(res->pdev, &qp->sq.hwq); |
| 1455 | kfree(qp->sq.swq); | 1447 | kfree(qp->sq.swq); |
| @@ -1462,7 +1454,6 @@ int bnxt_qplib_destroy_qp(struct bnxt_qplib_res *res, | |||
| 1462 | if (qp->orrq.max_elements) | 1454 | if (qp->orrq.max_elements) |
| 1463 | bnxt_qplib_free_hwq(res->pdev, &qp->orrq); | 1455 | bnxt_qplib_free_hwq(res->pdev, &qp->orrq); |
| 1464 | 1456 | ||
| 1465 | return 0; | ||
| 1466 | } | 1457 | } |
| 1467 | 1458 | ||
| 1468 | void *bnxt_qplib_get_qp1_sq_buf(struct bnxt_qplib_qp *qp, | 1459 | void *bnxt_qplib_get_qp1_sq_buf(struct bnxt_qplib_qp *qp, |
diff --git a/drivers/infiniband/hw/bnxt_re/qplib_fp.h b/drivers/infiniband/hw/bnxt_re/qplib_fp.h index 211b27a8f9e2..ca0a2ffa3509 100644 --- a/drivers/infiniband/hw/bnxt_re/qplib_fp.h +++ b/drivers/infiniband/hw/bnxt_re/qplib_fp.h | |||
| @@ -478,6 +478,9 @@ int bnxt_qplib_create_qp(struct bnxt_qplib_res *res, struct bnxt_qplib_qp *qp); | |||
| 478 | int bnxt_qplib_modify_qp(struct bnxt_qplib_res *res, struct bnxt_qplib_qp *qp); | 478 | int bnxt_qplib_modify_qp(struct bnxt_qplib_res *res, struct bnxt_qplib_qp *qp); |
| 479 | int bnxt_qplib_query_qp(struct bnxt_qplib_res *res, struct bnxt_qplib_qp *qp); | 479 | int bnxt_qplib_query_qp(struct bnxt_qplib_res *res, struct bnxt_qplib_qp *qp); |
| 480 | int bnxt_qplib_destroy_qp(struct bnxt_qplib_res *res, struct bnxt_qplib_qp *qp); | 480 | int bnxt_qplib_destroy_qp(struct bnxt_qplib_res *res, struct bnxt_qplib_qp *qp); |
| 481 | void bnxt_qplib_clean_qp(struct bnxt_qplib_qp *qp); | ||
| 482 | void bnxt_qplib_free_qp_res(struct bnxt_qplib_res *res, | ||
| 483 | struct bnxt_qplib_qp *qp); | ||
| 481 | void *bnxt_qplib_get_qp1_sq_buf(struct bnxt_qplib_qp *qp, | 484 | void *bnxt_qplib_get_qp1_sq_buf(struct bnxt_qplib_qp *qp, |
| 482 | struct bnxt_qplib_sge *sge); | 485 | struct bnxt_qplib_sge *sge); |
| 483 | void *bnxt_qplib_get_qp1_rq_buf(struct bnxt_qplib_qp *qp, | 486 | void *bnxt_qplib_get_qp1_rq_buf(struct bnxt_qplib_qp *qp, |
| @@ -500,7 +503,6 @@ void bnxt_qplib_req_notify_cq(struct bnxt_qplib_cq *cq, u32 arm_type); | |||
| 500 | void bnxt_qplib_free_nq(struct bnxt_qplib_nq *nq); | 503 | void bnxt_qplib_free_nq(struct bnxt_qplib_nq *nq); |
| 501 | int bnxt_qplib_alloc_nq(struct pci_dev *pdev, struct bnxt_qplib_nq *nq); | 504 | int bnxt_qplib_alloc_nq(struct pci_dev *pdev, struct bnxt_qplib_nq *nq); |
| 502 | void bnxt_qplib_add_flush_qp(struct bnxt_qplib_qp *qp); | 505 | void bnxt_qplib_add_flush_qp(struct bnxt_qplib_qp *qp); |
| 503 | void bnxt_qplib_del_flush_qp(struct bnxt_qplib_qp *qp); | ||
| 504 | void bnxt_qplib_acquire_cq_locks(struct bnxt_qplib_qp *qp, | 506 | void bnxt_qplib_acquire_cq_locks(struct bnxt_qplib_qp *qp, |
| 505 | unsigned long *flags); | 507 | unsigned long *flags); |
| 506 | void bnxt_qplib_release_cq_locks(struct bnxt_qplib_qp *qp, | 508 | void bnxt_qplib_release_cq_locks(struct bnxt_qplib_qp *qp, |
diff --git a/drivers/infiniband/hw/bnxt_re/qplib_sp.c b/drivers/infiniband/hw/bnxt_re/qplib_sp.c index c015c1861351..03057983341f 100644 --- a/drivers/infiniband/hw/bnxt_re/qplib_sp.c +++ b/drivers/infiniband/hw/bnxt_re/qplib_sp.c | |||
| @@ -52,18 +52,6 @@ const struct bnxt_qplib_gid bnxt_qplib_gid_zero = {{ 0, 0, 0, 0, 0, 0, 0, 0, | |||
| 52 | 52 | ||
| 53 | /* Device */ | 53 | /* Device */ |
| 54 | 54 | ||
| 55 | static bool bnxt_qplib_is_atomic_cap(struct bnxt_qplib_rcfw *rcfw) | ||
| 56 | { | ||
| 57 | int rc; | ||
| 58 | u16 pcie_ctl2; | ||
| 59 | |||
| 60 | rc = pcie_capability_read_word(rcfw->pdev, PCI_EXP_DEVCTL2, | ||
| 61 | &pcie_ctl2); | ||
| 62 | if (rc) | ||
| 63 | return false; | ||
| 64 | return !!(pcie_ctl2 & PCI_EXP_DEVCTL2_ATOMIC_REQ); | ||
| 65 | } | ||
| 66 | |||
| 67 | static void bnxt_qplib_query_version(struct bnxt_qplib_rcfw *rcfw, | 55 | static void bnxt_qplib_query_version(struct bnxt_qplib_rcfw *rcfw, |
| 68 | char *fw_ver) | 56 | char *fw_ver) |
| 69 | { | 57 | { |
| @@ -165,7 +153,7 @@ int bnxt_qplib_get_dev_attr(struct bnxt_qplib_rcfw *rcfw, | |||
| 165 | attr->tqm_alloc_reqs[i * 4 + 3] = *(++tqm_alloc); | 153 | attr->tqm_alloc_reqs[i * 4 + 3] = *(++tqm_alloc); |
| 166 | } | 154 | } |
| 167 | 155 | ||
| 168 | attr->is_atomic = bnxt_qplib_is_atomic_cap(rcfw); | 156 | attr->is_atomic = 0; |
| 169 | bail: | 157 | bail: |
| 170 | bnxt_qplib_rcfw_free_sbuf(rcfw, sbuf); | 158 | bnxt_qplib_rcfw_free_sbuf(rcfw, sbuf); |
| 171 | return rc; | 159 | return rc; |
diff --git a/drivers/infiniband/hw/vmw_pvrdma/pvrdma_cq.c b/drivers/infiniband/hw/vmw_pvrdma/pvrdma_cq.c index faa9478c14a6..f95b97646c25 100644 --- a/drivers/infiniband/hw/vmw_pvrdma/pvrdma_cq.c +++ b/drivers/infiniband/hw/vmw_pvrdma/pvrdma_cq.c | |||
| @@ -114,6 +114,7 @@ struct ib_cq *pvrdma_create_cq(struct ib_device *ibdev, | |||
| 114 | union pvrdma_cmd_resp rsp; | 114 | union pvrdma_cmd_resp rsp; |
| 115 | struct pvrdma_cmd_create_cq *cmd = &req.create_cq; | 115 | struct pvrdma_cmd_create_cq *cmd = &req.create_cq; |
| 116 | struct pvrdma_cmd_create_cq_resp *resp = &rsp.create_cq_resp; | 116 | struct pvrdma_cmd_create_cq_resp *resp = &rsp.create_cq_resp; |
| 117 | struct pvrdma_create_cq_resp cq_resp = {0}; | ||
| 117 | struct pvrdma_create_cq ucmd; | 118 | struct pvrdma_create_cq ucmd; |
| 118 | 119 | ||
| 119 | BUILD_BUG_ON(sizeof(struct pvrdma_cqe) != 64); | 120 | BUILD_BUG_ON(sizeof(struct pvrdma_cqe) != 64); |
| @@ -197,6 +198,7 @@ struct ib_cq *pvrdma_create_cq(struct ib_device *ibdev, | |||
| 197 | 198 | ||
| 198 | cq->ibcq.cqe = resp->cqe; | 199 | cq->ibcq.cqe = resp->cqe; |
| 199 | cq->cq_handle = resp->cq_handle; | 200 | cq->cq_handle = resp->cq_handle; |
| 201 | cq_resp.cqn = resp->cq_handle; | ||
| 200 | spin_lock_irqsave(&dev->cq_tbl_lock, flags); | 202 | spin_lock_irqsave(&dev->cq_tbl_lock, flags); |
| 201 | dev->cq_tbl[cq->cq_handle % dev->dsr->caps.max_cq] = cq; | 203 | dev->cq_tbl[cq->cq_handle % dev->dsr->caps.max_cq] = cq; |
| 202 | spin_unlock_irqrestore(&dev->cq_tbl_lock, flags); | 204 | spin_unlock_irqrestore(&dev->cq_tbl_lock, flags); |
| @@ -205,7 +207,7 @@ struct ib_cq *pvrdma_create_cq(struct ib_device *ibdev, | |||
| 205 | cq->uar = &(to_vucontext(context)->uar); | 207 | cq->uar = &(to_vucontext(context)->uar); |
| 206 | 208 | ||
| 207 | /* Copy udata back. */ | 209 | /* Copy udata back. */ |
| 208 | if (ib_copy_to_udata(udata, &cq->cq_handle, sizeof(__u32))) { | 210 | if (ib_copy_to_udata(udata, &cq_resp, sizeof(cq_resp))) { |
| 209 | dev_warn(&dev->pdev->dev, | 211 | dev_warn(&dev->pdev->dev, |
| 210 | "failed to copy back udata\n"); | 212 | "failed to copy back udata\n"); |
| 211 | pvrdma_destroy_cq(&cq->ibcq); | 213 | pvrdma_destroy_cq(&cq->ibcq); |
diff --git a/drivers/infiniband/hw/vmw_pvrdma/pvrdma_srq.c b/drivers/infiniband/hw/vmw_pvrdma/pvrdma_srq.c index 5acebb1ef631..af235967a9c2 100644 --- a/drivers/infiniband/hw/vmw_pvrdma/pvrdma_srq.c +++ b/drivers/infiniband/hw/vmw_pvrdma/pvrdma_srq.c | |||
| @@ -113,6 +113,7 @@ struct ib_srq *pvrdma_create_srq(struct ib_pd *pd, | |||
| 113 | union pvrdma_cmd_resp rsp; | 113 | union pvrdma_cmd_resp rsp; |
| 114 | struct pvrdma_cmd_create_srq *cmd = &req.create_srq; | 114 | struct pvrdma_cmd_create_srq *cmd = &req.create_srq; |
| 115 | struct pvrdma_cmd_create_srq_resp *resp = &rsp.create_srq_resp; | 115 | struct pvrdma_cmd_create_srq_resp *resp = &rsp.create_srq_resp; |
| 116 | struct pvrdma_create_srq_resp srq_resp = {0}; | ||
| 116 | struct pvrdma_create_srq ucmd; | 117 | struct pvrdma_create_srq ucmd; |
| 117 | unsigned long flags; | 118 | unsigned long flags; |
| 118 | int ret; | 119 | int ret; |
| @@ -204,12 +205,13 @@ struct ib_srq *pvrdma_create_srq(struct ib_pd *pd, | |||
| 204 | } | 205 | } |
| 205 | 206 | ||
| 206 | srq->srq_handle = resp->srqn; | 207 | srq->srq_handle = resp->srqn; |
| 208 | srq_resp.srqn = resp->srqn; | ||
| 207 | spin_lock_irqsave(&dev->srq_tbl_lock, flags); | 209 | spin_lock_irqsave(&dev->srq_tbl_lock, flags); |
| 208 | dev->srq_tbl[srq->srq_handle % dev->dsr->caps.max_srq] = srq; | 210 | dev->srq_tbl[srq->srq_handle % dev->dsr->caps.max_srq] = srq; |
| 209 | spin_unlock_irqrestore(&dev->srq_tbl_lock, flags); | 211 | spin_unlock_irqrestore(&dev->srq_tbl_lock, flags); |
| 210 | 212 | ||
| 211 | /* Copy udata back. */ | 213 | /* Copy udata back. */ |
| 212 | if (ib_copy_to_udata(udata, &srq->srq_handle, sizeof(__u32))) { | 214 | if (ib_copy_to_udata(udata, &srq_resp, sizeof(srq_resp))) { |
| 213 | dev_warn(&dev->pdev->dev, "failed to copy back udata\n"); | 215 | dev_warn(&dev->pdev->dev, "failed to copy back udata\n"); |
| 214 | pvrdma_destroy_srq(&srq->ibsrq); | 216 | pvrdma_destroy_srq(&srq->ibsrq); |
| 215 | return ERR_PTR(-EINVAL); | 217 | return ERR_PTR(-EINVAL); |
diff --git a/drivers/infiniband/hw/vmw_pvrdma/pvrdma_verbs.c b/drivers/infiniband/hw/vmw_pvrdma/pvrdma_verbs.c index 16b96616ef7e..a51463cd2f37 100644 --- a/drivers/infiniband/hw/vmw_pvrdma/pvrdma_verbs.c +++ b/drivers/infiniband/hw/vmw_pvrdma/pvrdma_verbs.c | |||
| @@ -447,6 +447,7 @@ struct ib_pd *pvrdma_alloc_pd(struct ib_device *ibdev, | |||
| 447 | union pvrdma_cmd_resp rsp; | 447 | union pvrdma_cmd_resp rsp; |
| 448 | struct pvrdma_cmd_create_pd *cmd = &req.create_pd; | 448 | struct pvrdma_cmd_create_pd *cmd = &req.create_pd; |
| 449 | struct pvrdma_cmd_create_pd_resp *resp = &rsp.create_pd_resp; | 449 | struct pvrdma_cmd_create_pd_resp *resp = &rsp.create_pd_resp; |
| 450 | struct pvrdma_alloc_pd_resp pd_resp = {0}; | ||
| 450 | int ret; | 451 | int ret; |
| 451 | void *ptr; | 452 | void *ptr; |
| 452 | 453 | ||
| @@ -475,9 +476,10 @@ struct ib_pd *pvrdma_alloc_pd(struct ib_device *ibdev, | |||
| 475 | pd->privileged = !context; | 476 | pd->privileged = !context; |
| 476 | pd->pd_handle = resp->pd_handle; | 477 | pd->pd_handle = resp->pd_handle; |
| 477 | pd->pdn = resp->pd_handle; | 478 | pd->pdn = resp->pd_handle; |
| 479 | pd_resp.pdn = resp->pd_handle; | ||
| 478 | 480 | ||
| 479 | if (context) { | 481 | if (context) { |
| 480 | if (ib_copy_to_udata(udata, &pd->pdn, sizeof(__u32))) { | 482 | if (ib_copy_to_udata(udata, &pd_resp, sizeof(pd_resp))) { |
| 481 | dev_warn(&dev->pdev->dev, | 483 | dev_warn(&dev->pdev->dev, |
| 482 | "failed to copy back protection domain\n"); | 484 | "failed to copy back protection domain\n"); |
| 483 | pvrdma_dealloc_pd(&pd->ibpd); | 485 | pvrdma_dealloc_pd(&pd->ibpd); |
diff --git a/drivers/infiniband/ulp/ipoib/ipoib_fs.c b/drivers/infiniband/ulp/ipoib/ipoib_fs.c index 11f74cbe6660..ea302b054601 100644 --- a/drivers/infiniband/ulp/ipoib/ipoib_fs.c +++ b/drivers/infiniband/ulp/ipoib/ipoib_fs.c | |||
| @@ -281,8 +281,6 @@ void ipoib_delete_debug_files(struct net_device *dev) | |||
| 281 | { | 281 | { |
| 282 | struct ipoib_dev_priv *priv = ipoib_priv(dev); | 282 | struct ipoib_dev_priv *priv = ipoib_priv(dev); |
| 283 | 283 | ||
| 284 | WARN_ONCE(!priv->mcg_dentry, "null mcg debug file\n"); | ||
| 285 | WARN_ONCE(!priv->path_dentry, "null path debug file\n"); | ||
| 286 | debugfs_remove(priv->mcg_dentry); | 284 | debugfs_remove(priv->mcg_dentry); |
| 287 | debugfs_remove(priv->path_dentry); | 285 | debugfs_remove(priv->path_dentry); |
| 288 | priv->mcg_dentry = priv->path_dentry = NULL; | 286 | priv->mcg_dentry = priv->path_dentry = NULL; |
diff --git a/drivers/iommu/intel-svm.c b/drivers/iommu/intel-svm.c index 35a408d0ae4f..99bc9bd64b9e 100644 --- a/drivers/iommu/intel-svm.c +++ b/drivers/iommu/intel-svm.c | |||
| @@ -205,7 +205,7 @@ static void intel_flush_svm_range_dev (struct intel_svm *svm, struct intel_svm_d | |||
| 205 | * for example, an "address" value of 0x12345f000 will | 205 | * for example, an "address" value of 0x12345f000 will |
| 206 | * flush from 0x123440000 to 0x12347ffff (256KiB). */ | 206 | * flush from 0x123440000 to 0x12347ffff (256KiB). */ |
| 207 | unsigned long last = address + ((unsigned long)(pages - 1) << VTD_PAGE_SHIFT); | 207 | unsigned long last = address + ((unsigned long)(pages - 1) << VTD_PAGE_SHIFT); |
| 208 | unsigned long mask = __rounddown_pow_of_two(address ^ last);; | 208 | unsigned long mask = __rounddown_pow_of_two(address ^ last); |
| 209 | 209 | ||
| 210 | desc.high = QI_DEV_EIOTLB_ADDR((address & ~mask) | (mask - 1)) | QI_DEV_EIOTLB_SIZE; | 210 | desc.high = QI_DEV_EIOTLB_ADDR((address & ~mask) | (mask - 1)) | QI_DEV_EIOTLB_SIZE; |
| 211 | } else { | 211 | } else { |
diff --git a/drivers/irqchip/irq-bcm7038-l1.c b/drivers/irqchip/irq-bcm7038-l1.c index 55cfb986225b..faf734ff4cf3 100644 --- a/drivers/irqchip/irq-bcm7038-l1.c +++ b/drivers/irqchip/irq-bcm7038-l1.c | |||
| @@ -339,9 +339,6 @@ int __init bcm7038_l1_of_init(struct device_node *dn, | |||
| 339 | goto out_unmap; | 339 | goto out_unmap; |
| 340 | } | 340 | } |
| 341 | 341 | ||
| 342 | pr_info("registered BCM7038 L1 intc (mem: 0x%p, IRQs: %d)\n", | ||
| 343 | intc->cpus[0]->map_base, IRQS_PER_WORD * intc->n_words); | ||
| 344 | |||
| 345 | return 0; | 342 | return 0; |
| 346 | 343 | ||
| 347 | out_unmap: | 344 | out_unmap: |
diff --git a/drivers/irqchip/irq-bcm7120-l2.c b/drivers/irqchip/irq-bcm7120-l2.c index 983640eba418..8968e5e93fcb 100644 --- a/drivers/irqchip/irq-bcm7120-l2.c +++ b/drivers/irqchip/irq-bcm7120-l2.c | |||
| @@ -318,9 +318,6 @@ static int __init bcm7120_l2_intc_probe(struct device_node *dn, | |||
| 318 | } | 318 | } |
| 319 | } | 319 | } |
| 320 | 320 | ||
| 321 | pr_info("registered %s intc (mem: 0x%p, parent IRQ(s): %d)\n", | ||
| 322 | intc_name, data->map_base[0], data->num_parent_irqs); | ||
| 323 | |||
| 324 | return 0; | 321 | return 0; |
| 325 | 322 | ||
| 326 | out_free_domain: | 323 | out_free_domain: |
diff --git a/drivers/irqchip/irq-brcmstb-l2.c b/drivers/irqchip/irq-brcmstb-l2.c index 691d20eb0bec..0e65f609352e 100644 --- a/drivers/irqchip/irq-brcmstb-l2.c +++ b/drivers/irqchip/irq-brcmstb-l2.c | |||
| @@ -262,9 +262,6 @@ static int __init brcmstb_l2_intc_of_init(struct device_node *np, | |||
| 262 | ct->chip.irq_set_wake = irq_gc_set_wake; | 262 | ct->chip.irq_set_wake = irq_gc_set_wake; |
| 263 | } | 263 | } |
| 264 | 264 | ||
| 265 | pr_info("registered L2 intc (mem: 0x%p, parent irq: %d)\n", | ||
| 266 | base, parent_irq); | ||
| 267 | |||
| 268 | return 0; | 265 | return 0; |
| 269 | 266 | ||
| 270 | out_free_domain: | 267 | out_free_domain: |
diff --git a/drivers/irqchip/irq-gic-v2m.c b/drivers/irqchip/irq-gic-v2m.c index 993a8426a453..1ff38aff9f29 100644 --- a/drivers/irqchip/irq-gic-v2m.c +++ b/drivers/irqchip/irq-gic-v2m.c | |||
| @@ -94,7 +94,7 @@ static struct irq_chip gicv2m_msi_irq_chip = { | |||
| 94 | 94 | ||
| 95 | static struct msi_domain_info gicv2m_msi_domain_info = { | 95 | static struct msi_domain_info gicv2m_msi_domain_info = { |
| 96 | .flags = (MSI_FLAG_USE_DEF_DOM_OPS | MSI_FLAG_USE_DEF_CHIP_OPS | | 96 | .flags = (MSI_FLAG_USE_DEF_DOM_OPS | MSI_FLAG_USE_DEF_CHIP_OPS | |
| 97 | MSI_FLAG_PCI_MSIX), | 97 | MSI_FLAG_PCI_MSIX | MSI_FLAG_MULTI_PCI_MSI), |
| 98 | .chip = &gicv2m_msi_irq_chip, | 98 | .chip = &gicv2m_msi_irq_chip, |
| 99 | }; | 99 | }; |
| 100 | 100 | ||
| @@ -155,18 +155,12 @@ static int gicv2m_irq_gic_domain_alloc(struct irq_domain *domain, | |||
| 155 | return 0; | 155 | return 0; |
| 156 | } | 156 | } |
| 157 | 157 | ||
| 158 | static void gicv2m_unalloc_msi(struct v2m_data *v2m, unsigned int hwirq) | 158 | static void gicv2m_unalloc_msi(struct v2m_data *v2m, unsigned int hwirq, |
| 159 | int nr_irqs) | ||
| 159 | { | 160 | { |
| 160 | int pos; | ||
| 161 | |||
| 162 | pos = hwirq - v2m->spi_start; | ||
| 163 | if (pos < 0 || pos >= v2m->nr_spis) { | ||
| 164 | pr_err("Failed to teardown msi. Invalid hwirq %d\n", hwirq); | ||
| 165 | return; | ||
| 166 | } | ||
| 167 | |||
| 168 | spin_lock(&v2m_lock); | 161 | spin_lock(&v2m_lock); |
| 169 | __clear_bit(pos, v2m->bm); | 162 | bitmap_release_region(v2m->bm, hwirq - v2m->spi_start, |
| 163 | get_count_order(nr_irqs)); | ||
| 170 | spin_unlock(&v2m_lock); | 164 | spin_unlock(&v2m_lock); |
| 171 | } | 165 | } |
| 172 | 166 | ||
| @@ -174,13 +168,13 @@ static int gicv2m_irq_domain_alloc(struct irq_domain *domain, unsigned int virq, | |||
| 174 | unsigned int nr_irqs, void *args) | 168 | unsigned int nr_irqs, void *args) |
| 175 | { | 169 | { |
| 176 | struct v2m_data *v2m = NULL, *tmp; | 170 | struct v2m_data *v2m = NULL, *tmp; |
| 177 | int hwirq, offset, err = 0; | 171 | int hwirq, offset, i, err = 0; |
| 178 | 172 | ||
| 179 | spin_lock(&v2m_lock); | 173 | spin_lock(&v2m_lock); |
| 180 | list_for_each_entry(tmp, &v2m_nodes, entry) { | 174 | list_for_each_entry(tmp, &v2m_nodes, entry) { |
| 181 | offset = find_first_zero_bit(tmp->bm, tmp->nr_spis); | 175 | offset = bitmap_find_free_region(tmp->bm, tmp->nr_spis, |
| 182 | if (offset < tmp->nr_spis) { | 176 | get_count_order(nr_irqs)); |
| 183 | __set_bit(offset, tmp->bm); | 177 | if (offset >= 0) { |
| 184 | v2m = tmp; | 178 | v2m = tmp; |
| 185 | break; | 179 | break; |
| 186 | } | 180 | } |
| @@ -192,16 +186,21 @@ static int gicv2m_irq_domain_alloc(struct irq_domain *domain, unsigned int virq, | |||
| 192 | 186 | ||
| 193 | hwirq = v2m->spi_start + offset; | 187 | hwirq = v2m->spi_start + offset; |
| 194 | 188 | ||
| 195 | err = gicv2m_irq_gic_domain_alloc(domain, virq, hwirq); | 189 | for (i = 0; i < nr_irqs; i++) { |
| 196 | if (err) { | 190 | err = gicv2m_irq_gic_domain_alloc(domain, virq + i, hwirq + i); |
| 197 | gicv2m_unalloc_msi(v2m, hwirq); | 191 | if (err) |
| 198 | return err; | 192 | goto fail; |
| 199 | } | ||
| 200 | 193 | ||
| 201 | irq_domain_set_hwirq_and_chip(domain, virq, hwirq, | 194 | irq_domain_set_hwirq_and_chip(domain, virq + i, hwirq + i, |
| 202 | &gicv2m_irq_chip, v2m); | 195 | &gicv2m_irq_chip, v2m); |
| 196 | } | ||
| 203 | 197 | ||
| 204 | return 0; | 198 | return 0; |
| 199 | |||
| 200 | fail: | ||
| 201 | irq_domain_free_irqs_parent(domain, virq, nr_irqs); | ||
| 202 | gicv2m_unalloc_msi(v2m, hwirq, get_count_order(nr_irqs)); | ||
| 203 | return err; | ||
| 205 | } | 204 | } |
| 206 | 205 | ||
| 207 | static void gicv2m_irq_domain_free(struct irq_domain *domain, | 206 | static void gicv2m_irq_domain_free(struct irq_domain *domain, |
| @@ -210,8 +209,7 @@ static void gicv2m_irq_domain_free(struct irq_domain *domain, | |||
| 210 | struct irq_data *d = irq_domain_get_irq_data(domain, virq); | 209 | struct irq_data *d = irq_domain_get_irq_data(domain, virq); |
| 211 | struct v2m_data *v2m = irq_data_get_irq_chip_data(d); | 210 | struct v2m_data *v2m = irq_data_get_irq_chip_data(d); |
| 212 | 211 | ||
| 213 | BUG_ON(nr_irqs != 1); | 212 | gicv2m_unalloc_msi(v2m, d->hwirq, nr_irqs); |
| 214 | gicv2m_unalloc_msi(v2m, d->hwirq); | ||
| 215 | irq_domain_free_irqs_parent(domain, virq, nr_irqs); | 213 | irq_domain_free_irqs_parent(domain, virq, nr_irqs); |
| 216 | } | 214 | } |
| 217 | 215 | ||
diff --git a/drivers/irqchip/irq-gic-v3-its-pci-msi.c b/drivers/irqchip/irq-gic-v3-its-pci-msi.c index 14a8c0a7e095..25a98de5cfb2 100644 --- a/drivers/irqchip/irq-gic-v3-its-pci-msi.c +++ b/drivers/irqchip/irq-gic-v3-its-pci-msi.c | |||
| @@ -132,6 +132,8 @@ static int __init its_pci_of_msi_init(void) | |||
| 132 | 132 | ||
| 133 | for (np = of_find_matching_node(NULL, its_device_id); np; | 133 | for (np = of_find_matching_node(NULL, its_device_id); np; |
| 134 | np = of_find_matching_node(np, its_device_id)) { | 134 | np = of_find_matching_node(np, its_device_id)) { |
| 135 | if (!of_device_is_available(np)) | ||
| 136 | continue; | ||
| 135 | if (!of_property_read_bool(np, "msi-controller")) | 137 | if (!of_property_read_bool(np, "msi-controller")) |
| 136 | continue; | 138 | continue; |
| 137 | 139 | ||
diff --git a/drivers/irqchip/irq-gic-v3-its-platform-msi.c b/drivers/irqchip/irq-gic-v3-its-platform-msi.c index 833a90fe33ae..8881a053c173 100644 --- a/drivers/irqchip/irq-gic-v3-its-platform-msi.c +++ b/drivers/irqchip/irq-gic-v3-its-platform-msi.c | |||
| @@ -154,6 +154,8 @@ static void __init its_pmsi_of_init(void) | |||
| 154 | 154 | ||
| 155 | for (np = of_find_matching_node(NULL, its_device_id); np; | 155 | for (np = of_find_matching_node(NULL, its_device_id); np; |
| 156 | np = of_find_matching_node(np, its_device_id)) { | 156 | np = of_find_matching_node(np, its_device_id)) { |
| 157 | if (!of_device_is_available(np)) | ||
| 158 | continue; | ||
| 157 | if (!of_property_read_bool(np, "msi-controller")) | 159 | if (!of_property_read_bool(np, "msi-controller")) |
| 158 | continue; | 160 | continue; |
| 159 | 161 | ||
diff --git a/drivers/irqchip/irq-gic-v3-its.c b/drivers/irqchip/irq-gic-v3-its.c index 06f025fd5726..1d3056f53747 100644 --- a/drivers/irqchip/irq-gic-v3-its.c +++ b/drivers/irqchip/irq-gic-v3-its.c | |||
| @@ -3314,6 +3314,8 @@ static int __init its_of_probe(struct device_node *node) | |||
| 3314 | 3314 | ||
| 3315 | for (np = of_find_matching_node(node, its_device_id); np; | 3315 | for (np = of_find_matching_node(node, its_device_id); np; |
| 3316 | np = of_find_matching_node(np, its_device_id)) { | 3316 | np = of_find_matching_node(np, its_device_id)) { |
| 3317 | if (!of_device_is_available(np)) | ||
| 3318 | continue; | ||
| 3317 | if (!of_property_read_bool(np, "msi-controller")) { | 3319 | if (!of_property_read_bool(np, "msi-controller")) { |
| 3318 | pr_warn("%pOF: no msi-controller property, ITS ignored\n", | 3320 | pr_warn("%pOF: no msi-controller property, ITS ignored\n", |
| 3319 | np); | 3321 | np); |
diff --git a/drivers/irqchip/irq-gic-v3.c b/drivers/irqchip/irq-gic-v3.c index a57c0fbbd34a..d99cc07903ec 100644 --- a/drivers/irqchip/irq-gic-v3.c +++ b/drivers/irqchip/irq-gic-v3.c | |||
| @@ -673,7 +673,7 @@ static void gic_send_sgi(u64 cluster_id, u16 tlist, unsigned int irq) | |||
| 673 | MPIDR_TO_SGI_RS(cluster_id) | | 673 | MPIDR_TO_SGI_RS(cluster_id) | |
| 674 | tlist << ICC_SGI1R_TARGET_LIST_SHIFT); | 674 | tlist << ICC_SGI1R_TARGET_LIST_SHIFT); |
| 675 | 675 | ||
| 676 | pr_debug("CPU%d: ICC_SGI1R_EL1 %llx\n", smp_processor_id(), val); | 676 | pr_devel("CPU%d: ICC_SGI1R_EL1 %llx\n", smp_processor_id(), val); |
| 677 | gic_write_sgi1r(val); | 677 | gic_write_sgi1r(val); |
| 678 | } | 678 | } |
| 679 | 679 | ||
| @@ -688,7 +688,7 @@ static void gic_raise_softirq(const struct cpumask *mask, unsigned int irq) | |||
| 688 | * Ensure that stores to Normal memory are visible to the | 688 | * Ensure that stores to Normal memory are visible to the |
| 689 | * other CPUs before issuing the IPI. | 689 | * other CPUs before issuing the IPI. |
| 690 | */ | 690 | */ |
| 691 | smp_wmb(); | 691 | wmb(); |
| 692 | 692 | ||
| 693 | for_each_cpu(cpu, mask) { | 693 | for_each_cpu(cpu, mask) { |
| 694 | u64 cluster_id = MPIDR_TO_SGI_CLUSTER_ID(cpu_logical_map(cpu)); | 694 | u64 cluster_id = MPIDR_TO_SGI_CLUSTER_ID(cpu_logical_map(cpu)); |
diff --git a/drivers/irqchip/irq-mips-gic.c b/drivers/irqchip/irq-mips-gic.c index ef92a4d2038e..d32268cc1174 100644 --- a/drivers/irqchip/irq-mips-gic.c +++ b/drivers/irqchip/irq-mips-gic.c | |||
| @@ -424,8 +424,6 @@ static int gic_shared_irq_domain_map(struct irq_domain *d, unsigned int virq, | |||
| 424 | spin_lock_irqsave(&gic_lock, flags); | 424 | spin_lock_irqsave(&gic_lock, flags); |
| 425 | write_gic_map_pin(intr, GIC_MAP_PIN_MAP_TO_PIN | gic_cpu_pin); | 425 | write_gic_map_pin(intr, GIC_MAP_PIN_MAP_TO_PIN | gic_cpu_pin); |
| 426 | write_gic_map_vp(intr, BIT(mips_cm_vp_id(cpu))); | 426 | write_gic_map_vp(intr, BIT(mips_cm_vp_id(cpu))); |
| 427 | gic_clear_pcpu_masks(intr); | ||
| 428 | set_bit(intr, per_cpu_ptr(pcpu_masks, cpu)); | ||
| 429 | irq_data_update_effective_affinity(data, cpumask_of(cpu)); | 427 | irq_data_update_effective_affinity(data, cpumask_of(cpu)); |
| 430 | spin_unlock_irqrestore(&gic_lock, flags); | 428 | spin_unlock_irqrestore(&gic_lock, flags); |
| 431 | 429 | ||
diff --git a/drivers/macintosh/macio_asic.c b/drivers/macintosh/macio_asic.c index 62f541f968f6..07074820a167 100644 --- a/drivers/macintosh/macio_asic.c +++ b/drivers/macintosh/macio_asic.c | |||
| @@ -375,6 +375,7 @@ static struct macio_dev * macio_add_one_device(struct macio_chip *chip, | |||
| 375 | dev->ofdev.dev.of_node = np; | 375 | dev->ofdev.dev.of_node = np; |
| 376 | dev->ofdev.archdata.dma_mask = 0xffffffffUL; | 376 | dev->ofdev.archdata.dma_mask = 0xffffffffUL; |
| 377 | dev->ofdev.dev.dma_mask = &dev->ofdev.archdata.dma_mask; | 377 | dev->ofdev.dev.dma_mask = &dev->ofdev.archdata.dma_mask; |
| 378 | dev->ofdev.dev.coherent_dma_mask = dev->ofdev.archdata.dma_mask; | ||
| 378 | dev->ofdev.dev.parent = parent; | 379 | dev->ofdev.dev.parent = parent; |
| 379 | dev->ofdev.dev.bus = &macio_bus_type; | 380 | dev->ofdev.dev.bus = &macio_bus_type; |
| 380 | dev->ofdev.dev.release = macio_release_dev; | 381 | dev->ofdev.dev.release = macio_release_dev; |
diff --git a/drivers/md/dm.c b/drivers/md/dm.c index d6de00f367ef..68136806d365 100644 --- a/drivers/md/dm.c +++ b/drivers/md/dm.c | |||
| @@ -903,7 +903,8 @@ static void dec_pending(struct dm_io *io, blk_status_t error) | |||
| 903 | queue_io(md, bio); | 903 | queue_io(md, bio); |
| 904 | } else { | 904 | } else { |
| 905 | /* done with normal IO or empty flush */ | 905 | /* done with normal IO or empty flush */ |
| 906 | bio->bi_status = io_error; | 906 | if (io_error) |
| 907 | bio->bi_status = io_error; | ||
| 907 | bio_endio(bio); | 908 | bio_endio(bio); |
| 908 | } | 909 | } |
| 909 | } | 910 | } |
diff --git a/drivers/md/raid1.c b/drivers/md/raid1.c index b2eae332e1a2..f978eddc7a21 100644 --- a/drivers/md/raid1.c +++ b/drivers/md/raid1.c | |||
| @@ -1108,7 +1108,7 @@ static void alloc_behind_master_bio(struct r1bio *r1_bio, | |||
| 1108 | 1108 | ||
| 1109 | bio_copy_data(behind_bio, bio); | 1109 | bio_copy_data(behind_bio, bio); |
| 1110 | skip_copy: | 1110 | skip_copy: |
| 1111 | r1_bio->behind_master_bio = behind_bio;; | 1111 | r1_bio->behind_master_bio = behind_bio; |
| 1112 | set_bit(R1BIO_BehindIO, &r1_bio->state); | 1112 | set_bit(R1BIO_BehindIO, &r1_bio->state); |
| 1113 | 1113 | ||
| 1114 | return; | 1114 | return; |
diff --git a/drivers/message/fusion/mptctl.c b/drivers/message/fusion/mptctl.c index 8d12017b9893..4470630dd545 100644 --- a/drivers/message/fusion/mptctl.c +++ b/drivers/message/fusion/mptctl.c | |||
| @@ -2687,6 +2687,8 @@ mptctl_hp_targetinfo(unsigned long arg) | |||
| 2687 | __FILE__, __LINE__, iocnum); | 2687 | __FILE__, __LINE__, iocnum); |
| 2688 | return -ENODEV; | 2688 | return -ENODEV; |
| 2689 | } | 2689 | } |
| 2690 | if (karg.hdr.id >= MPT_MAX_FC_DEVICES) | ||
| 2691 | return -EINVAL; | ||
| 2690 | dctlprintk(ioc, printk(MYIOC_s_DEBUG_FMT "mptctl_hp_targetinfo called.\n", | 2692 | dctlprintk(ioc, printk(MYIOC_s_DEBUG_FMT "mptctl_hp_targetinfo called.\n", |
| 2691 | ioc->name)); | 2693 | ioc->name)); |
| 2692 | 2694 | ||
diff --git a/drivers/misc/mei/bus.c b/drivers/misc/mei/bus.c index 3e5eabdae8d9..772d02922529 100644 --- a/drivers/misc/mei/bus.c +++ b/drivers/misc/mei/bus.c | |||
| @@ -548,12 +548,6 @@ int mei_cldev_disable(struct mei_cl_device *cldev) | |||
| 548 | goto out; | 548 | goto out; |
| 549 | } | 549 | } |
| 550 | 550 | ||
| 551 | if (bus->dev_state == MEI_DEV_POWER_DOWN) { | ||
| 552 | dev_dbg(bus->dev, "Device is powering down, don't bother with disconnection\n"); | ||
| 553 | err = 0; | ||
| 554 | goto out; | ||
| 555 | } | ||
| 556 | |||
| 557 | err = mei_cl_disconnect(cl); | 551 | err = mei_cl_disconnect(cl); |
| 558 | if (err < 0) | 552 | if (err < 0) |
| 559 | dev_err(bus->dev, "Could not disconnect from the ME client\n"); | 553 | dev_err(bus->dev, "Could not disconnect from the ME client\n"); |
diff --git a/drivers/misc/mei/client.c b/drivers/misc/mei/client.c index be64969d986a..7e60c1817c31 100644 --- a/drivers/misc/mei/client.c +++ b/drivers/misc/mei/client.c | |||
| @@ -945,6 +945,12 @@ int mei_cl_disconnect(struct mei_cl *cl) | |||
| 945 | return 0; | 945 | return 0; |
| 946 | } | 946 | } |
| 947 | 947 | ||
| 948 | if (dev->dev_state == MEI_DEV_POWER_DOWN) { | ||
| 949 | cl_dbg(dev, cl, "Device is powering down, don't bother with disconnection\n"); | ||
| 950 | mei_cl_set_disconnected(cl); | ||
| 951 | return 0; | ||
| 952 | } | ||
| 953 | |||
| 948 | rets = pm_runtime_get(dev->dev); | 954 | rets = pm_runtime_get(dev->dev); |
| 949 | if (rets < 0 && rets != -EINPROGRESS) { | 955 | if (rets < 0 && rets != -EINPROGRESS) { |
| 950 | pm_runtime_put_noidle(dev->dev); | 956 | pm_runtime_put_noidle(dev->dev); |
diff --git a/drivers/misc/mei/hw-me-regs.h b/drivers/misc/mei/hw-me-regs.h index 0ccccbaf530d..e4b10b2d1a08 100644 --- a/drivers/misc/mei/hw-me-regs.h +++ b/drivers/misc/mei/hw-me-regs.h | |||
| @@ -132,6 +132,11 @@ | |||
| 132 | #define MEI_DEV_ID_KBP 0xA2BA /* Kaby Point */ | 132 | #define MEI_DEV_ID_KBP 0xA2BA /* Kaby Point */ |
| 133 | #define MEI_DEV_ID_KBP_2 0xA2BB /* Kaby Point 2 */ | 133 | #define MEI_DEV_ID_KBP_2 0xA2BB /* Kaby Point 2 */ |
| 134 | 134 | ||
| 135 | #define MEI_DEV_ID_CNP_LP 0x9DE0 /* Cannon Point LP */ | ||
| 136 | #define MEI_DEV_ID_CNP_LP_4 0x9DE4 /* Cannon Point LP 4 (iTouch) */ | ||
| 137 | #define MEI_DEV_ID_CNP_H 0xA360 /* Cannon Point H */ | ||
| 138 | #define MEI_DEV_ID_CNP_H_4 0xA364 /* Cannon Point H 4 (iTouch) */ | ||
| 139 | |||
| 135 | /* | 140 | /* |
| 136 | * MEI HW Section | 141 | * MEI HW Section |
| 137 | */ | 142 | */ |
diff --git a/drivers/misc/mei/pci-me.c b/drivers/misc/mei/pci-me.c index 4a0ccda4d04b..ea4e152270a3 100644 --- a/drivers/misc/mei/pci-me.c +++ b/drivers/misc/mei/pci-me.c | |||
| @@ -98,6 +98,11 @@ static const struct pci_device_id mei_me_pci_tbl[] = { | |||
| 98 | {MEI_PCI_DEVICE(MEI_DEV_ID_KBP, MEI_ME_PCH8_CFG)}, | 98 | {MEI_PCI_DEVICE(MEI_DEV_ID_KBP, MEI_ME_PCH8_CFG)}, |
| 99 | {MEI_PCI_DEVICE(MEI_DEV_ID_KBP_2, MEI_ME_PCH8_CFG)}, | 99 | {MEI_PCI_DEVICE(MEI_DEV_ID_KBP_2, MEI_ME_PCH8_CFG)}, |
| 100 | 100 | ||
| 101 | {MEI_PCI_DEVICE(MEI_DEV_ID_CNP_LP, MEI_ME_PCH8_CFG)}, | ||
| 102 | {MEI_PCI_DEVICE(MEI_DEV_ID_CNP_LP_4, MEI_ME_PCH8_CFG)}, | ||
| 103 | {MEI_PCI_DEVICE(MEI_DEV_ID_CNP_H, MEI_ME_PCH8_CFG)}, | ||
| 104 | {MEI_PCI_DEVICE(MEI_DEV_ID_CNP_H_4, MEI_ME_PCH8_CFG)}, | ||
| 105 | |||
| 101 | /* required last entry */ | 106 | /* required last entry */ |
| 102 | {0, } | 107 | {0, } |
| 103 | }; | 108 | }; |
diff --git a/drivers/misc/ocxl/file.c b/drivers/misc/ocxl/file.c index d9aa407db06a..337462e1569f 100644 --- a/drivers/misc/ocxl/file.c +++ b/drivers/misc/ocxl/file.c | |||
| @@ -133,8 +133,10 @@ static long afu_ioctl(struct file *file, unsigned int cmd, | |||
| 133 | if (!rc) { | 133 | if (!rc) { |
| 134 | rc = copy_to_user((u64 __user *) args, &irq_offset, | 134 | rc = copy_to_user((u64 __user *) args, &irq_offset, |
| 135 | sizeof(irq_offset)); | 135 | sizeof(irq_offset)); |
| 136 | if (rc) | 136 | if (rc) { |
| 137 | ocxl_afu_irq_free(ctx, irq_offset); | 137 | ocxl_afu_irq_free(ctx, irq_offset); |
| 138 | return -EFAULT; | ||
| 139 | } | ||
| 138 | } | 140 | } |
| 139 | break; | 141 | break; |
| 140 | 142 | ||
| @@ -277,7 +279,7 @@ static ssize_t afu_read(struct file *file, char __user *buf, size_t count, | |||
| 277 | struct ocxl_context *ctx = file->private_data; | 279 | struct ocxl_context *ctx = file->private_data; |
| 278 | struct ocxl_kernel_event_header header; | 280 | struct ocxl_kernel_event_header header; |
| 279 | ssize_t rc; | 281 | ssize_t rc; |
| 280 | size_t used = 0; | 282 | ssize_t used = 0; |
| 281 | DEFINE_WAIT(event_wait); | 283 | DEFINE_WAIT(event_wait); |
| 282 | 284 | ||
| 283 | memset(&header, 0, sizeof(header)); | 285 | memset(&header, 0, sizeof(header)); |
| @@ -329,7 +331,7 @@ static ssize_t afu_read(struct file *file, char __user *buf, size_t count, | |||
| 329 | 331 | ||
| 330 | used += sizeof(header); | 332 | used += sizeof(header); |
| 331 | 333 | ||
| 332 | rc = (ssize_t) used; | 334 | rc = used; |
| 333 | return rc; | 335 | return rc; |
| 334 | } | 336 | } |
| 335 | 337 | ||
diff --git a/drivers/mmc/host/bcm2835.c b/drivers/mmc/host/bcm2835.c index 229dc18f0581..768972af8b85 100644 --- a/drivers/mmc/host/bcm2835.c +++ b/drivers/mmc/host/bcm2835.c | |||
| @@ -1265,7 +1265,8 @@ static int bcm2835_add_host(struct bcm2835_host *host) | |||
| 1265 | char pio_limit_string[20]; | 1265 | char pio_limit_string[20]; |
| 1266 | int ret; | 1266 | int ret; |
| 1267 | 1267 | ||
| 1268 | mmc->f_max = host->max_clk; | 1268 | if (!mmc->f_max || mmc->f_max > host->max_clk) |
| 1269 | mmc->f_max = host->max_clk; | ||
| 1269 | mmc->f_min = host->max_clk / SDCDIV_MAX_CDIV; | 1270 | mmc->f_min = host->max_clk / SDCDIV_MAX_CDIV; |
| 1270 | 1271 | ||
| 1271 | mmc->max_busy_timeout = ~0 / (mmc->f_max / 1000); | 1272 | mmc->max_busy_timeout = ~0 / (mmc->f_max / 1000); |
diff --git a/drivers/mmc/host/meson-gx-mmc.c b/drivers/mmc/host/meson-gx-mmc.c index 22438ebfe4e6..4f972b879fe6 100644 --- a/drivers/mmc/host/meson-gx-mmc.c +++ b/drivers/mmc/host/meson-gx-mmc.c | |||
| @@ -717,22 +717,6 @@ static int meson_mmc_clk_phase_tuning(struct mmc_host *mmc, u32 opcode, | |||
| 717 | static int meson_mmc_execute_tuning(struct mmc_host *mmc, u32 opcode) | 717 | static int meson_mmc_execute_tuning(struct mmc_host *mmc, u32 opcode) |
| 718 | { | 718 | { |
| 719 | struct meson_host *host = mmc_priv(mmc); | 719 | struct meson_host *host = mmc_priv(mmc); |
| 720 | int ret; | ||
| 721 | |||
| 722 | /* | ||
| 723 | * If this is the initial tuning, try to get a sane Rx starting | ||
| 724 | * phase before doing the actual tuning. | ||
| 725 | */ | ||
| 726 | if (!mmc->doing_retune) { | ||
| 727 | ret = meson_mmc_clk_phase_tuning(mmc, opcode, host->rx_clk); | ||
| 728 | |||
| 729 | if (ret) | ||
| 730 | return ret; | ||
| 731 | } | ||
| 732 | |||
| 733 | ret = meson_mmc_clk_phase_tuning(mmc, opcode, host->tx_clk); | ||
| 734 | if (ret) | ||
| 735 | return ret; | ||
| 736 | 720 | ||
| 737 | return meson_mmc_clk_phase_tuning(mmc, opcode, host->rx_clk); | 721 | return meson_mmc_clk_phase_tuning(mmc, opcode, host->rx_clk); |
| 738 | } | 722 | } |
| @@ -763,9 +747,8 @@ static void meson_mmc_set_ios(struct mmc_host *mmc, struct mmc_ios *ios) | |||
| 763 | if (!IS_ERR(mmc->supply.vmmc)) | 747 | if (!IS_ERR(mmc->supply.vmmc)) |
| 764 | mmc_regulator_set_ocr(mmc, mmc->supply.vmmc, ios->vdd); | 748 | mmc_regulator_set_ocr(mmc, mmc->supply.vmmc, ios->vdd); |
| 765 | 749 | ||
| 766 | /* Reset phases */ | 750 | /* Reset rx phase */ |
| 767 | clk_set_phase(host->rx_clk, 0); | 751 | clk_set_phase(host->rx_clk, 0); |
| 768 | clk_set_phase(host->tx_clk, 270); | ||
| 769 | 752 | ||
| 770 | break; | 753 | break; |
| 771 | 754 | ||
diff --git a/drivers/mtd/nand/Kconfig b/drivers/mtd/nand/Kconfig index e6b8c59f2c0d..736ac887303c 100644 --- a/drivers/mtd/nand/Kconfig +++ b/drivers/mtd/nand/Kconfig | |||
| @@ -328,7 +328,7 @@ config MTD_NAND_MARVELL | |||
| 328 | tristate "NAND controller support on Marvell boards" | 328 | tristate "NAND controller support on Marvell boards" |
| 329 | depends on PXA3xx || ARCH_MMP || PLAT_ORION || ARCH_MVEBU || \ | 329 | depends on PXA3xx || ARCH_MMP || PLAT_ORION || ARCH_MVEBU || \ |
| 330 | COMPILE_TEST | 330 | COMPILE_TEST |
| 331 | depends on HAS_IOMEM | 331 | depends on HAS_IOMEM && HAS_DMA |
| 332 | help | 332 | help |
| 333 | This enables the NAND flash controller driver for Marvell boards, | 333 | This enables the NAND flash controller driver for Marvell boards, |
| 334 | including: | 334 | including: |
diff --git a/drivers/mtd/nand/vf610_nfc.c b/drivers/mtd/nand/vf610_nfc.c index 80d31a58e558..f367144f3c6f 100644 --- a/drivers/mtd/nand/vf610_nfc.c +++ b/drivers/mtd/nand/vf610_nfc.c | |||
| @@ -752,10 +752,8 @@ static int vf610_nfc_probe(struct platform_device *pdev) | |||
| 752 | if (mtd->oobsize > 64) | 752 | if (mtd->oobsize > 64) |
| 753 | mtd->oobsize = 64; | 753 | mtd->oobsize = 64; |
| 754 | 754 | ||
| 755 | /* | 755 | /* Use default large page ECC layout defined in NAND core */ |
| 756 | * mtd->ecclayout is not specified here because we're using the | 756 | mtd_set_ooblayout(mtd, &nand_ooblayout_lp_ops); |
| 757 | * default large page ECC layout defined in NAND core. | ||
| 758 | */ | ||
| 759 | if (chip->ecc.strength == 32) { | 757 | if (chip->ecc.strength == 32) { |
| 760 | nfc->ecc_mode = ECC_60_BYTE; | 758 | nfc->ecc_mode = ECC_60_BYTE; |
| 761 | chip->ecc.bytes = 60; | 759 | chip->ecc.bytes = 60; |
diff --git a/drivers/net/ethernet/amd/xgbe/xgbe-pci.c b/drivers/net/ethernet/amd/xgbe/xgbe-pci.c index 3e5833cf1fab..eb23f9ba1a9a 100644 --- a/drivers/net/ethernet/amd/xgbe/xgbe-pci.c +++ b/drivers/net/ethernet/amd/xgbe/xgbe-pci.c | |||
| @@ -426,6 +426,8 @@ static int xgbe_pci_resume(struct pci_dev *pdev) | |||
| 426 | struct net_device *netdev = pdata->netdev; | 426 | struct net_device *netdev = pdata->netdev; |
| 427 | int ret = 0; | 427 | int ret = 0; |
| 428 | 428 | ||
| 429 | XP_IOWRITE(pdata, XP_INT_EN, 0x1fffff); | ||
| 430 | |||
| 429 | pdata->lpm_ctrl &= ~MDIO_CTRL1_LPOWER; | 431 | pdata->lpm_ctrl &= ~MDIO_CTRL1_LPOWER; |
| 430 | XMDIO_WRITE(pdata, MDIO_MMD_PCS, MDIO_CTRL1, pdata->lpm_ctrl); | 432 | XMDIO_WRITE(pdata, MDIO_MMD_PCS, MDIO_CTRL1, pdata->lpm_ctrl); |
| 431 | 433 | ||
diff --git a/drivers/net/ethernet/aquantia/atlantic/aq_pci_func.c b/drivers/net/ethernet/aquantia/atlantic/aq_pci_func.c index 22889fc158f2..87c4308b52a7 100644 --- a/drivers/net/ethernet/aquantia/atlantic/aq_pci_func.c +++ b/drivers/net/ethernet/aquantia/atlantic/aq_pci_func.c | |||
| @@ -226,6 +226,10 @@ static int aq_pci_probe(struct pci_dev *pdev, | |||
| 226 | goto err_ioremap; | 226 | goto err_ioremap; |
| 227 | 227 | ||
| 228 | self->aq_hw = kzalloc(sizeof(*self->aq_hw), GFP_KERNEL); | 228 | self->aq_hw = kzalloc(sizeof(*self->aq_hw), GFP_KERNEL); |
| 229 | if (!self->aq_hw) { | ||
| 230 | err = -ENOMEM; | ||
| 231 | goto err_ioremap; | ||
| 232 | } | ||
| 229 | self->aq_hw->aq_nic_cfg = aq_nic_get_cfg(self); | 233 | self->aq_hw->aq_nic_cfg = aq_nic_get_cfg(self); |
| 230 | 234 | ||
| 231 | for (bar = 0; bar < 4; ++bar) { | 235 | for (bar = 0; bar < 4; ++bar) { |
| @@ -235,19 +239,19 @@ static int aq_pci_probe(struct pci_dev *pdev, | |||
| 235 | mmio_pa = pci_resource_start(pdev, bar); | 239 | mmio_pa = pci_resource_start(pdev, bar); |
| 236 | if (mmio_pa == 0U) { | 240 | if (mmio_pa == 0U) { |
| 237 | err = -EIO; | 241 | err = -EIO; |
| 238 | goto err_ioremap; | 242 | goto err_free_aq_hw; |
| 239 | } | 243 | } |
| 240 | 244 | ||
| 241 | reg_sz = pci_resource_len(pdev, bar); | 245 | reg_sz = pci_resource_len(pdev, bar); |
| 242 | if ((reg_sz <= 24 /*ATL_REGS_SIZE*/)) { | 246 | if ((reg_sz <= 24 /*ATL_REGS_SIZE*/)) { |
| 243 | err = -EIO; | 247 | err = -EIO; |
| 244 | goto err_ioremap; | 248 | goto err_free_aq_hw; |
| 245 | } | 249 | } |
| 246 | 250 | ||
| 247 | self->aq_hw->mmio = ioremap_nocache(mmio_pa, reg_sz); | 251 | self->aq_hw->mmio = ioremap_nocache(mmio_pa, reg_sz); |
| 248 | if (!self->aq_hw->mmio) { | 252 | if (!self->aq_hw->mmio) { |
| 249 | err = -EIO; | 253 | err = -EIO; |
| 250 | goto err_ioremap; | 254 | goto err_free_aq_hw; |
| 251 | } | 255 | } |
| 252 | break; | 256 | break; |
| 253 | } | 257 | } |
| @@ -255,7 +259,7 @@ static int aq_pci_probe(struct pci_dev *pdev, | |||
| 255 | 259 | ||
| 256 | if (bar == 4) { | 260 | if (bar == 4) { |
| 257 | err = -EIO; | 261 | err = -EIO; |
| 258 | goto err_ioremap; | 262 | goto err_free_aq_hw; |
| 259 | } | 263 | } |
| 260 | 264 | ||
| 261 | numvecs = min((u8)AQ_CFG_VECS_DEF, | 265 | numvecs = min((u8)AQ_CFG_VECS_DEF, |
| @@ -290,6 +294,8 @@ err_register: | |||
| 290 | aq_pci_free_irq_vectors(self); | 294 | aq_pci_free_irq_vectors(self); |
| 291 | err_hwinit: | 295 | err_hwinit: |
| 292 | iounmap(self->aq_hw->mmio); | 296 | iounmap(self->aq_hw->mmio); |
| 297 | err_free_aq_hw: | ||
| 298 | kfree(self->aq_hw); | ||
| 293 | err_ioremap: | 299 | err_ioremap: |
| 294 | free_netdev(ndev); | 300 | free_netdev(ndev); |
| 295 | err_pci_func: | 301 | err_pci_func: |
diff --git a/drivers/net/ethernet/broadcom/tg3.c b/drivers/net/ethernet/broadcom/tg3.c index a77ee2f8fb8d..c1841db1b500 100644 --- a/drivers/net/ethernet/broadcom/tg3.c +++ b/drivers/net/ethernet/broadcom/tg3.c | |||
| @@ -820,7 +820,7 @@ static int tg3_ape_event_lock(struct tg3 *tp, u32 timeout_us) | |||
| 820 | 820 | ||
| 821 | tg3_ape_unlock(tp, TG3_APE_LOCK_MEM); | 821 | tg3_ape_unlock(tp, TG3_APE_LOCK_MEM); |
| 822 | 822 | ||
| 823 | udelay(10); | 823 | usleep_range(10, 20); |
| 824 | timeout_us -= (timeout_us > 10) ? 10 : timeout_us; | 824 | timeout_us -= (timeout_us > 10) ? 10 : timeout_us; |
| 825 | } | 825 | } |
| 826 | 826 | ||
| @@ -922,8 +922,8 @@ static int tg3_ape_send_event(struct tg3 *tp, u32 event) | |||
| 922 | if (!(apedata & APE_FW_STATUS_READY)) | 922 | if (!(apedata & APE_FW_STATUS_READY)) |
| 923 | return -EAGAIN; | 923 | return -EAGAIN; |
| 924 | 924 | ||
| 925 | /* Wait for up to 1 millisecond for APE to service previous event. */ | 925 | /* Wait for up to 20 millisecond for APE to service previous event. */ |
| 926 | err = tg3_ape_event_lock(tp, 1000); | 926 | err = tg3_ape_event_lock(tp, 20000); |
| 927 | if (err) | 927 | if (err) |
| 928 | return err; | 928 | return err; |
| 929 | 929 | ||
| @@ -946,6 +946,7 @@ static void tg3_ape_driver_state_change(struct tg3 *tp, int kind) | |||
| 946 | 946 | ||
| 947 | switch (kind) { | 947 | switch (kind) { |
| 948 | case RESET_KIND_INIT: | 948 | case RESET_KIND_INIT: |
| 949 | tg3_ape_write32(tp, TG3_APE_HOST_HEARTBEAT_COUNT, tp->ape_hb++); | ||
| 949 | tg3_ape_write32(tp, TG3_APE_HOST_SEG_SIG, | 950 | tg3_ape_write32(tp, TG3_APE_HOST_SEG_SIG, |
| 950 | APE_HOST_SEG_SIG_MAGIC); | 951 | APE_HOST_SEG_SIG_MAGIC); |
| 951 | tg3_ape_write32(tp, TG3_APE_HOST_SEG_LEN, | 952 | tg3_ape_write32(tp, TG3_APE_HOST_SEG_LEN, |
| @@ -962,13 +963,6 @@ static void tg3_ape_driver_state_change(struct tg3 *tp, int kind) | |||
| 962 | event = APE_EVENT_STATUS_STATE_START; | 963 | event = APE_EVENT_STATUS_STATE_START; |
| 963 | break; | 964 | break; |
| 964 | case RESET_KIND_SHUTDOWN: | 965 | case RESET_KIND_SHUTDOWN: |
| 965 | /* With the interface we are currently using, | ||
| 966 | * APE does not track driver state. Wiping | ||
| 967 | * out the HOST SEGMENT SIGNATURE forces | ||
| 968 | * the APE to assume OS absent status. | ||
| 969 | */ | ||
| 970 | tg3_ape_write32(tp, TG3_APE_HOST_SEG_SIG, 0x0); | ||
| 971 | |||
| 972 | if (device_may_wakeup(&tp->pdev->dev) && | 966 | if (device_may_wakeup(&tp->pdev->dev) && |
| 973 | tg3_flag(tp, WOL_ENABLE)) { | 967 | tg3_flag(tp, WOL_ENABLE)) { |
| 974 | tg3_ape_write32(tp, TG3_APE_HOST_WOL_SPEED, | 968 | tg3_ape_write32(tp, TG3_APE_HOST_WOL_SPEED, |
| @@ -990,6 +984,18 @@ static void tg3_ape_driver_state_change(struct tg3 *tp, int kind) | |||
| 990 | tg3_ape_send_event(tp, event); | 984 | tg3_ape_send_event(tp, event); |
| 991 | } | 985 | } |
| 992 | 986 | ||
| 987 | static void tg3_send_ape_heartbeat(struct tg3 *tp, | ||
| 988 | unsigned long interval) | ||
| 989 | { | ||
| 990 | /* Check if hb interval has exceeded */ | ||
| 991 | if (!tg3_flag(tp, ENABLE_APE) || | ||
| 992 | time_before(jiffies, tp->ape_hb_jiffies + interval)) | ||
| 993 | return; | ||
| 994 | |||
| 995 | tg3_ape_write32(tp, TG3_APE_HOST_HEARTBEAT_COUNT, tp->ape_hb++); | ||
| 996 | tp->ape_hb_jiffies = jiffies; | ||
| 997 | } | ||
| 998 | |||
| 993 | static void tg3_disable_ints(struct tg3 *tp) | 999 | static void tg3_disable_ints(struct tg3 *tp) |
| 994 | { | 1000 | { |
| 995 | int i; | 1001 | int i; |
| @@ -7262,6 +7268,7 @@ static int tg3_poll_msix(struct napi_struct *napi, int budget) | |||
| 7262 | } | 7268 | } |
| 7263 | } | 7269 | } |
| 7264 | 7270 | ||
| 7271 | tg3_send_ape_heartbeat(tp, TG3_APE_HB_INTERVAL << 1); | ||
| 7265 | return work_done; | 7272 | return work_done; |
| 7266 | 7273 | ||
| 7267 | tx_recovery: | 7274 | tx_recovery: |
| @@ -7344,6 +7351,7 @@ static int tg3_poll(struct napi_struct *napi, int budget) | |||
| 7344 | } | 7351 | } |
| 7345 | } | 7352 | } |
| 7346 | 7353 | ||
| 7354 | tg3_send_ape_heartbeat(tp, TG3_APE_HB_INTERVAL << 1); | ||
| 7347 | return work_done; | 7355 | return work_done; |
| 7348 | 7356 | ||
| 7349 | tx_recovery: | 7357 | tx_recovery: |
| @@ -10732,7 +10740,7 @@ static int tg3_reset_hw(struct tg3 *tp, bool reset_phy) | |||
| 10732 | if (tg3_flag(tp, ENABLE_APE)) | 10740 | if (tg3_flag(tp, ENABLE_APE)) |
| 10733 | /* Write our heartbeat update interval to APE. */ | 10741 | /* Write our heartbeat update interval to APE. */ |
| 10734 | tg3_ape_write32(tp, TG3_APE_HOST_HEARTBEAT_INT_MS, | 10742 | tg3_ape_write32(tp, TG3_APE_HOST_HEARTBEAT_INT_MS, |
| 10735 | APE_HOST_HEARTBEAT_INT_DISABLE); | 10743 | APE_HOST_HEARTBEAT_INT_5SEC); |
| 10736 | 10744 | ||
| 10737 | tg3_write_sig_post_reset(tp, RESET_KIND_INIT); | 10745 | tg3_write_sig_post_reset(tp, RESET_KIND_INIT); |
| 10738 | 10746 | ||
| @@ -11077,6 +11085,9 @@ static void tg3_timer(struct timer_list *t) | |||
| 11077 | tp->asf_counter = tp->asf_multiplier; | 11085 | tp->asf_counter = tp->asf_multiplier; |
| 11078 | } | 11086 | } |
| 11079 | 11087 | ||
| 11088 | /* Update the APE heartbeat every 5 seconds.*/ | ||
| 11089 | tg3_send_ape_heartbeat(tp, TG3_APE_HB_INTERVAL); | ||
| 11090 | |||
| 11080 | spin_unlock(&tp->lock); | 11091 | spin_unlock(&tp->lock); |
| 11081 | 11092 | ||
| 11082 | restart_timer: | 11093 | restart_timer: |
| @@ -16653,6 +16664,8 @@ static int tg3_get_invariants(struct tg3 *tp, const struct pci_device_id *ent) | |||
| 16653 | pci_state_reg); | 16664 | pci_state_reg); |
| 16654 | 16665 | ||
| 16655 | tg3_ape_lock_init(tp); | 16666 | tg3_ape_lock_init(tp); |
| 16667 | tp->ape_hb_interval = | ||
| 16668 | msecs_to_jiffies(APE_HOST_HEARTBEAT_INT_5SEC); | ||
| 16656 | } | 16669 | } |
| 16657 | 16670 | ||
| 16658 | /* Set up tp->grc_local_ctrl before calling | 16671 | /* Set up tp->grc_local_ctrl before calling |
diff --git a/drivers/net/ethernet/broadcom/tg3.h b/drivers/net/ethernet/broadcom/tg3.h index 47f51cc0566d..1d61aa3efda1 100644 --- a/drivers/net/ethernet/broadcom/tg3.h +++ b/drivers/net/ethernet/broadcom/tg3.h | |||
| @@ -2508,6 +2508,7 @@ | |||
| 2508 | #define TG3_APE_LOCK_PHY3 5 | 2508 | #define TG3_APE_LOCK_PHY3 5 |
| 2509 | #define TG3_APE_LOCK_GPIO 7 | 2509 | #define TG3_APE_LOCK_GPIO 7 |
| 2510 | 2510 | ||
| 2511 | #define TG3_APE_HB_INTERVAL (tp->ape_hb_interval) | ||
| 2511 | #define TG3_EEPROM_SB_F1R2_MBA_OFF 0x10 | 2512 | #define TG3_EEPROM_SB_F1R2_MBA_OFF 0x10 |
| 2512 | 2513 | ||
| 2513 | 2514 | ||
| @@ -3423,6 +3424,10 @@ struct tg3 { | |||
| 3423 | struct device *hwmon_dev; | 3424 | struct device *hwmon_dev; |
| 3424 | bool link_up; | 3425 | bool link_up; |
| 3425 | bool pcierr_recovery; | 3426 | bool pcierr_recovery; |
| 3427 | |||
| 3428 | u32 ape_hb; | ||
| 3429 | unsigned long ape_hb_interval; | ||
| 3430 | unsigned long ape_hb_jiffies; | ||
| 3426 | }; | 3431 | }; |
| 3427 | 3432 | ||
| 3428 | /* Accessor macros for chip and asic attributes | 3433 | /* Accessor macros for chip and asic attributes |
diff --git a/drivers/net/ethernet/cavium/common/cavium_ptp.c b/drivers/net/ethernet/cavium/common/cavium_ptp.c index c87c9c684a33..d59497a7bdce 100644 --- a/drivers/net/ethernet/cavium/common/cavium_ptp.c +++ b/drivers/net/ethernet/cavium/common/cavium_ptp.c | |||
| @@ -75,6 +75,8 @@ EXPORT_SYMBOL(cavium_ptp_get); | |||
| 75 | 75 | ||
| 76 | void cavium_ptp_put(struct cavium_ptp *ptp) | 76 | void cavium_ptp_put(struct cavium_ptp *ptp) |
| 77 | { | 77 | { |
| 78 | if (!ptp) | ||
| 79 | return; | ||
| 78 | pci_dev_put(ptp->pdev); | 80 | pci_dev_put(ptp->pdev); |
| 79 | } | 81 | } |
| 80 | EXPORT_SYMBOL(cavium_ptp_put); | 82 | EXPORT_SYMBOL(cavium_ptp_put); |
diff --git a/drivers/net/ethernet/cavium/thunder/nicvf_main.c b/drivers/net/ethernet/cavium/thunder/nicvf_main.c index b68cde9f17d2..7d9c5ffbd041 100644 --- a/drivers/net/ethernet/cavium/thunder/nicvf_main.c +++ b/drivers/net/ethernet/cavium/thunder/nicvf_main.c | |||
| @@ -67,11 +67,6 @@ module_param(cpi_alg, int, S_IRUGO); | |||
| 67 | MODULE_PARM_DESC(cpi_alg, | 67 | MODULE_PARM_DESC(cpi_alg, |
| 68 | "PFC algorithm (0=none, 1=VLAN, 2=VLAN16, 3=IP Diffserv)"); | 68 | "PFC algorithm (0=none, 1=VLAN, 2=VLAN16, 3=IP Diffserv)"); |
| 69 | 69 | ||
| 70 | struct nicvf_xdp_tx { | ||
| 71 | u64 dma_addr; | ||
| 72 | u8 qidx; | ||
| 73 | }; | ||
| 74 | |||
| 75 | static inline u8 nicvf_netdev_qidx(struct nicvf *nic, u8 qidx) | 70 | static inline u8 nicvf_netdev_qidx(struct nicvf *nic, u8 qidx) |
| 76 | { | 71 | { |
| 77 | if (nic->sqs_mode) | 72 | if (nic->sqs_mode) |
| @@ -507,29 +502,14 @@ static int nicvf_init_resources(struct nicvf *nic) | |||
| 507 | return 0; | 502 | return 0; |
| 508 | } | 503 | } |
| 509 | 504 | ||
| 510 | static void nicvf_unmap_page(struct nicvf *nic, struct page *page, u64 dma_addr) | ||
| 511 | { | ||
| 512 | /* Check if it's a recycled page, if not unmap the DMA mapping. | ||
| 513 | * Recycled page holds an extra reference. | ||
| 514 | */ | ||
| 515 | if (page_ref_count(page) == 1) { | ||
| 516 | dma_addr &= PAGE_MASK; | ||
| 517 | dma_unmap_page_attrs(&nic->pdev->dev, dma_addr, | ||
| 518 | RCV_FRAG_LEN + XDP_HEADROOM, | ||
| 519 | DMA_FROM_DEVICE, | ||
| 520 | DMA_ATTR_SKIP_CPU_SYNC); | ||
| 521 | } | ||
| 522 | } | ||
| 523 | |||
| 524 | static inline bool nicvf_xdp_rx(struct nicvf *nic, struct bpf_prog *prog, | 505 | static inline bool nicvf_xdp_rx(struct nicvf *nic, struct bpf_prog *prog, |
| 525 | struct cqe_rx_t *cqe_rx, struct snd_queue *sq, | 506 | struct cqe_rx_t *cqe_rx, struct snd_queue *sq, |
| 526 | struct rcv_queue *rq, struct sk_buff **skb) | 507 | struct rcv_queue *rq, struct sk_buff **skb) |
| 527 | { | 508 | { |
| 528 | struct xdp_buff xdp; | 509 | struct xdp_buff xdp; |
| 529 | struct page *page; | 510 | struct page *page; |
| 530 | struct nicvf_xdp_tx *xdp_tx = NULL; | ||
| 531 | u32 action; | 511 | u32 action; |
| 532 | u16 len, err, offset = 0; | 512 | u16 len, offset = 0; |
| 533 | u64 dma_addr, cpu_addr; | 513 | u64 dma_addr, cpu_addr; |
| 534 | void *orig_data; | 514 | void *orig_data; |
| 535 | 515 | ||
| @@ -543,7 +523,7 @@ static inline bool nicvf_xdp_rx(struct nicvf *nic, struct bpf_prog *prog, | |||
| 543 | cpu_addr = (u64)phys_to_virt(cpu_addr); | 523 | cpu_addr = (u64)phys_to_virt(cpu_addr); |
| 544 | page = virt_to_page((void *)cpu_addr); | 524 | page = virt_to_page((void *)cpu_addr); |
| 545 | 525 | ||
| 546 | xdp.data_hard_start = page_address(page) + RCV_BUF_HEADROOM; | 526 | xdp.data_hard_start = page_address(page); |
| 547 | xdp.data = (void *)cpu_addr; | 527 | xdp.data = (void *)cpu_addr; |
| 548 | xdp_set_data_meta_invalid(&xdp); | 528 | xdp_set_data_meta_invalid(&xdp); |
| 549 | xdp.data_end = xdp.data + len; | 529 | xdp.data_end = xdp.data + len; |
| @@ -563,7 +543,18 @@ static inline bool nicvf_xdp_rx(struct nicvf *nic, struct bpf_prog *prog, | |||
| 563 | 543 | ||
| 564 | switch (action) { | 544 | switch (action) { |
| 565 | case XDP_PASS: | 545 | case XDP_PASS: |
| 566 | nicvf_unmap_page(nic, page, dma_addr); | 546 | /* Check if it's a recycled page, if not |
| 547 | * unmap the DMA mapping. | ||
| 548 | * | ||
| 549 | * Recycled page holds an extra reference. | ||
| 550 | */ | ||
| 551 | if (page_ref_count(page) == 1) { | ||
| 552 | dma_addr &= PAGE_MASK; | ||
| 553 | dma_unmap_page_attrs(&nic->pdev->dev, dma_addr, | ||
| 554 | RCV_FRAG_LEN + XDP_PACKET_HEADROOM, | ||
| 555 | DMA_FROM_DEVICE, | ||
| 556 | DMA_ATTR_SKIP_CPU_SYNC); | ||
| 557 | } | ||
| 567 | 558 | ||
| 568 | /* Build SKB and pass on packet to network stack */ | 559 | /* Build SKB and pass on packet to network stack */ |
| 569 | *skb = build_skb(xdp.data, | 560 | *skb = build_skb(xdp.data, |
| @@ -576,20 +567,6 @@ static inline bool nicvf_xdp_rx(struct nicvf *nic, struct bpf_prog *prog, | |||
| 576 | case XDP_TX: | 567 | case XDP_TX: |
| 577 | nicvf_xdp_sq_append_pkt(nic, sq, (u64)xdp.data, dma_addr, len); | 568 | nicvf_xdp_sq_append_pkt(nic, sq, (u64)xdp.data, dma_addr, len); |
| 578 | return true; | 569 | return true; |
| 579 | case XDP_REDIRECT: | ||
| 580 | /* Save DMA address for use while transmitting */ | ||
| 581 | xdp_tx = (struct nicvf_xdp_tx *)page_address(page); | ||
| 582 | xdp_tx->dma_addr = dma_addr; | ||
| 583 | xdp_tx->qidx = nicvf_netdev_qidx(nic, cqe_rx->rq_idx); | ||
| 584 | |||
| 585 | err = xdp_do_redirect(nic->pnicvf->netdev, &xdp, prog); | ||
| 586 | if (!err) | ||
| 587 | return true; | ||
| 588 | |||
| 589 | /* Free the page on error */ | ||
| 590 | nicvf_unmap_page(nic, page, dma_addr); | ||
| 591 | put_page(page); | ||
| 592 | break; | ||
| 593 | default: | 570 | default: |
| 594 | bpf_warn_invalid_xdp_action(action); | 571 | bpf_warn_invalid_xdp_action(action); |
| 595 | /* fall through */ | 572 | /* fall through */ |
| @@ -597,7 +574,18 @@ static inline bool nicvf_xdp_rx(struct nicvf *nic, struct bpf_prog *prog, | |||
| 597 | trace_xdp_exception(nic->netdev, prog, action); | 574 | trace_xdp_exception(nic->netdev, prog, action); |
| 598 | /* fall through */ | 575 | /* fall through */ |
| 599 | case XDP_DROP: | 576 | case XDP_DROP: |
| 600 | nicvf_unmap_page(nic, page, dma_addr); | 577 | /* Check if it's a recycled page, if not |
| 578 | * unmap the DMA mapping. | ||
| 579 | * | ||
| 580 | * Recycled page holds an extra reference. | ||
| 581 | */ | ||
| 582 | if (page_ref_count(page) == 1) { | ||
| 583 | dma_addr &= PAGE_MASK; | ||
| 584 | dma_unmap_page_attrs(&nic->pdev->dev, dma_addr, | ||
| 585 | RCV_FRAG_LEN + XDP_PACKET_HEADROOM, | ||
| 586 | DMA_FROM_DEVICE, | ||
| 587 | DMA_ATTR_SKIP_CPU_SYNC); | ||
| 588 | } | ||
| 601 | put_page(page); | 589 | put_page(page); |
| 602 | return true; | 590 | return true; |
| 603 | } | 591 | } |
| @@ -1864,50 +1852,6 @@ static int nicvf_xdp(struct net_device *netdev, struct netdev_bpf *xdp) | |||
| 1864 | } | 1852 | } |
| 1865 | } | 1853 | } |
| 1866 | 1854 | ||
| 1867 | static int nicvf_xdp_xmit(struct net_device *netdev, struct xdp_buff *xdp) | ||
| 1868 | { | ||
| 1869 | struct nicvf *nic = netdev_priv(netdev); | ||
| 1870 | struct nicvf *snic = nic; | ||
| 1871 | struct nicvf_xdp_tx *xdp_tx; | ||
| 1872 | struct snd_queue *sq; | ||
| 1873 | struct page *page; | ||
| 1874 | int err, qidx; | ||
| 1875 | |||
| 1876 | if (!netif_running(netdev) || !nic->xdp_prog) | ||
| 1877 | return -EINVAL; | ||
| 1878 | |||
| 1879 | page = virt_to_page(xdp->data); | ||
| 1880 | xdp_tx = (struct nicvf_xdp_tx *)page_address(page); | ||
| 1881 | qidx = xdp_tx->qidx; | ||
| 1882 | |||
| 1883 | if (xdp_tx->qidx >= nic->xdp_tx_queues) | ||
| 1884 | return -EINVAL; | ||
| 1885 | |||
| 1886 | /* Get secondary Qset's info */ | ||
| 1887 | if (xdp_tx->qidx >= MAX_SND_QUEUES_PER_QS) { | ||
| 1888 | qidx = xdp_tx->qidx / MAX_SND_QUEUES_PER_QS; | ||
| 1889 | snic = (struct nicvf *)nic->snicvf[qidx - 1]; | ||
| 1890 | if (!snic) | ||
| 1891 | return -EINVAL; | ||
| 1892 | qidx = xdp_tx->qidx % MAX_SND_QUEUES_PER_QS; | ||
| 1893 | } | ||
| 1894 | |||
| 1895 | sq = &snic->qs->sq[qidx]; | ||
| 1896 | err = nicvf_xdp_sq_append_pkt(snic, sq, (u64)xdp->data, | ||
| 1897 | xdp_tx->dma_addr, | ||
| 1898 | xdp->data_end - xdp->data); | ||
| 1899 | if (err) | ||
| 1900 | return -ENOMEM; | ||
| 1901 | |||
| 1902 | nicvf_xdp_sq_doorbell(snic, sq, qidx); | ||
| 1903 | return 0; | ||
| 1904 | } | ||
| 1905 | |||
| 1906 | static void nicvf_xdp_flush(struct net_device *dev) | ||
| 1907 | { | ||
| 1908 | return; | ||
| 1909 | } | ||
| 1910 | |||
| 1911 | static int nicvf_config_hwtstamp(struct net_device *netdev, struct ifreq *ifr) | 1855 | static int nicvf_config_hwtstamp(struct net_device *netdev, struct ifreq *ifr) |
| 1912 | { | 1856 | { |
| 1913 | struct hwtstamp_config config; | 1857 | struct hwtstamp_config config; |
| @@ -1986,8 +1930,6 @@ static const struct net_device_ops nicvf_netdev_ops = { | |||
| 1986 | .ndo_fix_features = nicvf_fix_features, | 1930 | .ndo_fix_features = nicvf_fix_features, |
| 1987 | .ndo_set_features = nicvf_set_features, | 1931 | .ndo_set_features = nicvf_set_features, |
| 1988 | .ndo_bpf = nicvf_xdp, | 1932 | .ndo_bpf = nicvf_xdp, |
| 1989 | .ndo_xdp_xmit = nicvf_xdp_xmit, | ||
| 1990 | .ndo_xdp_flush = nicvf_xdp_flush, | ||
| 1991 | .ndo_do_ioctl = nicvf_ioctl, | 1933 | .ndo_do_ioctl = nicvf_ioctl, |
| 1992 | }; | 1934 | }; |
| 1993 | 1935 | ||
diff --git a/drivers/net/ethernet/cavium/thunder/nicvf_queues.c b/drivers/net/ethernet/cavium/thunder/nicvf_queues.c index 3eae9ff9b53a..d42704d07484 100644 --- a/drivers/net/ethernet/cavium/thunder/nicvf_queues.c +++ b/drivers/net/ethernet/cavium/thunder/nicvf_queues.c | |||
| @@ -204,7 +204,7 @@ static inline int nicvf_alloc_rcv_buffer(struct nicvf *nic, struct rbdr *rbdr, | |||
| 204 | 204 | ||
| 205 | /* Reserve space for header modifications by BPF program */ | 205 | /* Reserve space for header modifications by BPF program */ |
| 206 | if (rbdr->is_xdp) | 206 | if (rbdr->is_xdp) |
| 207 | buf_len += XDP_HEADROOM; | 207 | buf_len += XDP_PACKET_HEADROOM; |
| 208 | 208 | ||
| 209 | /* Check if it's recycled */ | 209 | /* Check if it's recycled */ |
| 210 | if (pgcache) | 210 | if (pgcache) |
| @@ -224,9 +224,8 @@ ret: | |||
| 224 | nic->rb_page = NULL; | 224 | nic->rb_page = NULL; |
| 225 | return -ENOMEM; | 225 | return -ENOMEM; |
| 226 | } | 226 | } |
| 227 | |||
| 228 | if (pgcache) | 227 | if (pgcache) |
| 229 | pgcache->dma_addr = *rbuf + XDP_HEADROOM; | 228 | pgcache->dma_addr = *rbuf + XDP_PACKET_HEADROOM; |
| 230 | nic->rb_page_offset += buf_len; | 229 | nic->rb_page_offset += buf_len; |
| 231 | } | 230 | } |
| 232 | 231 | ||
| @@ -1244,7 +1243,7 @@ int nicvf_xdp_sq_append_pkt(struct nicvf *nic, struct snd_queue *sq, | |||
| 1244 | int qentry; | 1243 | int qentry; |
| 1245 | 1244 | ||
| 1246 | if (subdesc_cnt > sq->xdp_free_cnt) | 1245 | if (subdesc_cnt > sq->xdp_free_cnt) |
| 1247 | return -1; | 1246 | return 0; |
| 1248 | 1247 | ||
| 1249 | qentry = nicvf_get_sq_desc(sq, subdesc_cnt); | 1248 | qentry = nicvf_get_sq_desc(sq, subdesc_cnt); |
| 1250 | 1249 | ||
| @@ -1255,7 +1254,7 @@ int nicvf_xdp_sq_append_pkt(struct nicvf *nic, struct snd_queue *sq, | |||
| 1255 | 1254 | ||
| 1256 | sq->xdp_desc_cnt += subdesc_cnt; | 1255 | sq->xdp_desc_cnt += subdesc_cnt; |
| 1257 | 1256 | ||
| 1258 | return 0; | 1257 | return 1; |
| 1259 | } | 1258 | } |
| 1260 | 1259 | ||
| 1261 | /* Calculate no of SQ subdescriptors needed to transmit all | 1260 | /* Calculate no of SQ subdescriptors needed to transmit all |
| @@ -1656,7 +1655,7 @@ static void nicvf_unmap_rcv_buffer(struct nicvf *nic, u64 dma_addr, | |||
| 1656 | if (page_ref_count(page) != 1) | 1655 | if (page_ref_count(page) != 1) |
| 1657 | return; | 1656 | return; |
| 1658 | 1657 | ||
| 1659 | len += XDP_HEADROOM; | 1658 | len += XDP_PACKET_HEADROOM; |
| 1660 | /* Receive buffers in XDP mode are mapped from page start */ | 1659 | /* Receive buffers in XDP mode are mapped from page start */ |
| 1661 | dma_addr &= PAGE_MASK; | 1660 | dma_addr &= PAGE_MASK; |
| 1662 | } | 1661 | } |
diff --git a/drivers/net/ethernet/cavium/thunder/nicvf_queues.h b/drivers/net/ethernet/cavium/thunder/nicvf_queues.h index ce1eed7a6d63..5e9a03cf1b4d 100644 --- a/drivers/net/ethernet/cavium/thunder/nicvf_queues.h +++ b/drivers/net/ethernet/cavium/thunder/nicvf_queues.h | |||
| @@ -11,7 +11,6 @@ | |||
| 11 | 11 | ||
| 12 | #include <linux/netdevice.h> | 12 | #include <linux/netdevice.h> |
| 13 | #include <linux/iommu.h> | 13 | #include <linux/iommu.h> |
| 14 | #include <linux/bpf.h> | ||
| 15 | #include <net/xdp.h> | 14 | #include <net/xdp.h> |
| 16 | #include "q_struct.h" | 15 | #include "q_struct.h" |
| 17 | 16 | ||
| @@ -94,9 +93,6 @@ | |||
| 94 | #define RCV_FRAG_LEN (SKB_DATA_ALIGN(DMA_BUFFER_LEN + NET_SKB_PAD) + \ | 93 | #define RCV_FRAG_LEN (SKB_DATA_ALIGN(DMA_BUFFER_LEN + NET_SKB_PAD) + \ |
| 95 | SKB_DATA_ALIGN(sizeof(struct skb_shared_info))) | 94 | SKB_DATA_ALIGN(sizeof(struct skb_shared_info))) |
| 96 | 95 | ||
| 97 | #define RCV_BUF_HEADROOM 128 /* To store dma address for XDP redirect */ | ||
| 98 | #define XDP_HEADROOM (XDP_PACKET_HEADROOM + RCV_BUF_HEADROOM) | ||
| 99 | |||
| 100 | #define MAX_CQES_FOR_TX ((SND_QUEUE_LEN / MIN_SQ_DESC_PER_PKT_XMIT) * \ | 96 | #define MAX_CQES_FOR_TX ((SND_QUEUE_LEN / MIN_SQ_DESC_PER_PKT_XMIT) * \ |
| 101 | MAX_CQE_PER_PKT_XMIT) | 97 | MAX_CQE_PER_PKT_XMIT) |
| 102 | 98 | ||
diff --git a/drivers/net/ethernet/chelsio/cxgb4/cudbg_lib.c b/drivers/net/ethernet/chelsio/cxgb4/cudbg_lib.c index 557fd8bfd54e..00a1d2d13169 100644 --- a/drivers/net/ethernet/chelsio/cxgb4/cudbg_lib.c +++ b/drivers/net/ethernet/chelsio/cxgb4/cudbg_lib.c | |||
| @@ -472,7 +472,7 @@ int cudbg_collect_cim_la(struct cudbg_init *pdbg_init, | |||
| 472 | 472 | ||
| 473 | if (is_t6(padap->params.chip)) { | 473 | if (is_t6(padap->params.chip)) { |
| 474 | size = padap->params.cim_la_size / 10 + 1; | 474 | size = padap->params.cim_la_size / 10 + 1; |
| 475 | size *= 11 * sizeof(u32); | 475 | size *= 10 * sizeof(u32); |
| 476 | } else { | 476 | } else { |
| 477 | size = padap->params.cim_la_size / 8; | 477 | size = padap->params.cim_la_size / 8; |
| 478 | size *= 8 * sizeof(u32); | 478 | size *= 8 * sizeof(u32); |
diff --git a/drivers/net/ethernet/chelsio/cxgb4/cxgb4_cudbg.c b/drivers/net/ethernet/chelsio/cxgb4/cxgb4_cudbg.c index 30485f9a598f..143686c60234 100644 --- a/drivers/net/ethernet/chelsio/cxgb4/cxgb4_cudbg.c +++ b/drivers/net/ethernet/chelsio/cxgb4/cxgb4_cudbg.c | |||
| @@ -102,7 +102,7 @@ static u32 cxgb4_get_entity_length(struct adapter *adap, u32 entity) | |||
| 102 | case CUDBG_CIM_LA: | 102 | case CUDBG_CIM_LA: |
| 103 | if (is_t6(adap->params.chip)) { | 103 | if (is_t6(adap->params.chip)) { |
| 104 | len = adap->params.cim_la_size / 10 + 1; | 104 | len = adap->params.cim_la_size / 10 + 1; |
| 105 | len *= 11 * sizeof(u32); | 105 | len *= 10 * sizeof(u32); |
| 106 | } else { | 106 | } else { |
| 107 | len = adap->params.cim_la_size / 8; | 107 | len = adap->params.cim_la_size / 8; |
| 108 | len *= 8 * sizeof(u32); | 108 | len *= 8 * sizeof(u32); |
diff --git a/drivers/net/ethernet/chelsio/cxgb4/cxgb4_main.c b/drivers/net/ethernet/chelsio/cxgb4/cxgb4_main.c index 56bc626ef006..7b452e85de2a 100644 --- a/drivers/net/ethernet/chelsio/cxgb4/cxgb4_main.c +++ b/drivers/net/ethernet/chelsio/cxgb4/cxgb4_main.c | |||
| @@ -4982,9 +4982,10 @@ static int cxgb4_iov_configure(struct pci_dev *pdev, int num_vfs) | |||
| 4982 | 4982 | ||
| 4983 | pcie_fw = readl(adap->regs + PCIE_FW_A); | 4983 | pcie_fw = readl(adap->regs + PCIE_FW_A); |
| 4984 | /* Check if cxgb4 is the MASTER and fw is initialized */ | 4984 | /* Check if cxgb4 is the MASTER and fw is initialized */ |
| 4985 | if (!(pcie_fw & PCIE_FW_INIT_F) || | 4985 | if (num_vfs && |
| 4986 | (!(pcie_fw & PCIE_FW_INIT_F) || | ||
| 4986 | !(pcie_fw & PCIE_FW_MASTER_VLD_F) || | 4987 | !(pcie_fw & PCIE_FW_MASTER_VLD_F) || |
| 4987 | PCIE_FW_MASTER_G(pcie_fw) != CXGB4_UNIFIED_PF) { | 4988 | PCIE_FW_MASTER_G(pcie_fw) != CXGB4_UNIFIED_PF)) { |
| 4988 | dev_warn(&pdev->dev, | 4989 | dev_warn(&pdev->dev, |
| 4989 | "cxgb4 driver needs to be MASTER to support SRIOV\n"); | 4990 | "cxgb4 driver needs to be MASTER to support SRIOV\n"); |
| 4990 | return -EOPNOTSUPP; | 4991 | return -EOPNOTSUPP; |
| @@ -5599,24 +5600,24 @@ static void remove_one(struct pci_dev *pdev) | |||
| 5599 | #if IS_ENABLED(CONFIG_IPV6) | 5600 | #if IS_ENABLED(CONFIG_IPV6) |
| 5600 | t4_cleanup_clip_tbl(adapter); | 5601 | t4_cleanup_clip_tbl(adapter); |
| 5601 | #endif | 5602 | #endif |
| 5602 | iounmap(adapter->regs); | ||
| 5603 | if (!is_t4(adapter->params.chip)) | 5603 | if (!is_t4(adapter->params.chip)) |
| 5604 | iounmap(adapter->bar2); | 5604 | iounmap(adapter->bar2); |
| 5605 | pci_disable_pcie_error_reporting(pdev); | ||
| 5606 | if ((adapter->flags & DEV_ENABLED)) { | ||
| 5607 | pci_disable_device(pdev); | ||
| 5608 | adapter->flags &= ~DEV_ENABLED; | ||
| 5609 | } | ||
| 5610 | pci_release_regions(pdev); | ||
| 5611 | kfree(adapter->mbox_log); | ||
| 5612 | synchronize_rcu(); | ||
| 5613 | kfree(adapter); | ||
| 5614 | } | 5605 | } |
| 5615 | #ifdef CONFIG_PCI_IOV | 5606 | #ifdef CONFIG_PCI_IOV |
| 5616 | else { | 5607 | else { |
| 5617 | cxgb4_iov_configure(adapter->pdev, 0); | 5608 | cxgb4_iov_configure(adapter->pdev, 0); |
| 5618 | } | 5609 | } |
| 5619 | #endif | 5610 | #endif |
| 5611 | iounmap(adapter->regs); | ||
| 5612 | pci_disable_pcie_error_reporting(pdev); | ||
| 5613 | if ((adapter->flags & DEV_ENABLED)) { | ||
| 5614 | pci_disable_device(pdev); | ||
| 5615 | adapter->flags &= ~DEV_ENABLED; | ||
| 5616 | } | ||
| 5617 | pci_release_regions(pdev); | ||
| 5618 | kfree(adapter->mbox_log); | ||
| 5619 | synchronize_rcu(); | ||
| 5620 | kfree(adapter); | ||
| 5620 | } | 5621 | } |
| 5621 | 5622 | ||
| 5622 | /* "Shutdown" quiesces the device, stopping Ingress Packet and Interrupt | 5623 | /* "Shutdown" quiesces the device, stopping Ingress Packet and Interrupt |
diff --git a/drivers/net/ethernet/chelsio/cxgb4/t4_hw.c b/drivers/net/ethernet/chelsio/cxgb4/t4_hw.c index 047609ef0515..920bccd6bc40 100644 --- a/drivers/net/ethernet/chelsio/cxgb4/t4_hw.c +++ b/drivers/net/ethernet/chelsio/cxgb4/t4_hw.c | |||
| @@ -2637,7 +2637,6 @@ void t4_get_regs(struct adapter *adap, void *buf, size_t buf_size) | |||
| 2637 | } | 2637 | } |
| 2638 | 2638 | ||
| 2639 | #define EEPROM_STAT_ADDR 0x7bfc | 2639 | #define EEPROM_STAT_ADDR 0x7bfc |
| 2640 | #define VPD_SIZE 0x800 | ||
| 2641 | #define VPD_BASE 0x400 | 2640 | #define VPD_BASE 0x400 |
| 2642 | #define VPD_BASE_OLD 0 | 2641 | #define VPD_BASE_OLD 0 |
| 2643 | #define VPD_LEN 1024 | 2642 | #define VPD_LEN 1024 |
| @@ -2704,15 +2703,6 @@ int t4_get_raw_vpd_params(struct adapter *adapter, struct vpd_params *p) | |||
| 2704 | if (!vpd) | 2703 | if (!vpd) |
| 2705 | return -ENOMEM; | 2704 | return -ENOMEM; |
| 2706 | 2705 | ||
| 2707 | /* We have two VPD data structures stored in the adapter VPD area. | ||
| 2708 | * By default, Linux calculates the size of the VPD area by traversing | ||
| 2709 | * the first VPD area at offset 0x0, so we need to tell the OS what | ||
| 2710 | * our real VPD size is. | ||
| 2711 | */ | ||
| 2712 | ret = pci_set_vpd_size(adapter->pdev, VPD_SIZE); | ||
| 2713 | if (ret < 0) | ||
| 2714 | goto out; | ||
| 2715 | |||
| 2716 | /* Card information normally starts at VPD_BASE but early cards had | 2706 | /* Card information normally starts at VPD_BASE but early cards had |
| 2717 | * it at 0. | 2707 | * it at 0. |
| 2718 | */ | 2708 | */ |
diff --git a/drivers/net/ethernet/freescale/gianfar.c b/drivers/net/ethernet/freescale/gianfar.c index 3bdeb295514b..f5c87bd35fa1 100644 --- a/drivers/net/ethernet/freescale/gianfar.c +++ b/drivers/net/ethernet/freescale/gianfar.c | |||
| @@ -2934,29 +2934,17 @@ static bool gfar_add_rx_frag(struct gfar_rx_buff *rxb, u32 lstatus, | |||
| 2934 | { | 2934 | { |
| 2935 | int size = lstatus & BD_LENGTH_MASK; | 2935 | int size = lstatus & BD_LENGTH_MASK; |
| 2936 | struct page *page = rxb->page; | 2936 | struct page *page = rxb->page; |
| 2937 | bool last = !!(lstatus & BD_LFLAG(RXBD_LAST)); | ||
| 2938 | |||
| 2939 | /* Remove the FCS from the packet length */ | ||
| 2940 | if (last) | ||
| 2941 | size -= ETH_FCS_LEN; | ||
| 2942 | 2937 | ||
| 2943 | if (likely(first)) { | 2938 | if (likely(first)) { |
| 2944 | skb_put(skb, size); | 2939 | skb_put(skb, size); |
| 2945 | } else { | 2940 | } else { |
| 2946 | /* the last fragments' length contains the full frame length */ | 2941 | /* the last fragments' length contains the full frame length */ |
| 2947 | if (last) | 2942 | if (lstatus & BD_LFLAG(RXBD_LAST)) |
| 2948 | size -= skb->len; | 2943 | size -= skb->len; |
| 2949 | 2944 | ||
| 2950 | /* Add the last fragment if it contains something other than | 2945 | skb_add_rx_frag(skb, skb_shinfo(skb)->nr_frags, page, |
| 2951 | * the FCS, otherwise drop it and trim off any part of the FCS | 2946 | rxb->page_offset + RXBUF_ALIGNMENT, |
| 2952 | * that was already received. | 2947 | size, GFAR_RXB_TRUESIZE); |
| 2953 | */ | ||
| 2954 | if (size > 0) | ||
| 2955 | skb_add_rx_frag(skb, skb_shinfo(skb)->nr_frags, page, | ||
| 2956 | rxb->page_offset + RXBUF_ALIGNMENT, | ||
| 2957 | size, GFAR_RXB_TRUESIZE); | ||
| 2958 | else if (size < 0) | ||
| 2959 | pskb_trim(skb, skb->len + size); | ||
| 2960 | } | 2948 | } |
| 2961 | 2949 | ||
| 2962 | /* try reuse page */ | 2950 | /* try reuse page */ |
| @@ -3069,6 +3057,9 @@ static void gfar_process_frame(struct net_device *ndev, struct sk_buff *skb) | |||
| 3069 | if (priv->padding) | 3057 | if (priv->padding) |
| 3070 | skb_pull(skb, priv->padding); | 3058 | skb_pull(skb, priv->padding); |
| 3071 | 3059 | ||
| 3060 | /* Trim off the FCS */ | ||
| 3061 | pskb_trim(skb, skb->len - ETH_FCS_LEN); | ||
| 3062 | |||
| 3072 | if (ndev->features & NETIF_F_RXCSUM) | 3063 | if (ndev->features & NETIF_F_RXCSUM) |
| 3073 | gfar_rx_checksum(skb, fcb); | 3064 | gfar_rx_checksum(skb, fcb); |
| 3074 | 3065 | ||
diff --git a/drivers/net/ethernet/ibm/ibmvnic.c b/drivers/net/ethernet/ibm/ibmvnic.c index 27447260215d..1b3cc8bb0705 100644 --- a/drivers/net/ethernet/ibm/ibmvnic.c +++ b/drivers/net/ethernet/ibm/ibmvnic.c | |||
| @@ -791,6 +791,18 @@ static int ibmvnic_login(struct net_device *netdev) | |||
| 791 | return 0; | 791 | return 0; |
| 792 | } | 792 | } |
| 793 | 793 | ||
| 794 | static void release_login_buffer(struct ibmvnic_adapter *adapter) | ||
| 795 | { | ||
| 796 | kfree(adapter->login_buf); | ||
| 797 | adapter->login_buf = NULL; | ||
| 798 | } | ||
| 799 | |||
| 800 | static void release_login_rsp_buffer(struct ibmvnic_adapter *adapter) | ||
| 801 | { | ||
| 802 | kfree(adapter->login_rsp_buf); | ||
| 803 | adapter->login_rsp_buf = NULL; | ||
| 804 | } | ||
| 805 | |||
| 794 | static void release_resources(struct ibmvnic_adapter *adapter) | 806 | static void release_resources(struct ibmvnic_adapter *adapter) |
| 795 | { | 807 | { |
| 796 | int i; | 808 | int i; |
| @@ -813,6 +825,10 @@ static void release_resources(struct ibmvnic_adapter *adapter) | |||
| 813 | } | 825 | } |
| 814 | } | 826 | } |
| 815 | } | 827 | } |
| 828 | kfree(adapter->napi); | ||
| 829 | adapter->napi = NULL; | ||
| 830 | |||
| 831 | release_login_rsp_buffer(adapter); | ||
| 816 | } | 832 | } |
| 817 | 833 | ||
| 818 | static int set_link_state(struct ibmvnic_adapter *adapter, u8 link_state) | 834 | static int set_link_state(struct ibmvnic_adapter *adapter, u8 link_state) |
| @@ -1057,6 +1073,35 @@ static int ibmvnic_open(struct net_device *netdev) | |||
| 1057 | return rc; | 1073 | return rc; |
| 1058 | } | 1074 | } |
| 1059 | 1075 | ||
| 1076 | static void clean_rx_pools(struct ibmvnic_adapter *adapter) | ||
| 1077 | { | ||
| 1078 | struct ibmvnic_rx_pool *rx_pool; | ||
| 1079 | u64 rx_entries; | ||
| 1080 | int rx_scrqs; | ||
| 1081 | int i, j; | ||
| 1082 | |||
| 1083 | if (!adapter->rx_pool) | ||
| 1084 | return; | ||
| 1085 | |||
| 1086 | rx_scrqs = be32_to_cpu(adapter->login_rsp_buf->num_rxadd_subcrqs); | ||
| 1087 | rx_entries = adapter->req_rx_add_entries_per_subcrq; | ||
| 1088 | |||
| 1089 | /* Free any remaining skbs in the rx buffer pools */ | ||
| 1090 | for (i = 0; i < rx_scrqs; i++) { | ||
| 1091 | rx_pool = &adapter->rx_pool[i]; | ||
| 1092 | if (!rx_pool) | ||
| 1093 | continue; | ||
| 1094 | |||
| 1095 | netdev_dbg(adapter->netdev, "Cleaning rx_pool[%d]\n", i); | ||
| 1096 | for (j = 0; j < rx_entries; j++) { | ||
| 1097 | if (rx_pool->rx_buff[j].skb) { | ||
| 1098 | dev_kfree_skb_any(rx_pool->rx_buff[j].skb); | ||
| 1099 | rx_pool->rx_buff[j].skb = NULL; | ||
| 1100 | } | ||
| 1101 | } | ||
| 1102 | } | ||
| 1103 | } | ||
| 1104 | |||
| 1060 | static void clean_tx_pools(struct ibmvnic_adapter *adapter) | 1105 | static void clean_tx_pools(struct ibmvnic_adapter *adapter) |
| 1061 | { | 1106 | { |
| 1062 | struct ibmvnic_tx_pool *tx_pool; | 1107 | struct ibmvnic_tx_pool *tx_pool; |
| @@ -1134,7 +1179,7 @@ static int __ibmvnic_close(struct net_device *netdev) | |||
| 1134 | } | 1179 | } |
| 1135 | } | 1180 | } |
| 1136 | } | 1181 | } |
| 1137 | 1182 | clean_rx_pools(adapter); | |
| 1138 | clean_tx_pools(adapter); | 1183 | clean_tx_pools(adapter); |
| 1139 | adapter->state = VNIC_CLOSED; | 1184 | adapter->state = VNIC_CLOSED; |
| 1140 | return rc; | 1185 | return rc; |
| @@ -1670,8 +1715,6 @@ static int do_reset(struct ibmvnic_adapter *adapter, | |||
| 1670 | return 0; | 1715 | return 0; |
| 1671 | } | 1716 | } |
| 1672 | 1717 | ||
| 1673 | netif_carrier_on(netdev); | ||
| 1674 | |||
| 1675 | /* kick napi */ | 1718 | /* kick napi */ |
| 1676 | for (i = 0; i < adapter->req_rx_queues; i++) | 1719 | for (i = 0; i < adapter->req_rx_queues; i++) |
| 1677 | napi_schedule(&adapter->napi[i]); | 1720 | napi_schedule(&adapter->napi[i]); |
| @@ -1679,6 +1722,8 @@ static int do_reset(struct ibmvnic_adapter *adapter, | |||
| 1679 | if (adapter->reset_reason != VNIC_RESET_FAILOVER) | 1722 | if (adapter->reset_reason != VNIC_RESET_FAILOVER) |
| 1680 | netdev_notify_peers(netdev); | 1723 | netdev_notify_peers(netdev); |
| 1681 | 1724 | ||
| 1725 | netif_carrier_on(netdev); | ||
| 1726 | |||
| 1682 | return 0; | 1727 | return 0; |
| 1683 | } | 1728 | } |
| 1684 | 1729 | ||
| @@ -1853,6 +1898,12 @@ restart_poll: | |||
| 1853 | be16_to_cpu(next->rx_comp.rc)); | 1898 | be16_to_cpu(next->rx_comp.rc)); |
| 1854 | /* free the entry */ | 1899 | /* free the entry */ |
| 1855 | next->rx_comp.first = 0; | 1900 | next->rx_comp.first = 0; |
| 1901 | dev_kfree_skb_any(rx_buff->skb); | ||
| 1902 | remove_buff_from_pool(adapter, rx_buff); | ||
| 1903 | continue; | ||
| 1904 | } else if (!rx_buff->skb) { | ||
| 1905 | /* free the entry */ | ||
| 1906 | next->rx_comp.first = 0; | ||
| 1856 | remove_buff_from_pool(adapter, rx_buff); | 1907 | remove_buff_from_pool(adapter, rx_buff); |
| 1857 | continue; | 1908 | continue; |
| 1858 | } | 1909 | } |
| @@ -3013,6 +3064,7 @@ static void send_login(struct ibmvnic_adapter *adapter) | |||
| 3013 | struct vnic_login_client_data *vlcd; | 3064 | struct vnic_login_client_data *vlcd; |
| 3014 | int i; | 3065 | int i; |
| 3015 | 3066 | ||
| 3067 | release_login_rsp_buffer(adapter); | ||
| 3016 | client_data_len = vnic_client_data_len(adapter); | 3068 | client_data_len = vnic_client_data_len(adapter); |
| 3017 | 3069 | ||
| 3018 | buffer_size = | 3070 | buffer_size = |
| @@ -3738,6 +3790,7 @@ static int handle_login_rsp(union ibmvnic_crq *login_rsp_crq, | |||
| 3738 | ibmvnic_remove(adapter->vdev); | 3790 | ibmvnic_remove(adapter->vdev); |
| 3739 | return -EIO; | 3791 | return -EIO; |
| 3740 | } | 3792 | } |
| 3793 | release_login_buffer(adapter); | ||
| 3741 | complete(&adapter->init_done); | 3794 | complete(&adapter->init_done); |
| 3742 | 3795 | ||
| 3743 | return 0; | 3796 | return 0; |
diff --git a/drivers/net/ethernet/marvell/mvpp2.c b/drivers/net/ethernet/marvell/mvpp2.c index a1d7b88cf083..5a1668cdb461 100644 --- a/drivers/net/ethernet/marvell/mvpp2.c +++ b/drivers/net/ethernet/marvell/mvpp2.c | |||
| @@ -7137,6 +7137,7 @@ static void mvpp2_set_rx_mode(struct net_device *dev) | |||
| 7137 | int id = port->id; | 7137 | int id = port->id; |
| 7138 | bool allmulti = dev->flags & IFF_ALLMULTI; | 7138 | bool allmulti = dev->flags & IFF_ALLMULTI; |
| 7139 | 7139 | ||
| 7140 | retry: | ||
| 7140 | mvpp2_prs_mac_promisc_set(priv, id, dev->flags & IFF_PROMISC); | 7141 | mvpp2_prs_mac_promisc_set(priv, id, dev->flags & IFF_PROMISC); |
| 7141 | mvpp2_prs_mac_multi_set(priv, id, MVPP2_PE_MAC_MC_ALL, allmulti); | 7142 | mvpp2_prs_mac_multi_set(priv, id, MVPP2_PE_MAC_MC_ALL, allmulti); |
| 7142 | mvpp2_prs_mac_multi_set(priv, id, MVPP2_PE_MAC_MC_IP6, allmulti); | 7143 | mvpp2_prs_mac_multi_set(priv, id, MVPP2_PE_MAC_MC_IP6, allmulti); |
| @@ -7144,9 +7145,13 @@ static void mvpp2_set_rx_mode(struct net_device *dev) | |||
| 7144 | /* Remove all port->id's mcast enries */ | 7145 | /* Remove all port->id's mcast enries */ |
| 7145 | mvpp2_prs_mcast_del_all(priv, id); | 7146 | mvpp2_prs_mcast_del_all(priv, id); |
| 7146 | 7147 | ||
| 7147 | if (allmulti && !netdev_mc_empty(dev)) { | 7148 | if (!allmulti) { |
| 7148 | netdev_for_each_mc_addr(ha, dev) | 7149 | netdev_for_each_mc_addr(ha, dev) { |
| 7149 | mvpp2_prs_mac_da_accept(priv, id, ha->addr, true); | 7150 | if (mvpp2_prs_mac_da_accept(priv, id, ha->addr, true)) { |
| 7151 | allmulti = true; | ||
| 7152 | goto retry; | ||
| 7153 | } | ||
| 7154 | } | ||
| 7150 | } | 7155 | } |
| 7151 | } | 7156 | } |
| 7152 | 7157 | ||
diff --git a/drivers/net/ethernet/mellanox/mlx5/core/diag/fs_tracepoint.c b/drivers/net/ethernet/mellanox/mlx5/core/diag/fs_tracepoint.c index 0be4575b58a2..fd509160c8f6 100644 --- a/drivers/net/ethernet/mellanox/mlx5/core/diag/fs_tracepoint.c +++ b/drivers/net/ethernet/mellanox/mlx5/core/diag/fs_tracepoint.c | |||
| @@ -96,10 +96,10 @@ static void print_lyr_2_4_hdrs(struct trace_seq *p, | |||
| 96 | "%pI4"); | 96 | "%pI4"); |
| 97 | } else if (ethertype.v == ETH_P_IPV6) { | 97 | } else if (ethertype.v == ETH_P_IPV6) { |
| 98 | static const struct in6_addr full_ones = { | 98 | static const struct in6_addr full_ones = { |
| 99 | .in6_u.u6_addr32 = {htonl(0xffffffff), | 99 | .in6_u.u6_addr32 = {__constant_htonl(0xffffffff), |
| 100 | htonl(0xffffffff), | 100 | __constant_htonl(0xffffffff), |
| 101 | htonl(0xffffffff), | 101 | __constant_htonl(0xffffffff), |
| 102 | htonl(0xffffffff)}, | 102 | __constant_htonl(0xffffffff)}, |
| 103 | }; | 103 | }; |
| 104 | DECLARE_MASK_VAL(struct in6_addr, src_ipv6); | 104 | DECLARE_MASK_VAL(struct in6_addr, src_ipv6); |
| 105 | DECLARE_MASK_VAL(struct in6_addr, dst_ipv6); | 105 | DECLARE_MASK_VAL(struct in6_addr, dst_ipv6); |
diff --git a/drivers/net/ethernet/mellanox/mlx5/core/en_main.c b/drivers/net/ethernet/mellanox/mlx5/core/en_main.c index 47bab842c5ee..da94c8cba5ee 100644 --- a/drivers/net/ethernet/mellanox/mlx5/core/en_main.c +++ b/drivers/net/ethernet/mellanox/mlx5/core/en_main.c | |||
| @@ -1768,13 +1768,16 @@ static void mlx5e_build_rq_param(struct mlx5e_priv *priv, | |||
| 1768 | param->wq.linear = 1; | 1768 | param->wq.linear = 1; |
| 1769 | } | 1769 | } |
| 1770 | 1770 | ||
| 1771 | static void mlx5e_build_drop_rq_param(struct mlx5e_rq_param *param) | 1771 | static void mlx5e_build_drop_rq_param(struct mlx5_core_dev *mdev, |
| 1772 | struct mlx5e_rq_param *param) | ||
| 1772 | { | 1773 | { |
| 1773 | void *rqc = param->rqc; | 1774 | void *rqc = param->rqc; |
| 1774 | void *wq = MLX5_ADDR_OF(rqc, rqc, wq); | 1775 | void *wq = MLX5_ADDR_OF(rqc, rqc, wq); |
| 1775 | 1776 | ||
| 1776 | MLX5_SET(wq, wq, wq_type, MLX5_WQ_TYPE_LINKED_LIST); | 1777 | MLX5_SET(wq, wq, wq_type, MLX5_WQ_TYPE_LINKED_LIST); |
| 1777 | MLX5_SET(wq, wq, log_wq_stride, ilog2(sizeof(struct mlx5e_rx_wqe))); | 1778 | MLX5_SET(wq, wq, log_wq_stride, ilog2(sizeof(struct mlx5e_rx_wqe))); |
| 1779 | |||
| 1780 | param->wq.buf_numa_node = dev_to_node(&mdev->pdev->dev); | ||
| 1778 | } | 1781 | } |
| 1779 | 1782 | ||
| 1780 | static void mlx5e_build_sq_param_common(struct mlx5e_priv *priv, | 1783 | static void mlx5e_build_sq_param_common(struct mlx5e_priv *priv, |
| @@ -2634,6 +2637,9 @@ static int mlx5e_alloc_drop_cq(struct mlx5_core_dev *mdev, | |||
| 2634 | struct mlx5e_cq *cq, | 2637 | struct mlx5e_cq *cq, |
| 2635 | struct mlx5e_cq_param *param) | 2638 | struct mlx5e_cq_param *param) |
| 2636 | { | 2639 | { |
| 2640 | param->wq.buf_numa_node = dev_to_node(&mdev->pdev->dev); | ||
| 2641 | param->wq.db_numa_node = dev_to_node(&mdev->pdev->dev); | ||
| 2642 | |||
| 2637 | return mlx5e_alloc_cq_common(mdev, param, cq); | 2643 | return mlx5e_alloc_cq_common(mdev, param, cq); |
| 2638 | } | 2644 | } |
| 2639 | 2645 | ||
| @@ -2645,7 +2651,7 @@ static int mlx5e_open_drop_rq(struct mlx5_core_dev *mdev, | |||
| 2645 | struct mlx5e_cq *cq = &drop_rq->cq; | 2651 | struct mlx5e_cq *cq = &drop_rq->cq; |
| 2646 | int err; | 2652 | int err; |
| 2647 | 2653 | ||
| 2648 | mlx5e_build_drop_rq_param(&rq_param); | 2654 | mlx5e_build_drop_rq_param(mdev, &rq_param); |
| 2649 | 2655 | ||
| 2650 | err = mlx5e_alloc_drop_cq(mdev, cq, &cq_param); | 2656 | err = mlx5e_alloc_drop_cq(mdev, cq, &cq_param); |
| 2651 | if (err) | 2657 | if (err) |
| @@ -2994,8 +3000,8 @@ static int mlx5e_setup_tc_block(struct net_device *dev, | |||
| 2994 | } | 3000 | } |
| 2995 | #endif | 3001 | #endif |
| 2996 | 3002 | ||
| 2997 | int mlx5e_setup_tc(struct net_device *dev, enum tc_setup_type type, | 3003 | static int mlx5e_setup_tc(struct net_device *dev, enum tc_setup_type type, |
| 2998 | void *type_data) | 3004 | void *type_data) |
| 2999 | { | 3005 | { |
| 3000 | switch (type) { | 3006 | switch (type) { |
| 3001 | #ifdef CONFIG_MLX5_ESWITCH | 3007 | #ifdef CONFIG_MLX5_ESWITCH |
diff --git a/drivers/net/ethernet/mellanox/mlx5/core/en_rx.c b/drivers/net/ethernet/mellanox/mlx5/core/en_rx.c index 0d4bb0688faa..e5c3ab46a24a 100644 --- a/drivers/net/ethernet/mellanox/mlx5/core/en_rx.c +++ b/drivers/net/ethernet/mellanox/mlx5/core/en_rx.c | |||
| @@ -36,6 +36,7 @@ | |||
| 36 | #include <linux/tcp.h> | 36 | #include <linux/tcp.h> |
| 37 | #include <linux/bpf_trace.h> | 37 | #include <linux/bpf_trace.h> |
| 38 | #include <net/busy_poll.h> | 38 | #include <net/busy_poll.h> |
| 39 | #include <net/ip6_checksum.h> | ||
| 39 | #include "en.h" | 40 | #include "en.h" |
| 40 | #include "en_tc.h" | 41 | #include "en_tc.h" |
| 41 | #include "eswitch.h" | 42 | #include "eswitch.h" |
| @@ -546,20 +547,33 @@ bool mlx5e_post_rx_mpwqes(struct mlx5e_rq *rq) | |||
| 546 | return true; | 547 | return true; |
| 547 | } | 548 | } |
| 548 | 549 | ||
| 550 | static void mlx5e_lro_update_tcp_hdr(struct mlx5_cqe64 *cqe, struct tcphdr *tcp) | ||
| 551 | { | ||
| 552 | u8 l4_hdr_type = get_cqe_l4_hdr_type(cqe); | ||
| 553 | u8 tcp_ack = (l4_hdr_type == CQE_L4_HDR_TYPE_TCP_ACK_NO_DATA) || | ||
| 554 | (l4_hdr_type == CQE_L4_HDR_TYPE_TCP_ACK_AND_DATA); | ||
| 555 | |||
| 556 | tcp->check = 0; | ||
| 557 | tcp->psh = get_cqe_lro_tcppsh(cqe); | ||
| 558 | |||
| 559 | if (tcp_ack) { | ||
| 560 | tcp->ack = 1; | ||
| 561 | tcp->ack_seq = cqe->lro_ack_seq_num; | ||
| 562 | tcp->window = cqe->lro_tcp_win; | ||
| 563 | } | ||
| 564 | } | ||
| 565 | |||
| 549 | static void mlx5e_lro_update_hdr(struct sk_buff *skb, struct mlx5_cqe64 *cqe, | 566 | static void mlx5e_lro_update_hdr(struct sk_buff *skb, struct mlx5_cqe64 *cqe, |
| 550 | u32 cqe_bcnt) | 567 | u32 cqe_bcnt) |
| 551 | { | 568 | { |
| 552 | struct ethhdr *eth = (struct ethhdr *)(skb->data); | 569 | struct ethhdr *eth = (struct ethhdr *)(skb->data); |
| 553 | struct tcphdr *tcp; | 570 | struct tcphdr *tcp; |
| 554 | int network_depth = 0; | 571 | int network_depth = 0; |
| 572 | __wsum check; | ||
| 555 | __be16 proto; | 573 | __be16 proto; |
| 556 | u16 tot_len; | 574 | u16 tot_len; |
| 557 | void *ip_p; | 575 | void *ip_p; |
| 558 | 576 | ||
| 559 | u8 l4_hdr_type = get_cqe_l4_hdr_type(cqe); | ||
| 560 | u8 tcp_ack = (l4_hdr_type == CQE_L4_HDR_TYPE_TCP_ACK_NO_DATA) || | ||
| 561 | (l4_hdr_type == CQE_L4_HDR_TYPE_TCP_ACK_AND_DATA); | ||
| 562 | |||
| 563 | proto = __vlan_get_protocol(skb, eth->h_proto, &network_depth); | 577 | proto = __vlan_get_protocol(skb, eth->h_proto, &network_depth); |
| 564 | 578 | ||
| 565 | tot_len = cqe_bcnt - network_depth; | 579 | tot_len = cqe_bcnt - network_depth; |
| @@ -576,23 +590,30 @@ static void mlx5e_lro_update_hdr(struct sk_buff *skb, struct mlx5_cqe64 *cqe, | |||
| 576 | ipv4->check = 0; | 590 | ipv4->check = 0; |
| 577 | ipv4->check = ip_fast_csum((unsigned char *)ipv4, | 591 | ipv4->check = ip_fast_csum((unsigned char *)ipv4, |
| 578 | ipv4->ihl); | 592 | ipv4->ihl); |
| 593 | |||
| 594 | mlx5e_lro_update_tcp_hdr(cqe, tcp); | ||
| 595 | check = csum_partial(tcp, tcp->doff * 4, | ||
| 596 | csum_unfold((__force __sum16)cqe->check_sum)); | ||
| 597 | /* Almost done, don't forget the pseudo header */ | ||
| 598 | tcp->check = csum_tcpudp_magic(ipv4->saddr, ipv4->daddr, | ||
| 599 | tot_len - sizeof(struct iphdr), | ||
| 600 | IPPROTO_TCP, check); | ||
| 579 | } else { | 601 | } else { |
| 602 | u16 payload_len = tot_len - sizeof(struct ipv6hdr); | ||
| 580 | struct ipv6hdr *ipv6 = ip_p; | 603 | struct ipv6hdr *ipv6 = ip_p; |
| 581 | 604 | ||
| 582 | tcp = ip_p + sizeof(struct ipv6hdr); | 605 | tcp = ip_p + sizeof(struct ipv6hdr); |
| 583 | skb_shinfo(skb)->gso_type = SKB_GSO_TCPV6; | 606 | skb_shinfo(skb)->gso_type = SKB_GSO_TCPV6; |
| 584 | 607 | ||
| 585 | ipv6->hop_limit = cqe->lro_min_ttl; | 608 | ipv6->hop_limit = cqe->lro_min_ttl; |
| 586 | ipv6->payload_len = cpu_to_be16(tot_len - | 609 | ipv6->payload_len = cpu_to_be16(payload_len); |
| 587 | sizeof(struct ipv6hdr)); | 610 | |
| 588 | } | 611 | mlx5e_lro_update_tcp_hdr(cqe, tcp); |
| 589 | 612 | check = csum_partial(tcp, tcp->doff * 4, | |
| 590 | tcp->psh = get_cqe_lro_tcppsh(cqe); | 613 | csum_unfold((__force __sum16)cqe->check_sum)); |
| 591 | 614 | /* Almost done, don't forget the pseudo header */ | |
| 592 | if (tcp_ack) { | 615 | tcp->check = csum_ipv6_magic(&ipv6->saddr, &ipv6->daddr, payload_len, |
| 593 | tcp->ack = 1; | 616 | IPPROTO_TCP, check); |
| 594 | tcp->ack_seq = cqe->lro_ack_seq_num; | ||
| 595 | tcp->window = cqe->lro_tcp_win; | ||
| 596 | } | 617 | } |
| 597 | } | 618 | } |
| 598 | 619 | ||
diff --git a/drivers/net/ethernet/mellanox/mlx5/core/en_selftest.c b/drivers/net/ethernet/mellanox/mlx5/core/en_selftest.c index 5a4608281f38..707976482c09 100644 --- a/drivers/net/ethernet/mellanox/mlx5/core/en_selftest.c +++ b/drivers/net/ethernet/mellanox/mlx5/core/en_selftest.c | |||
| @@ -216,7 +216,8 @@ mlx5e_test_loopback_validate(struct sk_buff *skb, | |||
| 216 | if (iph->protocol != IPPROTO_UDP) | 216 | if (iph->protocol != IPPROTO_UDP) |
| 217 | goto out; | 217 | goto out; |
| 218 | 218 | ||
| 219 | udph = udp_hdr(skb); | 219 | /* Don't assume skb_transport_header() was set */ |
| 220 | udph = (struct udphdr *)((u8 *)iph + 4 * iph->ihl); | ||
| 220 | if (udph->dest != htons(9)) | 221 | if (udph->dest != htons(9)) |
| 221 | goto out; | 222 | goto out; |
| 222 | 223 | ||
diff --git a/drivers/net/ethernet/mellanox/mlx5/core/en_tc.c b/drivers/net/ethernet/mellanox/mlx5/core/en_tc.c index fd98b0dc610f..fa86a1466718 100644 --- a/drivers/net/ethernet/mellanox/mlx5/core/en_tc.c +++ b/drivers/net/ethernet/mellanox/mlx5/core/en_tc.c | |||
| @@ -2529,7 +2529,8 @@ static int parse_tc_fdb_actions(struct mlx5e_priv *priv, struct tcf_exts *exts, | |||
| 2529 | if (tcf_vlan_action(a) == TCA_VLAN_ACT_POP) { | 2529 | if (tcf_vlan_action(a) == TCA_VLAN_ACT_POP) { |
| 2530 | attr->action |= MLX5_FLOW_CONTEXT_ACTION_VLAN_POP; | 2530 | attr->action |= MLX5_FLOW_CONTEXT_ACTION_VLAN_POP; |
| 2531 | } else if (tcf_vlan_action(a) == TCA_VLAN_ACT_PUSH) { | 2531 | } else if (tcf_vlan_action(a) == TCA_VLAN_ACT_PUSH) { |
| 2532 | if (tcf_vlan_push_proto(a) != htons(ETH_P_8021Q)) | 2532 | if (tcf_vlan_push_proto(a) != htons(ETH_P_8021Q) || |
| 2533 | tcf_vlan_push_prio(a)) | ||
| 2533 | return -EOPNOTSUPP; | 2534 | return -EOPNOTSUPP; |
| 2534 | 2535 | ||
| 2535 | attr->action |= MLX5_FLOW_CONTEXT_ACTION_VLAN_PUSH; | 2536 | attr->action |= MLX5_FLOW_CONTEXT_ACTION_VLAN_PUSH; |
diff --git a/drivers/net/ethernet/mellanox/mlx5/core/en_tx.c b/drivers/net/ethernet/mellanox/mlx5/core/en_tx.c index 569b42a01026..11b4f1089d1c 100644 --- a/drivers/net/ethernet/mellanox/mlx5/core/en_tx.c +++ b/drivers/net/ethernet/mellanox/mlx5/core/en_tx.c | |||
| @@ -176,7 +176,7 @@ static inline u16 mlx5e_calc_min_inline(enum mlx5_inline_modes mode, | |||
| 176 | default: | 176 | default: |
| 177 | hlen = mlx5e_skb_l2_header_offset(skb); | 177 | hlen = mlx5e_skb_l2_header_offset(skb); |
| 178 | } | 178 | } |
| 179 | return min_t(u16, hlen, skb->len); | 179 | return min_t(u16, hlen, skb_headlen(skb)); |
| 180 | } | 180 | } |
| 181 | 181 | ||
| 182 | static inline void mlx5e_tx_skb_pull_inline(unsigned char **skb_data, | 182 | static inline void mlx5e_tx_skb_pull_inline(unsigned char **skb_data, |
diff --git a/drivers/net/ethernet/mellanox/mlx5/core/eswitch.c b/drivers/net/ethernet/mellanox/mlx5/core/eswitch.c index 5ecf2cddc16d..c2b1d7d351fc 100644 --- a/drivers/net/ethernet/mellanox/mlx5/core/eswitch.c +++ b/drivers/net/ethernet/mellanox/mlx5/core/eswitch.c | |||
| @@ -1529,6 +1529,10 @@ static void esw_enable_vport(struct mlx5_eswitch *esw, int vport_num, | |||
| 1529 | 1529 | ||
| 1530 | esw_debug(esw->dev, "Enabling VPORT(%d)\n", vport_num); | 1530 | esw_debug(esw->dev, "Enabling VPORT(%d)\n", vport_num); |
| 1531 | 1531 | ||
| 1532 | /* Create steering drop counters for ingress and egress ACLs */ | ||
| 1533 | if (vport_num && esw->mode == SRIOV_LEGACY) | ||
| 1534 | esw_vport_create_drop_counters(vport); | ||
| 1535 | |||
| 1532 | /* Restore old vport configuration */ | 1536 | /* Restore old vport configuration */ |
| 1533 | esw_apply_vport_conf(esw, vport); | 1537 | esw_apply_vport_conf(esw, vport); |
| 1534 | 1538 | ||
| @@ -1545,10 +1549,6 @@ static void esw_enable_vport(struct mlx5_eswitch *esw, int vport_num, | |||
| 1545 | if (!vport_num) | 1549 | if (!vport_num) |
| 1546 | vport->info.trusted = true; | 1550 | vport->info.trusted = true; |
| 1547 | 1551 | ||
| 1548 | /* create steering drop counters for ingress and egress ACLs */ | ||
| 1549 | if (vport_num && esw->mode == SRIOV_LEGACY) | ||
| 1550 | esw_vport_create_drop_counters(vport); | ||
| 1551 | |||
| 1552 | esw_vport_change_handle_locked(vport); | 1552 | esw_vport_change_handle_locked(vport); |
| 1553 | 1553 | ||
| 1554 | esw->enabled_vports++; | 1554 | esw->enabled_vports++; |
diff --git a/drivers/net/ethernet/mellanox/mlx5/core/fs_core.c b/drivers/net/ethernet/mellanox/mlx5/core/fs_core.c index c025c98700e4..31fc2cfac3b3 100644 --- a/drivers/net/ethernet/mellanox/mlx5/core/fs_core.c +++ b/drivers/net/ethernet/mellanox/mlx5/core/fs_core.c | |||
| @@ -1429,7 +1429,8 @@ static bool check_conflicting_actions(u32 action1, u32 action2) | |||
| 1429 | 1429 | ||
| 1430 | if (xored_actions & (MLX5_FLOW_CONTEXT_ACTION_DROP | | 1430 | if (xored_actions & (MLX5_FLOW_CONTEXT_ACTION_DROP | |
| 1431 | MLX5_FLOW_CONTEXT_ACTION_ENCAP | | 1431 | MLX5_FLOW_CONTEXT_ACTION_ENCAP | |
| 1432 | MLX5_FLOW_CONTEXT_ACTION_DECAP)) | 1432 | MLX5_FLOW_CONTEXT_ACTION_DECAP | |
| 1433 | MLX5_FLOW_CONTEXT_ACTION_MOD_HDR)) | ||
| 1433 | return true; | 1434 | return true; |
| 1434 | 1435 | ||
| 1435 | return false; | 1436 | return false; |
| @@ -1758,8 +1759,11 @@ search_again_locked: | |||
| 1758 | 1759 | ||
| 1759 | /* Collect all fgs which has a matching match_criteria */ | 1760 | /* Collect all fgs which has a matching match_criteria */ |
| 1760 | err = build_match_list(&match_head, ft, spec); | 1761 | err = build_match_list(&match_head, ft, spec); |
| 1761 | if (err) | 1762 | if (err) { |
| 1763 | if (take_write) | ||
| 1764 | up_write_ref_node(&ft->node); | ||
| 1762 | return ERR_PTR(err); | 1765 | return ERR_PTR(err); |
| 1766 | } | ||
| 1763 | 1767 | ||
| 1764 | if (!take_write) | 1768 | if (!take_write) |
| 1765 | up_read_ref_node(&ft->node); | 1769 | up_read_ref_node(&ft->node); |
| @@ -1768,8 +1772,11 @@ search_again_locked: | |||
| 1768 | dest_num, version); | 1772 | dest_num, version); |
| 1769 | free_match_list(&match_head); | 1773 | free_match_list(&match_head); |
| 1770 | if (!IS_ERR(rule) || | 1774 | if (!IS_ERR(rule) || |
| 1771 | (PTR_ERR(rule) != -ENOENT && PTR_ERR(rule) != -EAGAIN)) | 1775 | (PTR_ERR(rule) != -ENOENT && PTR_ERR(rule) != -EAGAIN)) { |
| 1776 | if (take_write) | ||
| 1777 | up_write_ref_node(&ft->node); | ||
| 1772 | return rule; | 1778 | return rule; |
| 1779 | } | ||
| 1773 | 1780 | ||
| 1774 | if (!take_write) { | 1781 | if (!take_write) { |
| 1775 | nested_down_write_ref_node(&ft->node, FS_LOCK_GRANDPARENT); | 1782 | nested_down_write_ref_node(&ft->node, FS_LOCK_GRANDPARENT); |
diff --git a/drivers/net/ethernet/mellanox/mlx5/core/lib/clock.c b/drivers/net/ethernet/mellanox/mlx5/core/lib/clock.c index e159243e0fcf..857035583ccd 100644 --- a/drivers/net/ethernet/mellanox/mlx5/core/lib/clock.c +++ b/drivers/net/ethernet/mellanox/mlx5/core/lib/clock.c | |||
| @@ -34,6 +34,7 @@ | |||
| 34 | #include <linux/highmem.h> | 34 | #include <linux/highmem.h> |
| 35 | #include <rdma/mlx5-abi.h> | 35 | #include <rdma/mlx5-abi.h> |
| 36 | #include "en.h" | 36 | #include "en.h" |
| 37 | #include "clock.h" | ||
| 37 | 38 | ||
| 38 | enum { | 39 | enum { |
| 39 | MLX5_CYCLES_SHIFT = 23 | 40 | MLX5_CYCLES_SHIFT = 23 |
diff --git a/drivers/net/ethernet/mellanox/mlx5/core/main.c b/drivers/net/ethernet/mellanox/mlx5/core/main.c index 2ef641c91c26..ae391e4b7070 100644 --- a/drivers/net/ethernet/mellanox/mlx5/core/main.c +++ b/drivers/net/ethernet/mellanox/mlx5/core/main.c | |||
| @@ -551,7 +551,7 @@ static int handle_hca_cap(struct mlx5_core_dev *dev) | |||
| 551 | MLX5_SET(cmd_hca_cap, | 551 | MLX5_SET(cmd_hca_cap, |
| 552 | set_hca_cap, | 552 | set_hca_cap, |
| 553 | cache_line_128byte, | 553 | cache_line_128byte, |
| 554 | cache_line_size() == 128 ? 1 : 0); | 554 | cache_line_size() >= 128 ? 1 : 0); |
| 555 | 555 | ||
| 556 | if (MLX5_CAP_GEN_MAX(dev, dct)) | 556 | if (MLX5_CAP_GEN_MAX(dev, dct)) |
| 557 | MLX5_SET(cmd_hca_cap, set_hca_cap, dct, 1); | 557 | MLX5_SET(cmd_hca_cap, set_hca_cap, dct, 1); |
diff --git a/drivers/net/ethernet/mellanox/mlxsw/spectrum_router.c b/drivers/net/ethernet/mellanox/mlxsw/spectrum_router.c index f0b25baba09a..f7948e983637 100644 --- a/drivers/net/ethernet/mellanox/mlxsw/spectrum_router.c +++ b/drivers/net/ethernet/mellanox/mlxsw/spectrum_router.c | |||
| @@ -788,6 +788,9 @@ static struct mlxsw_sp_vr *mlxsw_sp_vr_create(struct mlxsw_sp *mlxsw_sp, | |||
| 788 | u32 tb_id, | 788 | u32 tb_id, |
| 789 | struct netlink_ext_ack *extack) | 789 | struct netlink_ext_ack *extack) |
| 790 | { | 790 | { |
| 791 | struct mlxsw_sp_mr_table *mr4_table; | ||
| 792 | struct mlxsw_sp_fib *fib4; | ||
| 793 | struct mlxsw_sp_fib *fib6; | ||
| 791 | struct mlxsw_sp_vr *vr; | 794 | struct mlxsw_sp_vr *vr; |
| 792 | int err; | 795 | int err; |
| 793 | 796 | ||
| @@ -796,29 +799,30 @@ static struct mlxsw_sp_vr *mlxsw_sp_vr_create(struct mlxsw_sp *mlxsw_sp, | |||
| 796 | NL_SET_ERR_MSG(extack, "spectrum: Exceeded number of supported virtual routers"); | 799 | NL_SET_ERR_MSG(extack, "spectrum: Exceeded number of supported virtual routers"); |
| 797 | return ERR_PTR(-EBUSY); | 800 | return ERR_PTR(-EBUSY); |
| 798 | } | 801 | } |
| 799 | vr->fib4 = mlxsw_sp_fib_create(mlxsw_sp, vr, MLXSW_SP_L3_PROTO_IPV4); | 802 | fib4 = mlxsw_sp_fib_create(mlxsw_sp, vr, MLXSW_SP_L3_PROTO_IPV4); |
| 800 | if (IS_ERR(vr->fib4)) | 803 | if (IS_ERR(fib4)) |
| 801 | return ERR_CAST(vr->fib4); | 804 | return ERR_CAST(fib4); |
| 802 | vr->fib6 = mlxsw_sp_fib_create(mlxsw_sp, vr, MLXSW_SP_L3_PROTO_IPV6); | 805 | fib6 = mlxsw_sp_fib_create(mlxsw_sp, vr, MLXSW_SP_L3_PROTO_IPV6); |
| 803 | if (IS_ERR(vr->fib6)) { | 806 | if (IS_ERR(fib6)) { |
| 804 | err = PTR_ERR(vr->fib6); | 807 | err = PTR_ERR(fib6); |
| 805 | goto err_fib6_create; | 808 | goto err_fib6_create; |
| 806 | } | 809 | } |
| 807 | vr->mr4_table = mlxsw_sp_mr_table_create(mlxsw_sp, vr->id, | 810 | mr4_table = mlxsw_sp_mr_table_create(mlxsw_sp, vr->id, |
| 808 | MLXSW_SP_L3_PROTO_IPV4); | 811 | MLXSW_SP_L3_PROTO_IPV4); |
| 809 | if (IS_ERR(vr->mr4_table)) { | 812 | if (IS_ERR(mr4_table)) { |
| 810 | err = PTR_ERR(vr->mr4_table); | 813 | err = PTR_ERR(mr4_table); |
| 811 | goto err_mr_table_create; | 814 | goto err_mr_table_create; |
| 812 | } | 815 | } |
| 816 | vr->fib4 = fib4; | ||
| 817 | vr->fib6 = fib6; | ||
| 818 | vr->mr4_table = mr4_table; | ||
| 813 | vr->tb_id = tb_id; | 819 | vr->tb_id = tb_id; |
| 814 | return vr; | 820 | return vr; |
| 815 | 821 | ||
| 816 | err_mr_table_create: | 822 | err_mr_table_create: |
| 817 | mlxsw_sp_fib_destroy(mlxsw_sp, vr->fib6); | 823 | mlxsw_sp_fib_destroy(mlxsw_sp, fib6); |
| 818 | vr->fib6 = NULL; | ||
| 819 | err_fib6_create: | 824 | err_fib6_create: |
| 820 | mlxsw_sp_fib_destroy(mlxsw_sp, vr->fib4); | 825 | mlxsw_sp_fib_destroy(mlxsw_sp, fib4); |
| 821 | vr->fib4 = NULL; | ||
| 822 | return ERR_PTR(err); | 826 | return ERR_PTR(err); |
| 823 | } | 827 | } |
| 824 | 828 | ||
| @@ -3790,6 +3794,9 @@ mlxsw_sp_fib4_entry_offload_unset(struct mlxsw_sp_fib_entry *fib_entry) | |||
| 3790 | struct mlxsw_sp_nexthop_group *nh_grp = fib_entry->nh_group; | 3794 | struct mlxsw_sp_nexthop_group *nh_grp = fib_entry->nh_group; |
| 3791 | int i; | 3795 | int i; |
| 3792 | 3796 | ||
| 3797 | if (!list_is_singular(&nh_grp->fib_list)) | ||
| 3798 | return; | ||
| 3799 | |||
| 3793 | for (i = 0; i < nh_grp->count; i++) { | 3800 | for (i = 0; i < nh_grp->count; i++) { |
| 3794 | struct mlxsw_sp_nexthop *nh = &nh_grp->nexthops[i]; | 3801 | struct mlxsw_sp_nexthop *nh = &nh_grp->nexthops[i]; |
| 3795 | 3802 | ||
diff --git a/drivers/net/ethernet/qualcomm/rmnet/rmnet_config.c b/drivers/net/ethernet/qualcomm/rmnet/rmnet_config.c index 7e7704daf5f1..c4949183eef3 100644 --- a/drivers/net/ethernet/qualcomm/rmnet/rmnet_config.c +++ b/drivers/net/ethernet/qualcomm/rmnet/rmnet_config.c | |||
| @@ -43,12 +43,6 @@ | |||
| 43 | 43 | ||
| 44 | /* Local Definitions and Declarations */ | 44 | /* Local Definitions and Declarations */ |
| 45 | 45 | ||
| 46 | struct rmnet_walk_data { | ||
| 47 | struct net_device *real_dev; | ||
| 48 | struct list_head *head; | ||
| 49 | struct rmnet_port *port; | ||
| 50 | }; | ||
| 51 | |||
| 52 | static int rmnet_is_real_dev_registered(const struct net_device *real_dev) | 46 | static int rmnet_is_real_dev_registered(const struct net_device *real_dev) |
| 53 | { | 47 | { |
| 54 | return rcu_access_pointer(real_dev->rx_handler) == rmnet_rx_handler; | 48 | return rcu_access_pointer(real_dev->rx_handler) == rmnet_rx_handler; |
| @@ -112,17 +106,14 @@ static int rmnet_register_real_device(struct net_device *real_dev) | |||
| 112 | static void rmnet_unregister_bridge(struct net_device *dev, | 106 | static void rmnet_unregister_bridge(struct net_device *dev, |
| 113 | struct rmnet_port *port) | 107 | struct rmnet_port *port) |
| 114 | { | 108 | { |
| 115 | struct net_device *rmnet_dev, *bridge_dev; | ||
| 116 | struct rmnet_port *bridge_port; | 109 | struct rmnet_port *bridge_port; |
| 110 | struct net_device *bridge_dev; | ||
| 117 | 111 | ||
| 118 | if (port->rmnet_mode != RMNET_EPMODE_BRIDGE) | 112 | if (port->rmnet_mode != RMNET_EPMODE_BRIDGE) |
| 119 | return; | 113 | return; |
| 120 | 114 | ||
| 121 | /* bridge slave handling */ | 115 | /* bridge slave handling */ |
| 122 | if (!port->nr_rmnet_devs) { | 116 | if (!port->nr_rmnet_devs) { |
| 123 | rmnet_dev = netdev_master_upper_dev_get_rcu(dev); | ||
| 124 | netdev_upper_dev_unlink(dev, rmnet_dev); | ||
| 125 | |||
| 126 | bridge_dev = port->bridge_ep; | 117 | bridge_dev = port->bridge_ep; |
| 127 | 118 | ||
| 128 | bridge_port = rmnet_get_port_rtnl(bridge_dev); | 119 | bridge_port = rmnet_get_port_rtnl(bridge_dev); |
| @@ -132,9 +123,6 @@ static void rmnet_unregister_bridge(struct net_device *dev, | |||
| 132 | bridge_dev = port->bridge_ep; | 123 | bridge_dev = port->bridge_ep; |
| 133 | 124 | ||
| 134 | bridge_port = rmnet_get_port_rtnl(bridge_dev); | 125 | bridge_port = rmnet_get_port_rtnl(bridge_dev); |
| 135 | rmnet_dev = netdev_master_upper_dev_get_rcu(bridge_dev); | ||
| 136 | netdev_upper_dev_unlink(bridge_dev, rmnet_dev); | ||
| 137 | |||
| 138 | rmnet_unregister_real_device(bridge_dev, bridge_port); | 126 | rmnet_unregister_real_device(bridge_dev, bridge_port); |
| 139 | } | 127 | } |
| 140 | } | 128 | } |
| @@ -173,10 +161,6 @@ static int rmnet_newlink(struct net *src_net, struct net_device *dev, | |||
| 173 | if (err) | 161 | if (err) |
| 174 | goto err1; | 162 | goto err1; |
| 175 | 163 | ||
| 176 | err = netdev_master_upper_dev_link(dev, real_dev, NULL, NULL, extack); | ||
| 177 | if (err) | ||
| 178 | goto err2; | ||
| 179 | |||
| 180 | port->rmnet_mode = mode; | 164 | port->rmnet_mode = mode; |
| 181 | 165 | ||
| 182 | hlist_add_head_rcu(&ep->hlnode, &port->muxed_ep[mux_id]); | 166 | hlist_add_head_rcu(&ep->hlnode, &port->muxed_ep[mux_id]); |
| @@ -193,8 +177,6 @@ static int rmnet_newlink(struct net *src_net, struct net_device *dev, | |||
| 193 | 177 | ||
| 194 | return 0; | 178 | return 0; |
| 195 | 179 | ||
| 196 | err2: | ||
| 197 | rmnet_vnd_dellink(mux_id, port, ep); | ||
| 198 | err1: | 180 | err1: |
| 199 | rmnet_unregister_real_device(real_dev, port); | 181 | rmnet_unregister_real_device(real_dev, port); |
| 200 | err0: | 182 | err0: |
| @@ -204,14 +186,13 @@ err0: | |||
| 204 | 186 | ||
| 205 | static void rmnet_dellink(struct net_device *dev, struct list_head *head) | 187 | static void rmnet_dellink(struct net_device *dev, struct list_head *head) |
| 206 | { | 188 | { |
| 189 | struct rmnet_priv *priv = netdev_priv(dev); | ||
| 207 | struct net_device *real_dev; | 190 | struct net_device *real_dev; |
| 208 | struct rmnet_endpoint *ep; | 191 | struct rmnet_endpoint *ep; |
| 209 | struct rmnet_port *port; | 192 | struct rmnet_port *port; |
| 210 | u8 mux_id; | 193 | u8 mux_id; |
| 211 | 194 | ||
| 212 | rcu_read_lock(); | 195 | real_dev = priv->real_dev; |
| 213 | real_dev = netdev_master_upper_dev_get_rcu(dev); | ||
| 214 | rcu_read_unlock(); | ||
| 215 | 196 | ||
| 216 | if (!real_dev || !rmnet_is_real_dev_registered(real_dev)) | 197 | if (!real_dev || !rmnet_is_real_dev_registered(real_dev)) |
| 217 | return; | 198 | return; |
| @@ -219,7 +200,6 @@ static void rmnet_dellink(struct net_device *dev, struct list_head *head) | |||
| 219 | port = rmnet_get_port_rtnl(real_dev); | 200 | port = rmnet_get_port_rtnl(real_dev); |
| 220 | 201 | ||
| 221 | mux_id = rmnet_vnd_get_mux(dev); | 202 | mux_id = rmnet_vnd_get_mux(dev); |
| 222 | netdev_upper_dev_unlink(dev, real_dev); | ||
| 223 | 203 | ||
| 224 | ep = rmnet_get_endpoint(port, mux_id); | 204 | ep = rmnet_get_endpoint(port, mux_id); |
| 225 | if (ep) { | 205 | if (ep) { |
| @@ -233,30 +213,13 @@ static void rmnet_dellink(struct net_device *dev, struct list_head *head) | |||
| 233 | unregister_netdevice_queue(dev, head); | 213 | unregister_netdevice_queue(dev, head); |
| 234 | } | 214 | } |
| 235 | 215 | ||
| 236 | static int rmnet_dev_walk_unreg(struct net_device *rmnet_dev, void *data) | ||
| 237 | { | ||
| 238 | struct rmnet_walk_data *d = data; | ||
| 239 | struct rmnet_endpoint *ep; | ||
| 240 | u8 mux_id; | ||
| 241 | |||
| 242 | mux_id = rmnet_vnd_get_mux(rmnet_dev); | ||
| 243 | ep = rmnet_get_endpoint(d->port, mux_id); | ||
| 244 | if (ep) { | ||
| 245 | hlist_del_init_rcu(&ep->hlnode); | ||
| 246 | rmnet_vnd_dellink(mux_id, d->port, ep); | ||
| 247 | kfree(ep); | ||
| 248 | } | ||
| 249 | netdev_upper_dev_unlink(rmnet_dev, d->real_dev); | ||
| 250 | unregister_netdevice_queue(rmnet_dev, d->head); | ||
| 251 | |||
| 252 | return 0; | ||
| 253 | } | ||
| 254 | |||
| 255 | static void rmnet_force_unassociate_device(struct net_device *dev) | 216 | static void rmnet_force_unassociate_device(struct net_device *dev) |
| 256 | { | 217 | { |
| 257 | struct net_device *real_dev = dev; | 218 | struct net_device *real_dev = dev; |
| 258 | struct rmnet_walk_data d; | 219 | struct hlist_node *tmp_ep; |
| 220 | struct rmnet_endpoint *ep; | ||
| 259 | struct rmnet_port *port; | 221 | struct rmnet_port *port; |
| 222 | unsigned long bkt_ep; | ||
| 260 | LIST_HEAD(list); | 223 | LIST_HEAD(list); |
| 261 | 224 | ||
| 262 | if (!rmnet_is_real_dev_registered(real_dev)) | 225 | if (!rmnet_is_real_dev_registered(real_dev)) |
| @@ -264,16 +227,19 @@ static void rmnet_force_unassociate_device(struct net_device *dev) | |||
| 264 | 227 | ||
| 265 | ASSERT_RTNL(); | 228 | ASSERT_RTNL(); |
| 266 | 229 | ||
| 267 | d.real_dev = real_dev; | ||
| 268 | d.head = &list; | ||
| 269 | |||
| 270 | port = rmnet_get_port_rtnl(dev); | 230 | port = rmnet_get_port_rtnl(dev); |
| 271 | d.port = port; | ||
| 272 | 231 | ||
| 273 | rcu_read_lock(); | 232 | rcu_read_lock(); |
| 274 | rmnet_unregister_bridge(dev, port); | 233 | rmnet_unregister_bridge(dev, port); |
| 275 | 234 | ||
| 276 | netdev_walk_all_lower_dev_rcu(real_dev, rmnet_dev_walk_unreg, &d); | 235 | hash_for_each_safe(port->muxed_ep, bkt_ep, tmp_ep, ep, hlnode) { |
| 236 | unregister_netdevice_queue(ep->egress_dev, &list); | ||
| 237 | rmnet_vnd_dellink(ep->mux_id, port, ep); | ||
| 238 | |||
| 239 | hlist_del_init_rcu(&ep->hlnode); | ||
| 240 | kfree(ep); | ||
| 241 | } | ||
| 242 | |||
| 277 | rcu_read_unlock(); | 243 | rcu_read_unlock(); |
| 278 | unregister_netdevice_many(&list); | 244 | unregister_netdevice_many(&list); |
| 279 | 245 | ||
| @@ -422,11 +388,6 @@ int rmnet_add_bridge(struct net_device *rmnet_dev, | |||
| 422 | if (err) | 388 | if (err) |
| 423 | return -EBUSY; | 389 | return -EBUSY; |
| 424 | 390 | ||
| 425 | err = netdev_master_upper_dev_link(slave_dev, rmnet_dev, NULL, NULL, | ||
| 426 | extack); | ||
| 427 | if (err) | ||
| 428 | return -EINVAL; | ||
| 429 | |||
| 430 | slave_port = rmnet_get_port(slave_dev); | 391 | slave_port = rmnet_get_port(slave_dev); |
| 431 | slave_port->rmnet_mode = RMNET_EPMODE_BRIDGE; | 392 | slave_port->rmnet_mode = RMNET_EPMODE_BRIDGE; |
| 432 | slave_port->bridge_ep = real_dev; | 393 | slave_port->bridge_ep = real_dev; |
| @@ -449,7 +410,6 @@ int rmnet_del_bridge(struct net_device *rmnet_dev, | |||
| 449 | port->rmnet_mode = RMNET_EPMODE_VND; | 410 | port->rmnet_mode = RMNET_EPMODE_VND; |
| 450 | port->bridge_ep = NULL; | 411 | port->bridge_ep = NULL; |
| 451 | 412 | ||
| 452 | netdev_upper_dev_unlink(slave_dev, rmnet_dev); | ||
| 453 | slave_port = rmnet_get_port(slave_dev); | 413 | slave_port = rmnet_get_port(slave_dev); |
| 454 | rmnet_unregister_real_device(slave_dev, slave_port); | 414 | rmnet_unregister_real_device(slave_dev, slave_port); |
| 455 | 415 | ||
diff --git a/drivers/net/ethernet/qualcomm/rmnet/rmnet_map_command.c b/drivers/net/ethernet/qualcomm/rmnet/rmnet_map_command.c index 6bc328fb88e1..b0dbca070c00 100644 --- a/drivers/net/ethernet/qualcomm/rmnet/rmnet_map_command.c +++ b/drivers/net/ethernet/qualcomm/rmnet/rmnet_map_command.c | |||
| @@ -38,6 +38,11 @@ static u8 rmnet_map_do_flow_control(struct sk_buff *skb, | |||
| 38 | } | 38 | } |
| 39 | 39 | ||
| 40 | ep = rmnet_get_endpoint(port, mux_id); | 40 | ep = rmnet_get_endpoint(port, mux_id); |
| 41 | if (!ep) { | ||
| 42 | kfree_skb(skb); | ||
| 43 | return RX_HANDLER_CONSUMED; | ||
| 44 | } | ||
| 45 | |||
| 41 | vnd = ep->egress_dev; | 46 | vnd = ep->egress_dev; |
| 42 | 47 | ||
| 43 | ip_family = cmd->flow_control.ip_family; | 48 | ip_family = cmd->flow_control.ip_family; |
diff --git a/drivers/net/ethernet/qualcomm/rmnet/rmnet_vnd.c b/drivers/net/ethernet/qualcomm/rmnet/rmnet_vnd.c index 570a227acdd8..346d310914df 100644 --- a/drivers/net/ethernet/qualcomm/rmnet/rmnet_vnd.c +++ b/drivers/net/ethernet/qualcomm/rmnet/rmnet_vnd.c | |||
| @@ -121,7 +121,7 @@ static void rmnet_get_stats64(struct net_device *dev, | |||
| 121 | memset(&total_stats, 0, sizeof(struct rmnet_vnd_stats)); | 121 | memset(&total_stats, 0, sizeof(struct rmnet_vnd_stats)); |
| 122 | 122 | ||
| 123 | for_each_possible_cpu(cpu) { | 123 | for_each_possible_cpu(cpu) { |
| 124 | pcpu_ptr = this_cpu_ptr(priv->pcpu_stats); | 124 | pcpu_ptr = per_cpu_ptr(priv->pcpu_stats, cpu); |
| 125 | 125 | ||
| 126 | do { | 126 | do { |
| 127 | start = u64_stats_fetch_begin_irq(&pcpu_ptr->syncp); | 127 | start = u64_stats_fetch_begin_irq(&pcpu_ptr->syncp); |
diff --git a/drivers/net/ethernet/renesas/ravb_main.c b/drivers/net/ethernet/renesas/ravb_main.c index c87f57ca4437..a95fbd5510d9 100644 --- a/drivers/net/ethernet/renesas/ravb_main.c +++ b/drivers/net/ethernet/renesas/ravb_main.c | |||
| @@ -2255,9 +2255,6 @@ static int ravb_wol_setup(struct net_device *ndev) | |||
| 2255 | /* Enable MagicPacket */ | 2255 | /* Enable MagicPacket */ |
| 2256 | ravb_modify(ndev, ECMR, ECMR_MPDE, ECMR_MPDE); | 2256 | ravb_modify(ndev, ECMR, ECMR_MPDE, ECMR_MPDE); |
| 2257 | 2257 | ||
| 2258 | /* Increased clock usage so device won't be suspended */ | ||
| 2259 | clk_enable(priv->clk); | ||
| 2260 | |||
| 2261 | return enable_irq_wake(priv->emac_irq); | 2258 | return enable_irq_wake(priv->emac_irq); |
| 2262 | } | 2259 | } |
| 2263 | 2260 | ||
| @@ -2276,9 +2273,6 @@ static int ravb_wol_restore(struct net_device *ndev) | |||
| 2276 | if (ret < 0) | 2273 | if (ret < 0) |
| 2277 | return ret; | 2274 | return ret; |
| 2278 | 2275 | ||
| 2279 | /* Restore clock usage count */ | ||
| 2280 | clk_disable(priv->clk); | ||
| 2281 | |||
| 2282 | return disable_irq_wake(priv->emac_irq); | 2276 | return disable_irq_wake(priv->emac_irq); |
| 2283 | } | 2277 | } |
| 2284 | 2278 | ||
diff --git a/drivers/net/ethernet/renesas/sh_eth.c b/drivers/net/ethernet/renesas/sh_eth.c index a197e11f3a56..92dcf8717fc6 100644 --- a/drivers/net/ethernet/renesas/sh_eth.c +++ b/drivers/net/ethernet/renesas/sh_eth.c | |||
| @@ -40,7 +40,6 @@ | |||
| 40 | #include <linux/slab.h> | 40 | #include <linux/slab.h> |
| 41 | #include <linux/ethtool.h> | 41 | #include <linux/ethtool.h> |
| 42 | #include <linux/if_vlan.h> | 42 | #include <linux/if_vlan.h> |
| 43 | #include <linux/clk.h> | ||
| 44 | #include <linux/sh_eth.h> | 43 | #include <linux/sh_eth.h> |
| 45 | #include <linux/of_mdio.h> | 44 | #include <linux/of_mdio.h> |
| 46 | 45 | ||
| @@ -2304,7 +2303,7 @@ static void sh_eth_get_wol(struct net_device *ndev, struct ethtool_wolinfo *wol) | |||
| 2304 | wol->supported = 0; | 2303 | wol->supported = 0; |
| 2305 | wol->wolopts = 0; | 2304 | wol->wolopts = 0; |
| 2306 | 2305 | ||
| 2307 | if (mdp->cd->magic && mdp->clk) { | 2306 | if (mdp->cd->magic) { |
| 2308 | wol->supported = WAKE_MAGIC; | 2307 | wol->supported = WAKE_MAGIC; |
| 2309 | wol->wolopts = mdp->wol_enabled ? WAKE_MAGIC : 0; | 2308 | wol->wolopts = mdp->wol_enabled ? WAKE_MAGIC : 0; |
| 2310 | } | 2309 | } |
| @@ -2314,7 +2313,7 @@ static int sh_eth_set_wol(struct net_device *ndev, struct ethtool_wolinfo *wol) | |||
| 2314 | { | 2313 | { |
| 2315 | struct sh_eth_private *mdp = netdev_priv(ndev); | 2314 | struct sh_eth_private *mdp = netdev_priv(ndev); |
| 2316 | 2315 | ||
| 2317 | if (!mdp->cd->magic || !mdp->clk || wol->wolopts & ~WAKE_MAGIC) | 2316 | if (!mdp->cd->magic || wol->wolopts & ~WAKE_MAGIC) |
| 2318 | return -EOPNOTSUPP; | 2317 | return -EOPNOTSUPP; |
| 2319 | 2318 | ||
| 2320 | mdp->wol_enabled = !!(wol->wolopts & WAKE_MAGIC); | 2319 | mdp->wol_enabled = !!(wol->wolopts & WAKE_MAGIC); |
| @@ -3153,11 +3152,6 @@ static int sh_eth_drv_probe(struct platform_device *pdev) | |||
| 3153 | goto out_release; | 3152 | goto out_release; |
| 3154 | } | 3153 | } |
| 3155 | 3154 | ||
| 3156 | /* Get clock, if not found that's OK but Wake-On-Lan is unavailable */ | ||
| 3157 | mdp->clk = devm_clk_get(&pdev->dev, NULL); | ||
| 3158 | if (IS_ERR(mdp->clk)) | ||
| 3159 | mdp->clk = NULL; | ||
| 3160 | |||
| 3161 | ndev->base_addr = res->start; | 3155 | ndev->base_addr = res->start; |
| 3162 | 3156 | ||
| 3163 | spin_lock_init(&mdp->lock); | 3157 | spin_lock_init(&mdp->lock); |
| @@ -3278,7 +3272,7 @@ static int sh_eth_drv_probe(struct platform_device *pdev) | |||
| 3278 | if (ret) | 3272 | if (ret) |
| 3279 | goto out_napi_del; | 3273 | goto out_napi_del; |
| 3280 | 3274 | ||
| 3281 | if (mdp->cd->magic && mdp->clk) | 3275 | if (mdp->cd->magic) |
| 3282 | device_set_wakeup_capable(&pdev->dev, 1); | 3276 | device_set_wakeup_capable(&pdev->dev, 1); |
| 3283 | 3277 | ||
| 3284 | /* print device information */ | 3278 | /* print device information */ |
| @@ -3331,9 +3325,6 @@ static int sh_eth_wol_setup(struct net_device *ndev) | |||
| 3331 | /* Enable MagicPacket */ | 3325 | /* Enable MagicPacket */ |
| 3332 | sh_eth_modify(ndev, ECMR, ECMR_MPDE, ECMR_MPDE); | 3326 | sh_eth_modify(ndev, ECMR, ECMR_MPDE, ECMR_MPDE); |
| 3333 | 3327 | ||
| 3334 | /* Increased clock usage so device won't be suspended */ | ||
| 3335 | clk_enable(mdp->clk); | ||
| 3336 | |||
| 3337 | return enable_irq_wake(ndev->irq); | 3328 | return enable_irq_wake(ndev->irq); |
| 3338 | } | 3329 | } |
| 3339 | 3330 | ||
| @@ -3359,9 +3350,6 @@ static int sh_eth_wol_restore(struct net_device *ndev) | |||
| 3359 | if (ret < 0) | 3350 | if (ret < 0) |
| 3360 | return ret; | 3351 | return ret; |
| 3361 | 3352 | ||
| 3362 | /* Restore clock usage count */ | ||
| 3363 | clk_disable(mdp->clk); | ||
| 3364 | |||
| 3365 | return disable_irq_wake(ndev->irq); | 3353 | return disable_irq_wake(ndev->irq); |
| 3366 | } | 3354 | } |
| 3367 | 3355 | ||
diff --git a/drivers/net/ethernet/smsc/Kconfig b/drivers/net/ethernet/smsc/Kconfig index 63aca9f847e1..4c2f612e4414 100644 --- a/drivers/net/ethernet/smsc/Kconfig +++ b/drivers/net/ethernet/smsc/Kconfig | |||
| @@ -20,7 +20,7 @@ if NET_VENDOR_SMSC | |||
| 20 | 20 | ||
| 21 | config SMC9194 | 21 | config SMC9194 |
| 22 | tristate "SMC 9194 support" | 22 | tristate "SMC 9194 support" |
| 23 | depends on (ISA || MAC && BROKEN) | 23 | depends on ISA |
| 24 | select CRC32 | 24 | select CRC32 |
| 25 | ---help--- | 25 | ---help--- |
| 26 | This is support for the SMC9xxx based Ethernet cards. Choose this | 26 | This is support for the SMC9xxx based Ethernet cards. Choose this |
diff --git a/drivers/net/macvlan.c b/drivers/net/macvlan.c index a0f2be81d52e..8fc02d9db3d0 100644 --- a/drivers/net/macvlan.c +++ b/drivers/net/macvlan.c | |||
| @@ -1451,7 +1451,7 @@ destroy_macvlan_port: | |||
| 1451 | /* the macvlan port may be freed by macvlan_uninit when fail to register. | 1451 | /* the macvlan port may be freed by macvlan_uninit when fail to register. |
| 1452 | * so we destroy the macvlan port only when it's valid. | 1452 | * so we destroy the macvlan port only when it's valid. |
| 1453 | */ | 1453 | */ |
| 1454 | if (create && macvlan_port_get_rtnl(dev)) | 1454 | if (create && macvlan_port_get_rtnl(lowerdev)) |
| 1455 | macvlan_port_destroy(port->dev); | 1455 | macvlan_port_destroy(port->dev); |
| 1456 | return err; | 1456 | return err; |
| 1457 | } | 1457 | } |
diff --git a/drivers/net/phy/phy_device.c b/drivers/net/phy/phy_device.c index b13eed21c87d..d39ae77707ef 100644 --- a/drivers/net/phy/phy_device.c +++ b/drivers/net/phy/phy_device.c | |||
| @@ -1382,7 +1382,7 @@ int genphy_setup_forced(struct phy_device *phydev) | |||
| 1382 | ctl |= BMCR_FULLDPLX; | 1382 | ctl |= BMCR_FULLDPLX; |
| 1383 | 1383 | ||
| 1384 | return phy_modify(phydev, MII_BMCR, | 1384 | return phy_modify(phydev, MII_BMCR, |
| 1385 | BMCR_LOOPBACK | BMCR_ISOLATE | BMCR_PDOWN, ctl); | 1385 | ~(BMCR_LOOPBACK | BMCR_ISOLATE | BMCR_PDOWN), ctl); |
| 1386 | } | 1386 | } |
| 1387 | EXPORT_SYMBOL(genphy_setup_forced); | 1387 | EXPORT_SYMBOL(genphy_setup_forced); |
| 1388 | 1388 | ||
diff --git a/drivers/net/thunderbolt.c b/drivers/net/thunderbolt.c index ca5e375de27c..e0d6760f3219 100644 --- a/drivers/net/thunderbolt.c +++ b/drivers/net/thunderbolt.c | |||
| @@ -166,6 +166,8 @@ struct tbnet_ring { | |||
| 166 | * @connected_work: Worker that finalizes the ThunderboltIP connection | 166 | * @connected_work: Worker that finalizes the ThunderboltIP connection |
| 167 | * setup and enables DMA paths for high speed data | 167 | * setup and enables DMA paths for high speed data |
| 168 | * transfers | 168 | * transfers |
| 169 | * @disconnect_work: Worker that handles tearing down the ThunderboltIP | ||
| 170 | * connection | ||
| 169 | * @rx_hdr: Copy of the currently processed Rx frame. Used when a | 171 | * @rx_hdr: Copy of the currently processed Rx frame. Used when a |
| 170 | * network packet consists of multiple Thunderbolt frames. | 172 | * network packet consists of multiple Thunderbolt frames. |
| 171 | * In host byte order. | 173 | * In host byte order. |
| @@ -190,6 +192,7 @@ struct tbnet { | |||
| 190 | int login_retries; | 192 | int login_retries; |
| 191 | struct delayed_work login_work; | 193 | struct delayed_work login_work; |
| 192 | struct work_struct connected_work; | 194 | struct work_struct connected_work; |
| 195 | struct work_struct disconnect_work; | ||
| 193 | struct thunderbolt_ip_frame_header rx_hdr; | 196 | struct thunderbolt_ip_frame_header rx_hdr; |
| 194 | struct tbnet_ring rx_ring; | 197 | struct tbnet_ring rx_ring; |
| 195 | atomic_t frame_id; | 198 | atomic_t frame_id; |
| @@ -445,7 +448,7 @@ static int tbnet_handle_packet(const void *buf, size_t size, void *data) | |||
| 445 | case TBIP_LOGOUT: | 448 | case TBIP_LOGOUT: |
| 446 | ret = tbnet_logout_response(net, route, sequence, command_id); | 449 | ret = tbnet_logout_response(net, route, sequence, command_id); |
| 447 | if (!ret) | 450 | if (!ret) |
| 448 | tbnet_tear_down(net, false); | 451 | queue_work(system_long_wq, &net->disconnect_work); |
| 449 | break; | 452 | break; |
| 450 | 453 | ||
| 451 | default: | 454 | default: |
| @@ -659,6 +662,13 @@ static void tbnet_login_work(struct work_struct *work) | |||
| 659 | } | 662 | } |
| 660 | } | 663 | } |
| 661 | 664 | ||
| 665 | static void tbnet_disconnect_work(struct work_struct *work) | ||
| 666 | { | ||
| 667 | struct tbnet *net = container_of(work, typeof(*net), disconnect_work); | ||
| 668 | |||
| 669 | tbnet_tear_down(net, false); | ||
| 670 | } | ||
| 671 | |||
| 662 | static bool tbnet_check_frame(struct tbnet *net, const struct tbnet_frame *tf, | 672 | static bool tbnet_check_frame(struct tbnet *net, const struct tbnet_frame *tf, |
| 663 | const struct thunderbolt_ip_frame_header *hdr) | 673 | const struct thunderbolt_ip_frame_header *hdr) |
| 664 | { | 674 | { |
| @@ -881,6 +891,7 @@ static int tbnet_stop(struct net_device *dev) | |||
| 881 | 891 | ||
| 882 | napi_disable(&net->napi); | 892 | napi_disable(&net->napi); |
| 883 | 893 | ||
| 894 | cancel_work_sync(&net->disconnect_work); | ||
| 884 | tbnet_tear_down(net, true); | 895 | tbnet_tear_down(net, true); |
| 885 | 896 | ||
| 886 | tb_ring_free(net->rx_ring.ring); | 897 | tb_ring_free(net->rx_ring.ring); |
| @@ -1195,6 +1206,7 @@ static int tbnet_probe(struct tb_service *svc, const struct tb_service_id *id) | |||
| 1195 | net = netdev_priv(dev); | 1206 | net = netdev_priv(dev); |
| 1196 | INIT_DELAYED_WORK(&net->login_work, tbnet_login_work); | 1207 | INIT_DELAYED_WORK(&net->login_work, tbnet_login_work); |
| 1197 | INIT_WORK(&net->connected_work, tbnet_connected_work); | 1208 | INIT_WORK(&net->connected_work, tbnet_connected_work); |
| 1209 | INIT_WORK(&net->disconnect_work, tbnet_disconnect_work); | ||
| 1198 | mutex_init(&net->connection_lock); | 1210 | mutex_init(&net->connection_lock); |
| 1199 | atomic_set(&net->command_id, 0); | 1211 | atomic_set(&net->command_id, 0); |
| 1200 | atomic_set(&net->frame_id, 0); | 1212 | atomic_set(&net->frame_id, 0); |
| @@ -1270,10 +1282,7 @@ static int __maybe_unused tbnet_suspend(struct device *dev) | |||
| 1270 | stop_login(net); | 1282 | stop_login(net); |
| 1271 | if (netif_running(net->dev)) { | 1283 | if (netif_running(net->dev)) { |
| 1272 | netif_device_detach(net->dev); | 1284 | netif_device_detach(net->dev); |
| 1273 | tb_ring_stop(net->rx_ring.ring); | 1285 | tbnet_tear_down(net, true); |
| 1274 | tb_ring_stop(net->tx_ring.ring); | ||
| 1275 | tbnet_free_buffers(&net->rx_ring); | ||
| 1276 | tbnet_free_buffers(&net->tx_ring); | ||
| 1277 | } | 1286 | } |
| 1278 | 1287 | ||
| 1279 | return 0; | 1288 | return 0; |
diff --git a/drivers/net/tun.c b/drivers/net/tun.c index 81e6cc951e7f..b52258c327d2 100644 --- a/drivers/net/tun.c +++ b/drivers/net/tun.c | |||
| @@ -1489,27 +1489,23 @@ static struct sk_buff *tun_napi_alloc_frags(struct tun_file *tfile, | |||
| 1489 | skb->truesize += skb->data_len; | 1489 | skb->truesize += skb->data_len; |
| 1490 | 1490 | ||
| 1491 | for (i = 1; i < it->nr_segs; i++) { | 1491 | for (i = 1; i < it->nr_segs; i++) { |
| 1492 | struct page_frag *pfrag = ¤t->task_frag; | ||
| 1492 | size_t fragsz = it->iov[i].iov_len; | 1493 | size_t fragsz = it->iov[i].iov_len; |
| 1493 | unsigned long offset; | ||
| 1494 | struct page *page; | ||
| 1495 | void *data; | ||
| 1496 | 1494 | ||
| 1497 | if (fragsz == 0 || fragsz > PAGE_SIZE) { | 1495 | if (fragsz == 0 || fragsz > PAGE_SIZE) { |
| 1498 | err = -EINVAL; | 1496 | err = -EINVAL; |
| 1499 | goto free; | 1497 | goto free; |
| 1500 | } | 1498 | } |
| 1501 | 1499 | ||
| 1502 | local_bh_disable(); | 1500 | if (!skb_page_frag_refill(fragsz, pfrag, GFP_KERNEL)) { |
| 1503 | data = napi_alloc_frag(fragsz); | ||
| 1504 | local_bh_enable(); | ||
| 1505 | if (!data) { | ||
| 1506 | err = -ENOMEM; | 1501 | err = -ENOMEM; |
| 1507 | goto free; | 1502 | goto free; |
| 1508 | } | 1503 | } |
| 1509 | 1504 | ||
| 1510 | page = virt_to_head_page(data); | 1505 | skb_fill_page_desc(skb, i - 1, pfrag->page, |
| 1511 | offset = data - page_address(page); | 1506 | pfrag->offset, fragsz); |
| 1512 | skb_fill_page_desc(skb, i - 1, page, offset, fragsz); | 1507 | page_ref_inc(pfrag->page); |
| 1508 | pfrag->offset += fragsz; | ||
| 1513 | } | 1509 | } |
| 1514 | 1510 | ||
| 1515 | return skb; | 1511 | return skb; |
diff --git a/drivers/net/usb/smsc75xx.c b/drivers/net/usb/smsc75xx.c index d0a113743195..7a6a1fe79309 100644 --- a/drivers/net/usb/smsc75xx.c +++ b/drivers/net/usb/smsc75xx.c | |||
| @@ -954,10 +954,11 @@ static int smsc75xx_set_features(struct net_device *netdev, | |||
| 954 | /* it's racing here! */ | 954 | /* it's racing here! */ |
| 955 | 955 | ||
| 956 | ret = smsc75xx_write_reg(dev, RFE_CTL, pdata->rfe_ctl); | 956 | ret = smsc75xx_write_reg(dev, RFE_CTL, pdata->rfe_ctl); |
| 957 | if (ret < 0) | 957 | if (ret < 0) { |
| 958 | netdev_warn(dev->net, "Error writing RFE_CTL\n"); | 958 | netdev_warn(dev->net, "Error writing RFE_CTL\n"); |
| 959 | 959 | return ret; | |
| 960 | return ret; | 960 | } |
| 961 | return 0; | ||
| 961 | } | 962 | } |
| 962 | 963 | ||
| 963 | static int smsc75xx_wait_ready(struct usbnet *dev, int in_pm) | 964 | static int smsc75xx_wait_ready(struct usbnet *dev, int in_pm) |
diff --git a/drivers/net/virtio_net.c b/drivers/net/virtio_net.c index 626c27352ae2..9bb9e562b893 100644 --- a/drivers/net/virtio_net.c +++ b/drivers/net/virtio_net.c | |||
| @@ -443,12 +443,8 @@ static bool __virtnet_xdp_xmit(struct virtnet_info *vi, | |||
| 443 | sg_init_one(sq->sg, xdp->data, xdp->data_end - xdp->data); | 443 | sg_init_one(sq->sg, xdp->data, xdp->data_end - xdp->data); |
| 444 | 444 | ||
| 445 | err = virtqueue_add_outbuf(sq->vq, sq->sg, 1, xdp->data, GFP_ATOMIC); | 445 | err = virtqueue_add_outbuf(sq->vq, sq->sg, 1, xdp->data, GFP_ATOMIC); |
| 446 | if (unlikely(err)) { | 446 | if (unlikely(err)) |
| 447 | struct page *page = virt_to_head_page(xdp->data); | 447 | return false; /* Caller handle free/refcnt */ |
| 448 | |||
| 449 | put_page(page); | ||
| 450 | return false; | ||
| 451 | } | ||
| 452 | 448 | ||
| 453 | return true; | 449 | return true; |
| 454 | } | 450 | } |
| @@ -456,8 +452,18 @@ static bool __virtnet_xdp_xmit(struct virtnet_info *vi, | |||
| 456 | static int virtnet_xdp_xmit(struct net_device *dev, struct xdp_buff *xdp) | 452 | static int virtnet_xdp_xmit(struct net_device *dev, struct xdp_buff *xdp) |
| 457 | { | 453 | { |
| 458 | struct virtnet_info *vi = netdev_priv(dev); | 454 | struct virtnet_info *vi = netdev_priv(dev); |
| 459 | bool sent = __virtnet_xdp_xmit(vi, xdp); | 455 | struct receive_queue *rq = vi->rq; |
| 456 | struct bpf_prog *xdp_prog; | ||
| 457 | bool sent; | ||
| 460 | 458 | ||
| 459 | /* Only allow ndo_xdp_xmit if XDP is loaded on dev, as this | ||
| 460 | * indicate XDP resources have been successfully allocated. | ||
| 461 | */ | ||
| 462 | xdp_prog = rcu_dereference(rq->xdp_prog); | ||
| 463 | if (!xdp_prog) | ||
| 464 | return -ENXIO; | ||
| 465 | |||
| 466 | sent = __virtnet_xdp_xmit(vi, xdp); | ||
| 461 | if (!sent) | 467 | if (!sent) |
| 462 | return -ENOSPC; | 468 | return -ENOSPC; |
| 463 | return 0; | 469 | return 0; |
| @@ -546,8 +552,11 @@ static struct sk_buff *receive_small(struct net_device *dev, | |||
| 546 | unsigned int buflen = SKB_DATA_ALIGN(GOOD_PACKET_LEN + headroom) + | 552 | unsigned int buflen = SKB_DATA_ALIGN(GOOD_PACKET_LEN + headroom) + |
| 547 | SKB_DATA_ALIGN(sizeof(struct skb_shared_info)); | 553 | SKB_DATA_ALIGN(sizeof(struct skb_shared_info)); |
| 548 | struct page *page = virt_to_head_page(buf); | 554 | struct page *page = virt_to_head_page(buf); |
| 549 | unsigned int delta = 0, err; | 555 | unsigned int delta = 0; |
| 550 | struct page *xdp_page; | 556 | struct page *xdp_page; |
| 557 | bool sent; | ||
| 558 | int err; | ||
| 559 | |||
| 551 | len -= vi->hdr_len; | 560 | len -= vi->hdr_len; |
| 552 | 561 | ||
| 553 | rcu_read_lock(); | 562 | rcu_read_lock(); |
| @@ -558,7 +567,7 @@ static struct sk_buff *receive_small(struct net_device *dev, | |||
| 558 | void *orig_data; | 567 | void *orig_data; |
| 559 | u32 act; | 568 | u32 act; |
| 560 | 569 | ||
| 561 | if (unlikely(hdr->hdr.gso_type || hdr->hdr.flags)) | 570 | if (unlikely(hdr->hdr.gso_type)) |
| 562 | goto err_xdp; | 571 | goto err_xdp; |
| 563 | 572 | ||
| 564 | if (unlikely(xdp_headroom < virtnet_get_headroom(vi))) { | 573 | if (unlikely(xdp_headroom < virtnet_get_headroom(vi))) { |
| @@ -596,16 +605,19 @@ static struct sk_buff *receive_small(struct net_device *dev, | |||
| 596 | delta = orig_data - xdp.data; | 605 | delta = orig_data - xdp.data; |
| 597 | break; | 606 | break; |
| 598 | case XDP_TX: | 607 | case XDP_TX: |
| 599 | if (unlikely(!__virtnet_xdp_xmit(vi, &xdp))) | 608 | sent = __virtnet_xdp_xmit(vi, &xdp); |
| 609 | if (unlikely(!sent)) { | ||
| 600 | trace_xdp_exception(vi->dev, xdp_prog, act); | 610 | trace_xdp_exception(vi->dev, xdp_prog, act); |
| 601 | else | 611 | goto err_xdp; |
| 602 | *xdp_xmit = true; | 612 | } |
| 613 | *xdp_xmit = true; | ||
| 603 | rcu_read_unlock(); | 614 | rcu_read_unlock(); |
| 604 | goto xdp_xmit; | 615 | goto xdp_xmit; |
| 605 | case XDP_REDIRECT: | 616 | case XDP_REDIRECT: |
| 606 | err = xdp_do_redirect(dev, &xdp, xdp_prog); | 617 | err = xdp_do_redirect(dev, &xdp, xdp_prog); |
| 607 | if (!err) | 618 | if (err) |
| 608 | *xdp_xmit = true; | 619 | goto err_xdp; |
| 620 | *xdp_xmit = true; | ||
| 609 | rcu_read_unlock(); | 621 | rcu_read_unlock(); |
| 610 | goto xdp_xmit; | 622 | goto xdp_xmit; |
| 611 | default: | 623 | default: |
| @@ -677,7 +689,7 @@ static struct sk_buff *receive_mergeable(struct net_device *dev, | |||
| 677 | struct bpf_prog *xdp_prog; | 689 | struct bpf_prog *xdp_prog; |
| 678 | unsigned int truesize; | 690 | unsigned int truesize; |
| 679 | unsigned int headroom = mergeable_ctx_to_headroom(ctx); | 691 | unsigned int headroom = mergeable_ctx_to_headroom(ctx); |
| 680 | int err; | 692 | bool sent; |
| 681 | 693 | ||
| 682 | head_skb = NULL; | 694 | head_skb = NULL; |
| 683 | 695 | ||
| @@ -746,20 +758,18 @@ static struct sk_buff *receive_mergeable(struct net_device *dev, | |||
| 746 | } | 758 | } |
| 747 | break; | 759 | break; |
| 748 | case XDP_TX: | 760 | case XDP_TX: |
| 749 | if (unlikely(!__virtnet_xdp_xmit(vi, &xdp))) | 761 | sent = __virtnet_xdp_xmit(vi, &xdp); |
| 762 | if (unlikely(!sent)) { | ||
| 750 | trace_xdp_exception(vi->dev, xdp_prog, act); | 763 | trace_xdp_exception(vi->dev, xdp_prog, act); |
| 751 | else | 764 | if (unlikely(xdp_page != page)) |
| 752 | *xdp_xmit = true; | 765 | put_page(xdp_page); |
| 766 | goto err_xdp; | ||
| 767 | } | ||
| 768 | *xdp_xmit = true; | ||
| 753 | if (unlikely(xdp_page != page)) | 769 | if (unlikely(xdp_page != page)) |
| 754 | goto err_xdp; | 770 | goto err_xdp; |
| 755 | rcu_read_unlock(); | 771 | rcu_read_unlock(); |
| 756 | goto xdp_xmit; | 772 | goto xdp_xmit; |
| 757 | case XDP_REDIRECT: | ||
| 758 | err = xdp_do_redirect(dev, &xdp, xdp_prog); | ||
| 759 | if (!err) | ||
| 760 | *xdp_xmit = true; | ||
| 761 | rcu_read_unlock(); | ||
| 762 | goto xdp_xmit; | ||
| 763 | default: | 773 | default: |
| 764 | bpf_warn_invalid_xdp_action(act); | 774 | bpf_warn_invalid_xdp_action(act); |
| 765 | case XDP_ABORTED: | 775 | case XDP_ABORTED: |
diff --git a/drivers/net/wireless/mac80211_hwsim.c b/drivers/net/wireless/mac80211_hwsim.c index 1cf22e62e3dd..6e0af815f25e 100644 --- a/drivers/net/wireless/mac80211_hwsim.c +++ b/drivers/net/wireless/mac80211_hwsim.c | |||
| @@ -3516,7 +3516,7 @@ static int __init init_mac80211_hwsim(void) | |||
| 3516 | 3516 | ||
| 3517 | spin_lock_init(&hwsim_radio_lock); | 3517 | spin_lock_init(&hwsim_radio_lock); |
| 3518 | 3518 | ||
| 3519 | hwsim_wq = alloc_workqueue("hwsim_wq",WQ_MEM_RECLAIM,0); | 3519 | hwsim_wq = alloc_workqueue("hwsim_wq", 0, 0); |
| 3520 | if (!hwsim_wq) | 3520 | if (!hwsim_wq) |
| 3521 | return -ENOMEM; | 3521 | return -ENOMEM; |
| 3522 | rhashtable_init(&hwsim_radios_rht, &hwsim_rht_params); | 3522 | rhashtable_init(&hwsim_radios_rht, &hwsim_rht_params); |
diff --git a/drivers/nvme/host/core.c b/drivers/nvme/host/core.c index f431c32774f3..0fe7ea35c221 100644 --- a/drivers/nvme/host/core.c +++ b/drivers/nvme/host/core.c | |||
| @@ -120,8 +120,12 @@ int nvme_reset_ctrl_sync(struct nvme_ctrl *ctrl) | |||
| 120 | int ret; | 120 | int ret; |
| 121 | 121 | ||
| 122 | ret = nvme_reset_ctrl(ctrl); | 122 | ret = nvme_reset_ctrl(ctrl); |
| 123 | if (!ret) | 123 | if (!ret) { |
| 124 | flush_work(&ctrl->reset_work); | 124 | flush_work(&ctrl->reset_work); |
| 125 | if (ctrl->state != NVME_CTRL_LIVE) | ||
| 126 | ret = -ENETRESET; | ||
| 127 | } | ||
| 128 | |||
| 125 | return ret; | 129 | return ret; |
| 126 | } | 130 | } |
| 127 | EXPORT_SYMBOL_GPL(nvme_reset_ctrl_sync); | 131 | EXPORT_SYMBOL_GPL(nvme_reset_ctrl_sync); |
| @@ -265,7 +269,7 @@ bool nvme_change_ctrl_state(struct nvme_ctrl *ctrl, | |||
| 265 | switch (new_state) { | 269 | switch (new_state) { |
| 266 | case NVME_CTRL_ADMIN_ONLY: | 270 | case NVME_CTRL_ADMIN_ONLY: |
| 267 | switch (old_state) { | 271 | switch (old_state) { |
| 268 | case NVME_CTRL_RECONNECTING: | 272 | case NVME_CTRL_CONNECTING: |
| 269 | changed = true; | 273 | changed = true; |
| 270 | /* FALLTHRU */ | 274 | /* FALLTHRU */ |
| 271 | default: | 275 | default: |
| @@ -276,7 +280,7 @@ bool nvme_change_ctrl_state(struct nvme_ctrl *ctrl, | |||
| 276 | switch (old_state) { | 280 | switch (old_state) { |
| 277 | case NVME_CTRL_NEW: | 281 | case NVME_CTRL_NEW: |
| 278 | case NVME_CTRL_RESETTING: | 282 | case NVME_CTRL_RESETTING: |
| 279 | case NVME_CTRL_RECONNECTING: | 283 | case NVME_CTRL_CONNECTING: |
| 280 | changed = true; | 284 | changed = true; |
| 281 | /* FALLTHRU */ | 285 | /* FALLTHRU */ |
| 282 | default: | 286 | default: |
| @@ -294,9 +298,9 @@ bool nvme_change_ctrl_state(struct nvme_ctrl *ctrl, | |||
| 294 | break; | 298 | break; |
| 295 | } | 299 | } |
| 296 | break; | 300 | break; |
| 297 | case NVME_CTRL_RECONNECTING: | 301 | case NVME_CTRL_CONNECTING: |
| 298 | switch (old_state) { | 302 | switch (old_state) { |
| 299 | case NVME_CTRL_LIVE: | 303 | case NVME_CTRL_NEW: |
| 300 | case NVME_CTRL_RESETTING: | 304 | case NVME_CTRL_RESETTING: |
| 301 | changed = true; | 305 | changed = true; |
| 302 | /* FALLTHRU */ | 306 | /* FALLTHRU */ |
| @@ -309,7 +313,7 @@ bool nvme_change_ctrl_state(struct nvme_ctrl *ctrl, | |||
| 309 | case NVME_CTRL_LIVE: | 313 | case NVME_CTRL_LIVE: |
| 310 | case NVME_CTRL_ADMIN_ONLY: | 314 | case NVME_CTRL_ADMIN_ONLY: |
| 311 | case NVME_CTRL_RESETTING: | 315 | case NVME_CTRL_RESETTING: |
| 312 | case NVME_CTRL_RECONNECTING: | 316 | case NVME_CTRL_CONNECTING: |
| 313 | changed = true; | 317 | changed = true; |
| 314 | /* FALLTHRU */ | 318 | /* FALLTHRU */ |
| 315 | default: | 319 | default: |
| @@ -518,9 +522,11 @@ static blk_status_t nvme_setup_discard(struct nvme_ns *ns, struct request *req, | |||
| 518 | u64 slba = nvme_block_nr(ns, bio->bi_iter.bi_sector); | 522 | u64 slba = nvme_block_nr(ns, bio->bi_iter.bi_sector); |
| 519 | u32 nlb = bio->bi_iter.bi_size >> ns->lba_shift; | 523 | u32 nlb = bio->bi_iter.bi_size >> ns->lba_shift; |
| 520 | 524 | ||
| 521 | range[n].cattr = cpu_to_le32(0); | 525 | if (n < segments) { |
| 522 | range[n].nlb = cpu_to_le32(nlb); | 526 | range[n].cattr = cpu_to_le32(0); |
| 523 | range[n].slba = cpu_to_le64(slba); | 527 | range[n].nlb = cpu_to_le32(nlb); |
| 528 | range[n].slba = cpu_to_le64(slba); | ||
| 529 | } | ||
| 524 | n++; | 530 | n++; |
| 525 | } | 531 | } |
| 526 | 532 | ||
| @@ -794,13 +800,9 @@ static void nvme_keep_alive_end_io(struct request *rq, blk_status_t status) | |||
| 794 | 800 | ||
| 795 | static int nvme_keep_alive(struct nvme_ctrl *ctrl) | 801 | static int nvme_keep_alive(struct nvme_ctrl *ctrl) |
| 796 | { | 802 | { |
| 797 | struct nvme_command c; | ||
| 798 | struct request *rq; | 803 | struct request *rq; |
| 799 | 804 | ||
| 800 | memset(&c, 0, sizeof(c)); | 805 | rq = nvme_alloc_request(ctrl->admin_q, &ctrl->ka_cmd, BLK_MQ_REQ_RESERVED, |
| 801 | c.common.opcode = nvme_admin_keep_alive; | ||
| 802 | |||
| 803 | rq = nvme_alloc_request(ctrl->admin_q, &c, BLK_MQ_REQ_RESERVED, | ||
| 804 | NVME_QID_ANY); | 806 | NVME_QID_ANY); |
| 805 | if (IS_ERR(rq)) | 807 | if (IS_ERR(rq)) |
| 806 | return PTR_ERR(rq); | 808 | return PTR_ERR(rq); |
| @@ -832,6 +834,8 @@ void nvme_start_keep_alive(struct nvme_ctrl *ctrl) | |||
| 832 | return; | 834 | return; |
| 833 | 835 | ||
| 834 | INIT_DELAYED_WORK(&ctrl->ka_work, nvme_keep_alive_work); | 836 | INIT_DELAYED_WORK(&ctrl->ka_work, nvme_keep_alive_work); |
| 837 | memset(&ctrl->ka_cmd, 0, sizeof(ctrl->ka_cmd)); | ||
| 838 | ctrl->ka_cmd.common.opcode = nvme_admin_keep_alive; | ||
| 835 | schedule_delayed_work(&ctrl->ka_work, ctrl->kato * HZ); | 839 | schedule_delayed_work(&ctrl->ka_work, ctrl->kato * HZ); |
| 836 | } | 840 | } |
| 837 | EXPORT_SYMBOL_GPL(nvme_start_keep_alive); | 841 | EXPORT_SYMBOL_GPL(nvme_start_keep_alive); |
| @@ -1117,14 +1121,19 @@ static u32 nvme_passthru_start(struct nvme_ctrl *ctrl, struct nvme_ns *ns, | |||
| 1117 | 1121 | ||
| 1118 | static void nvme_update_formats(struct nvme_ctrl *ctrl) | 1122 | static void nvme_update_formats(struct nvme_ctrl *ctrl) |
| 1119 | { | 1123 | { |
| 1120 | struct nvme_ns *ns; | 1124 | struct nvme_ns *ns, *next; |
| 1125 | LIST_HEAD(rm_list); | ||
| 1121 | 1126 | ||
| 1122 | mutex_lock(&ctrl->namespaces_mutex); | 1127 | mutex_lock(&ctrl->namespaces_mutex); |
| 1123 | list_for_each_entry(ns, &ctrl->namespaces, list) { | 1128 | list_for_each_entry(ns, &ctrl->namespaces, list) { |
| 1124 | if (ns->disk && nvme_revalidate_disk(ns->disk)) | 1129 | if (ns->disk && nvme_revalidate_disk(ns->disk)) { |
| 1125 | nvme_ns_remove(ns); | 1130 | list_move_tail(&ns->list, &rm_list); |
| 1131 | } | ||
| 1126 | } | 1132 | } |
| 1127 | mutex_unlock(&ctrl->namespaces_mutex); | 1133 | mutex_unlock(&ctrl->namespaces_mutex); |
| 1134 | |||
| 1135 | list_for_each_entry_safe(ns, next, &rm_list, list) | ||
| 1136 | nvme_ns_remove(ns); | ||
| 1128 | } | 1137 | } |
| 1129 | 1138 | ||
| 1130 | static void nvme_passthru_end(struct nvme_ctrl *ctrl, u32 effects) | 1139 | static void nvme_passthru_end(struct nvme_ctrl *ctrl, u32 effects) |
| @@ -2687,7 +2696,7 @@ static ssize_t nvme_sysfs_show_state(struct device *dev, | |||
| 2687 | [NVME_CTRL_LIVE] = "live", | 2696 | [NVME_CTRL_LIVE] = "live", |
| 2688 | [NVME_CTRL_ADMIN_ONLY] = "only-admin", | 2697 | [NVME_CTRL_ADMIN_ONLY] = "only-admin", |
| 2689 | [NVME_CTRL_RESETTING] = "resetting", | 2698 | [NVME_CTRL_RESETTING] = "resetting", |
| 2690 | [NVME_CTRL_RECONNECTING]= "reconnecting", | 2699 | [NVME_CTRL_CONNECTING] = "connecting", |
| 2691 | [NVME_CTRL_DELETING] = "deleting", | 2700 | [NVME_CTRL_DELETING] = "deleting", |
| 2692 | [NVME_CTRL_DEAD] = "dead", | 2701 | [NVME_CTRL_DEAD] = "dead", |
| 2693 | }; | 2702 | }; |
diff --git a/drivers/nvme/host/fabrics.h b/drivers/nvme/host/fabrics.h index 25b19f722f5b..a3145d90c1d2 100644 --- a/drivers/nvme/host/fabrics.h +++ b/drivers/nvme/host/fabrics.h | |||
| @@ -171,13 +171,14 @@ static inline blk_status_t nvmf_check_init_req(struct nvme_ctrl *ctrl, | |||
| 171 | cmd->common.opcode != nvme_fabrics_command || | 171 | cmd->common.opcode != nvme_fabrics_command || |
| 172 | cmd->fabrics.fctype != nvme_fabrics_type_connect) { | 172 | cmd->fabrics.fctype != nvme_fabrics_type_connect) { |
| 173 | /* | 173 | /* |
| 174 | * Reconnecting state means transport disruption, which can take | 174 | * Connecting state means transport disruption or initial |
| 175 | * a long time and even might fail permanently, fail fast to | 175 | * establishment, which can take a long time and even might |
| 176 | * give upper layers a chance to failover. | 176 | * fail permanently, fail fast to give upper layers a chance |
| 177 | * to failover. | ||
| 177 | * Deleting state means that the ctrl will never accept commands | 178 | * Deleting state means that the ctrl will never accept commands |
| 178 | * again, fail it permanently. | 179 | * again, fail it permanently. |
| 179 | */ | 180 | */ |
| 180 | if (ctrl->state == NVME_CTRL_RECONNECTING || | 181 | if (ctrl->state == NVME_CTRL_CONNECTING || |
| 181 | ctrl->state == NVME_CTRL_DELETING) { | 182 | ctrl->state == NVME_CTRL_DELETING) { |
| 182 | nvme_req(rq)->status = NVME_SC_ABORT_REQ; | 183 | nvme_req(rq)->status = NVME_SC_ABORT_REQ; |
| 183 | return BLK_STS_IOERR; | 184 | return BLK_STS_IOERR; |
diff --git a/drivers/nvme/host/fc.c b/drivers/nvme/host/fc.c index b856d7c919d2..7f51f8414b97 100644 --- a/drivers/nvme/host/fc.c +++ b/drivers/nvme/host/fc.c | |||
| @@ -55,9 +55,7 @@ struct nvme_fc_queue { | |||
| 55 | 55 | ||
| 56 | enum nvme_fcop_flags { | 56 | enum nvme_fcop_flags { |
| 57 | FCOP_FLAGS_TERMIO = (1 << 0), | 57 | FCOP_FLAGS_TERMIO = (1 << 0), |
| 58 | FCOP_FLAGS_RELEASED = (1 << 1), | 58 | FCOP_FLAGS_AEN = (1 << 1), |
| 59 | FCOP_FLAGS_COMPLETE = (1 << 2), | ||
| 60 | FCOP_FLAGS_AEN = (1 << 3), | ||
| 61 | }; | 59 | }; |
| 62 | 60 | ||
| 63 | struct nvmefc_ls_req_op { | 61 | struct nvmefc_ls_req_op { |
| @@ -532,7 +530,7 @@ nvme_fc_resume_controller(struct nvme_fc_ctrl *ctrl) | |||
| 532 | { | 530 | { |
| 533 | switch (ctrl->ctrl.state) { | 531 | switch (ctrl->ctrl.state) { |
| 534 | case NVME_CTRL_NEW: | 532 | case NVME_CTRL_NEW: |
| 535 | case NVME_CTRL_RECONNECTING: | 533 | case NVME_CTRL_CONNECTING: |
| 536 | /* | 534 | /* |
| 537 | * As all reconnects were suppressed, schedule a | 535 | * As all reconnects were suppressed, schedule a |
| 538 | * connect. | 536 | * connect. |
| @@ -777,7 +775,7 @@ nvme_fc_ctrl_connectivity_loss(struct nvme_fc_ctrl *ctrl) | |||
| 777 | } | 775 | } |
| 778 | break; | 776 | break; |
| 779 | 777 | ||
| 780 | case NVME_CTRL_RECONNECTING: | 778 | case NVME_CTRL_CONNECTING: |
| 781 | /* | 779 | /* |
| 782 | * The association has already been terminated and the | 780 | * The association has already been terminated and the |
| 783 | * controller is attempting reconnects. No need to do anything | 781 | * controller is attempting reconnects. No need to do anything |
| @@ -1470,7 +1468,6 @@ nvme_fc_xmt_disconnect_assoc(struct nvme_fc_ctrl *ctrl) | |||
| 1470 | 1468 | ||
| 1471 | /* *********************** NVME Ctrl Routines **************************** */ | 1469 | /* *********************** NVME Ctrl Routines **************************** */ |
| 1472 | 1470 | ||
| 1473 | static void __nvme_fc_final_op_cleanup(struct request *rq); | ||
| 1474 | static void nvme_fc_error_recovery(struct nvme_fc_ctrl *ctrl, char *errmsg); | 1471 | static void nvme_fc_error_recovery(struct nvme_fc_ctrl *ctrl, char *errmsg); |
| 1475 | 1472 | ||
| 1476 | static int | 1473 | static int |
| @@ -1512,13 +1509,19 @@ nvme_fc_exit_request(struct blk_mq_tag_set *set, struct request *rq, | |||
| 1512 | static int | 1509 | static int |
| 1513 | __nvme_fc_abort_op(struct nvme_fc_ctrl *ctrl, struct nvme_fc_fcp_op *op) | 1510 | __nvme_fc_abort_op(struct nvme_fc_ctrl *ctrl, struct nvme_fc_fcp_op *op) |
| 1514 | { | 1511 | { |
| 1515 | int state; | 1512 | unsigned long flags; |
| 1513 | int opstate; | ||
| 1514 | |||
| 1515 | spin_lock_irqsave(&ctrl->lock, flags); | ||
| 1516 | opstate = atomic_xchg(&op->state, FCPOP_STATE_ABORTED); | ||
| 1517 | if (opstate != FCPOP_STATE_ACTIVE) | ||
| 1518 | atomic_set(&op->state, opstate); | ||
| 1519 | else if (ctrl->flags & FCCTRL_TERMIO) | ||
| 1520 | ctrl->iocnt++; | ||
| 1521 | spin_unlock_irqrestore(&ctrl->lock, flags); | ||
| 1516 | 1522 | ||
| 1517 | state = atomic_xchg(&op->state, FCPOP_STATE_ABORTED); | 1523 | if (opstate != FCPOP_STATE_ACTIVE) |
| 1518 | if (state != FCPOP_STATE_ACTIVE) { | ||
| 1519 | atomic_set(&op->state, state); | ||
| 1520 | return -ECANCELED; | 1524 | return -ECANCELED; |
| 1521 | } | ||
| 1522 | 1525 | ||
| 1523 | ctrl->lport->ops->fcp_abort(&ctrl->lport->localport, | 1526 | ctrl->lport->ops->fcp_abort(&ctrl->lport->localport, |
| 1524 | &ctrl->rport->remoteport, | 1527 | &ctrl->rport->remoteport, |
| @@ -1532,60 +1535,26 @@ static void | |||
| 1532 | nvme_fc_abort_aen_ops(struct nvme_fc_ctrl *ctrl) | 1535 | nvme_fc_abort_aen_ops(struct nvme_fc_ctrl *ctrl) |
| 1533 | { | 1536 | { |
| 1534 | struct nvme_fc_fcp_op *aen_op = ctrl->aen_ops; | 1537 | struct nvme_fc_fcp_op *aen_op = ctrl->aen_ops; |
| 1535 | unsigned long flags; | 1538 | int i; |
| 1536 | int i, ret; | ||
| 1537 | |||
| 1538 | for (i = 0; i < NVME_NR_AEN_COMMANDS; i++, aen_op++) { | ||
| 1539 | if (atomic_read(&aen_op->state) != FCPOP_STATE_ACTIVE) | ||
| 1540 | continue; | ||
| 1541 | |||
| 1542 | spin_lock_irqsave(&ctrl->lock, flags); | ||
| 1543 | if (ctrl->flags & FCCTRL_TERMIO) { | ||
| 1544 | ctrl->iocnt++; | ||
| 1545 | aen_op->flags |= FCOP_FLAGS_TERMIO; | ||
| 1546 | } | ||
| 1547 | spin_unlock_irqrestore(&ctrl->lock, flags); | ||
| 1548 | |||
| 1549 | ret = __nvme_fc_abort_op(ctrl, aen_op); | ||
| 1550 | if (ret) { | ||
| 1551 | /* | ||
| 1552 | * if __nvme_fc_abort_op failed the io wasn't | ||
| 1553 | * active. Thus this call path is running in | ||
| 1554 | * parallel to the io complete. Treat as non-error. | ||
| 1555 | */ | ||
| 1556 | 1539 | ||
| 1557 | /* back out the flags/counters */ | 1540 | for (i = 0; i < NVME_NR_AEN_COMMANDS; i++, aen_op++) |
| 1558 | spin_lock_irqsave(&ctrl->lock, flags); | 1541 | __nvme_fc_abort_op(ctrl, aen_op); |
| 1559 | if (ctrl->flags & FCCTRL_TERMIO) | ||
| 1560 | ctrl->iocnt--; | ||
| 1561 | aen_op->flags &= ~FCOP_FLAGS_TERMIO; | ||
| 1562 | spin_unlock_irqrestore(&ctrl->lock, flags); | ||
| 1563 | return; | ||
| 1564 | } | ||
| 1565 | } | ||
| 1566 | } | 1542 | } |
| 1567 | 1543 | ||
| 1568 | static inline int | 1544 | static inline void |
| 1569 | __nvme_fc_fcpop_chk_teardowns(struct nvme_fc_ctrl *ctrl, | 1545 | __nvme_fc_fcpop_chk_teardowns(struct nvme_fc_ctrl *ctrl, |
| 1570 | struct nvme_fc_fcp_op *op) | 1546 | struct nvme_fc_fcp_op *op, int opstate) |
| 1571 | { | 1547 | { |
| 1572 | unsigned long flags; | 1548 | unsigned long flags; |
| 1573 | bool complete_rq = false; | ||
| 1574 | 1549 | ||
| 1575 | spin_lock_irqsave(&ctrl->lock, flags); | 1550 | if (opstate == FCPOP_STATE_ABORTED) { |
| 1576 | if (unlikely(op->flags & FCOP_FLAGS_TERMIO)) { | 1551 | spin_lock_irqsave(&ctrl->lock, flags); |
| 1577 | if (ctrl->flags & FCCTRL_TERMIO) { | 1552 | if (ctrl->flags & FCCTRL_TERMIO) { |
| 1578 | if (!--ctrl->iocnt) | 1553 | if (!--ctrl->iocnt) |
| 1579 | wake_up(&ctrl->ioabort_wait); | 1554 | wake_up(&ctrl->ioabort_wait); |
| 1580 | } | 1555 | } |
| 1556 | spin_unlock_irqrestore(&ctrl->lock, flags); | ||
| 1581 | } | 1557 | } |
| 1582 | if (op->flags & FCOP_FLAGS_RELEASED) | ||
| 1583 | complete_rq = true; | ||
| 1584 | else | ||
| 1585 | op->flags |= FCOP_FLAGS_COMPLETE; | ||
| 1586 | spin_unlock_irqrestore(&ctrl->lock, flags); | ||
| 1587 | |||
| 1588 | return complete_rq; | ||
| 1589 | } | 1558 | } |
| 1590 | 1559 | ||
| 1591 | static void | 1560 | static void |
| @@ -1601,6 +1570,7 @@ nvme_fc_fcpio_done(struct nvmefc_fcp_req *req) | |||
| 1601 | __le16 status = cpu_to_le16(NVME_SC_SUCCESS << 1); | 1570 | __le16 status = cpu_to_le16(NVME_SC_SUCCESS << 1); |
| 1602 | union nvme_result result; | 1571 | union nvme_result result; |
| 1603 | bool terminate_assoc = true; | 1572 | bool terminate_assoc = true; |
| 1573 | int opstate; | ||
| 1604 | 1574 | ||
| 1605 | /* | 1575 | /* |
| 1606 | * WARNING: | 1576 | * WARNING: |
| @@ -1639,11 +1609,12 @@ nvme_fc_fcpio_done(struct nvmefc_fcp_req *req) | |||
| 1639 | * association to be terminated. | 1609 | * association to be terminated. |
| 1640 | */ | 1610 | */ |
| 1641 | 1611 | ||
| 1612 | opstate = atomic_xchg(&op->state, FCPOP_STATE_COMPLETE); | ||
| 1613 | |||
| 1642 | fc_dma_sync_single_for_cpu(ctrl->lport->dev, op->fcp_req.rspdma, | 1614 | fc_dma_sync_single_for_cpu(ctrl->lport->dev, op->fcp_req.rspdma, |
| 1643 | sizeof(op->rsp_iu), DMA_FROM_DEVICE); | 1615 | sizeof(op->rsp_iu), DMA_FROM_DEVICE); |
| 1644 | 1616 | ||
| 1645 | if (atomic_read(&op->state) == FCPOP_STATE_ABORTED || | 1617 | if (opstate == FCPOP_STATE_ABORTED) |
| 1646 | op->flags & FCOP_FLAGS_TERMIO) | ||
| 1647 | status = cpu_to_le16(NVME_SC_ABORT_REQ << 1); | 1618 | status = cpu_to_le16(NVME_SC_ABORT_REQ << 1); |
| 1648 | else if (freq->status) | 1619 | else if (freq->status) |
| 1649 | status = cpu_to_le16(NVME_SC_INTERNAL << 1); | 1620 | status = cpu_to_le16(NVME_SC_INTERNAL << 1); |
| @@ -1708,7 +1679,7 @@ nvme_fc_fcpio_done(struct nvmefc_fcp_req *req) | |||
| 1708 | done: | 1679 | done: |
| 1709 | if (op->flags & FCOP_FLAGS_AEN) { | 1680 | if (op->flags & FCOP_FLAGS_AEN) { |
| 1710 | nvme_complete_async_event(&queue->ctrl->ctrl, status, &result); | 1681 | nvme_complete_async_event(&queue->ctrl->ctrl, status, &result); |
| 1711 | __nvme_fc_fcpop_chk_teardowns(ctrl, op); | 1682 | __nvme_fc_fcpop_chk_teardowns(ctrl, op, opstate); |
| 1712 | atomic_set(&op->state, FCPOP_STATE_IDLE); | 1683 | atomic_set(&op->state, FCPOP_STATE_IDLE); |
| 1713 | op->flags = FCOP_FLAGS_AEN; /* clear other flags */ | 1684 | op->flags = FCOP_FLAGS_AEN; /* clear other flags */ |
| 1714 | nvme_fc_ctrl_put(ctrl); | 1685 | nvme_fc_ctrl_put(ctrl); |
| @@ -1722,13 +1693,11 @@ done: | |||
| 1722 | if (status && | 1693 | if (status && |
| 1723 | (blk_queue_dying(rq->q) || | 1694 | (blk_queue_dying(rq->q) || |
| 1724 | ctrl->ctrl.state == NVME_CTRL_NEW || | 1695 | ctrl->ctrl.state == NVME_CTRL_NEW || |
| 1725 | ctrl->ctrl.state == NVME_CTRL_RECONNECTING)) | 1696 | ctrl->ctrl.state == NVME_CTRL_CONNECTING)) |
| 1726 | status |= cpu_to_le16(NVME_SC_DNR << 1); | 1697 | status |= cpu_to_le16(NVME_SC_DNR << 1); |
| 1727 | 1698 | ||
| 1728 | if (__nvme_fc_fcpop_chk_teardowns(ctrl, op)) | 1699 | __nvme_fc_fcpop_chk_teardowns(ctrl, op, opstate); |
| 1729 | __nvme_fc_final_op_cleanup(rq); | 1700 | nvme_end_request(rq, status, result); |
| 1730 | else | ||
| 1731 | nvme_end_request(rq, status, result); | ||
| 1732 | 1701 | ||
| 1733 | check_error: | 1702 | check_error: |
| 1734 | if (terminate_assoc) | 1703 | if (terminate_assoc) |
| @@ -2415,46 +2384,16 @@ nvme_fc_submit_async_event(struct nvme_ctrl *arg) | |||
| 2415 | } | 2384 | } |
| 2416 | 2385 | ||
| 2417 | static void | 2386 | static void |
| 2418 | __nvme_fc_final_op_cleanup(struct request *rq) | 2387 | nvme_fc_complete_rq(struct request *rq) |
| 2419 | { | 2388 | { |
| 2420 | struct nvme_fc_fcp_op *op = blk_mq_rq_to_pdu(rq); | 2389 | struct nvme_fc_fcp_op *op = blk_mq_rq_to_pdu(rq); |
| 2421 | struct nvme_fc_ctrl *ctrl = op->ctrl; | 2390 | struct nvme_fc_ctrl *ctrl = op->ctrl; |
| 2422 | 2391 | ||
| 2423 | atomic_set(&op->state, FCPOP_STATE_IDLE); | 2392 | atomic_set(&op->state, FCPOP_STATE_IDLE); |
| 2424 | op->flags &= ~(FCOP_FLAGS_TERMIO | FCOP_FLAGS_RELEASED | | ||
| 2425 | FCOP_FLAGS_COMPLETE); | ||
| 2426 | 2393 | ||
| 2427 | nvme_fc_unmap_data(ctrl, rq, op); | 2394 | nvme_fc_unmap_data(ctrl, rq, op); |
| 2428 | nvme_complete_rq(rq); | 2395 | nvme_complete_rq(rq); |
| 2429 | nvme_fc_ctrl_put(ctrl); | 2396 | nvme_fc_ctrl_put(ctrl); |
| 2430 | |||
| 2431 | } | ||
| 2432 | |||
| 2433 | static void | ||
| 2434 | nvme_fc_complete_rq(struct request *rq) | ||
| 2435 | { | ||
| 2436 | struct nvme_fc_fcp_op *op = blk_mq_rq_to_pdu(rq); | ||
| 2437 | struct nvme_fc_ctrl *ctrl = op->ctrl; | ||
| 2438 | unsigned long flags; | ||
| 2439 | bool completed = false; | ||
| 2440 | |||
| 2441 | /* | ||
| 2442 | * the core layer, on controller resets after calling | ||
| 2443 | * nvme_shutdown_ctrl(), calls complete_rq without our | ||
| 2444 | * calling blk_mq_complete_request(), thus there may still | ||
| 2445 | * be live i/o outstanding with the LLDD. Means transport has | ||
| 2446 | * to track complete calls vs fcpio_done calls to know what | ||
| 2447 | * path to take on completes and dones. | ||
| 2448 | */ | ||
| 2449 | spin_lock_irqsave(&ctrl->lock, flags); | ||
| 2450 | if (op->flags & FCOP_FLAGS_COMPLETE) | ||
| 2451 | completed = true; | ||
| 2452 | else | ||
| 2453 | op->flags |= FCOP_FLAGS_RELEASED; | ||
| 2454 | spin_unlock_irqrestore(&ctrl->lock, flags); | ||
| 2455 | |||
| 2456 | if (completed) | ||
| 2457 | __nvme_fc_final_op_cleanup(rq); | ||
| 2458 | } | 2397 | } |
| 2459 | 2398 | ||
| 2460 | /* | 2399 | /* |
| @@ -2476,35 +2415,11 @@ nvme_fc_terminate_exchange(struct request *req, void *data, bool reserved) | |||
| 2476 | struct nvme_ctrl *nctrl = data; | 2415 | struct nvme_ctrl *nctrl = data; |
| 2477 | struct nvme_fc_ctrl *ctrl = to_fc_ctrl(nctrl); | 2416 | struct nvme_fc_ctrl *ctrl = to_fc_ctrl(nctrl); |
| 2478 | struct nvme_fc_fcp_op *op = blk_mq_rq_to_pdu(req); | 2417 | struct nvme_fc_fcp_op *op = blk_mq_rq_to_pdu(req); |
| 2479 | unsigned long flags; | ||
| 2480 | int status; | ||
| 2481 | 2418 | ||
| 2482 | if (!blk_mq_request_started(req)) | 2419 | if (!blk_mq_request_started(req)) |
| 2483 | return; | 2420 | return; |
| 2484 | 2421 | ||
| 2485 | spin_lock_irqsave(&ctrl->lock, flags); | 2422 | __nvme_fc_abort_op(ctrl, op); |
| 2486 | if (ctrl->flags & FCCTRL_TERMIO) { | ||
| 2487 | ctrl->iocnt++; | ||
| 2488 | op->flags |= FCOP_FLAGS_TERMIO; | ||
| 2489 | } | ||
| 2490 | spin_unlock_irqrestore(&ctrl->lock, flags); | ||
| 2491 | |||
| 2492 | status = __nvme_fc_abort_op(ctrl, op); | ||
| 2493 | if (status) { | ||
| 2494 | /* | ||
| 2495 | * if __nvme_fc_abort_op failed the io wasn't | ||
| 2496 | * active. Thus this call path is running in | ||
| 2497 | * parallel to the io complete. Treat as non-error. | ||
| 2498 | */ | ||
| 2499 | |||
| 2500 | /* back out the flags/counters */ | ||
| 2501 | spin_lock_irqsave(&ctrl->lock, flags); | ||
| 2502 | if (ctrl->flags & FCCTRL_TERMIO) | ||
| 2503 | ctrl->iocnt--; | ||
| 2504 | op->flags &= ~FCOP_FLAGS_TERMIO; | ||
| 2505 | spin_unlock_irqrestore(&ctrl->lock, flags); | ||
| 2506 | return; | ||
| 2507 | } | ||
| 2508 | } | 2423 | } |
| 2509 | 2424 | ||
| 2510 | 2425 | ||
| @@ -2943,7 +2858,7 @@ nvme_fc_reconnect_or_delete(struct nvme_fc_ctrl *ctrl, int status) | |||
| 2943 | unsigned long recon_delay = ctrl->ctrl.opts->reconnect_delay * HZ; | 2858 | unsigned long recon_delay = ctrl->ctrl.opts->reconnect_delay * HZ; |
| 2944 | bool recon = true; | 2859 | bool recon = true; |
| 2945 | 2860 | ||
| 2946 | if (ctrl->ctrl.state != NVME_CTRL_RECONNECTING) | 2861 | if (ctrl->ctrl.state != NVME_CTRL_CONNECTING) |
| 2947 | return; | 2862 | return; |
| 2948 | 2863 | ||
| 2949 | if (portptr->port_state == FC_OBJSTATE_ONLINE) | 2864 | if (portptr->port_state == FC_OBJSTATE_ONLINE) |
| @@ -2991,10 +2906,10 @@ nvme_fc_reset_ctrl_work(struct work_struct *work) | |||
| 2991 | /* will block will waiting for io to terminate */ | 2906 | /* will block will waiting for io to terminate */ |
| 2992 | nvme_fc_delete_association(ctrl); | 2907 | nvme_fc_delete_association(ctrl); |
| 2993 | 2908 | ||
| 2994 | if (!nvme_change_ctrl_state(&ctrl->ctrl, NVME_CTRL_RECONNECTING)) { | 2909 | if (!nvme_change_ctrl_state(&ctrl->ctrl, NVME_CTRL_CONNECTING)) { |
| 2995 | dev_err(ctrl->ctrl.device, | 2910 | dev_err(ctrl->ctrl.device, |
| 2996 | "NVME-FC{%d}: error_recovery: Couldn't change state " | 2911 | "NVME-FC{%d}: error_recovery: Couldn't change state " |
| 2997 | "to RECONNECTING\n", ctrl->cnum); | 2912 | "to CONNECTING\n", ctrl->cnum); |
| 2998 | return; | 2913 | return; |
| 2999 | } | 2914 | } |
| 3000 | 2915 | ||
| @@ -3195,7 +3110,7 @@ nvme_fc_init_ctrl(struct device *dev, struct nvmf_ctrl_options *opts, | |||
| 3195 | * transport errors (frame drop, LS failure) inherently must kill | 3110 | * transport errors (frame drop, LS failure) inherently must kill |
| 3196 | * the association. The transport is coded so that any command used | 3111 | * the association. The transport is coded so that any command used |
| 3197 | * to create the association (prior to a LIVE state transition | 3112 | * to create the association (prior to a LIVE state transition |
| 3198 | * while NEW or RECONNECTING) will fail if it completes in error or | 3113 | * while NEW or CONNECTING) will fail if it completes in error or |
| 3199 | * times out. | 3114 | * times out. |
| 3200 | * | 3115 | * |
| 3201 | * As such: as the connect request was mostly likely due to a | 3116 | * As such: as the connect request was mostly likely due to a |
diff --git a/drivers/nvme/host/nvme.h b/drivers/nvme/host/nvme.h index 8e4550fa08f8..0521e4707d1c 100644 --- a/drivers/nvme/host/nvme.h +++ b/drivers/nvme/host/nvme.h | |||
| @@ -123,7 +123,7 @@ enum nvme_ctrl_state { | |||
| 123 | NVME_CTRL_LIVE, | 123 | NVME_CTRL_LIVE, |
| 124 | NVME_CTRL_ADMIN_ONLY, /* Only admin queue live */ | 124 | NVME_CTRL_ADMIN_ONLY, /* Only admin queue live */ |
| 125 | NVME_CTRL_RESETTING, | 125 | NVME_CTRL_RESETTING, |
| 126 | NVME_CTRL_RECONNECTING, | 126 | NVME_CTRL_CONNECTING, |
| 127 | NVME_CTRL_DELETING, | 127 | NVME_CTRL_DELETING, |
| 128 | NVME_CTRL_DEAD, | 128 | NVME_CTRL_DEAD, |
| 129 | }; | 129 | }; |
| @@ -183,6 +183,7 @@ struct nvme_ctrl { | |||
| 183 | struct work_struct scan_work; | 183 | struct work_struct scan_work; |
| 184 | struct work_struct async_event_work; | 184 | struct work_struct async_event_work; |
| 185 | struct delayed_work ka_work; | 185 | struct delayed_work ka_work; |
| 186 | struct nvme_command ka_cmd; | ||
| 186 | struct work_struct fw_act_work; | 187 | struct work_struct fw_act_work; |
| 187 | 188 | ||
| 188 | /* Power saving configuration */ | 189 | /* Power saving configuration */ |
diff --git a/drivers/nvme/host/pci.c b/drivers/nvme/host/pci.c index 6fe7af00a1f4..73036d2fbbd5 100644 --- a/drivers/nvme/host/pci.c +++ b/drivers/nvme/host/pci.c | |||
| @@ -1141,7 +1141,7 @@ static bool nvme_should_reset(struct nvme_dev *dev, u32 csts) | |||
| 1141 | /* If there is a reset/reinit ongoing, we shouldn't reset again. */ | 1141 | /* If there is a reset/reinit ongoing, we shouldn't reset again. */ |
| 1142 | switch (dev->ctrl.state) { | 1142 | switch (dev->ctrl.state) { |
| 1143 | case NVME_CTRL_RESETTING: | 1143 | case NVME_CTRL_RESETTING: |
| 1144 | case NVME_CTRL_RECONNECTING: | 1144 | case NVME_CTRL_CONNECTING: |
| 1145 | return false; | 1145 | return false; |
| 1146 | default: | 1146 | default: |
| 1147 | break; | 1147 | break; |
| @@ -1215,13 +1215,17 @@ static enum blk_eh_timer_return nvme_timeout(struct request *req, bool reserved) | |||
| 1215 | * cancellation error. All outstanding requests are completed on | 1215 | * cancellation error. All outstanding requests are completed on |
| 1216 | * shutdown, so we return BLK_EH_HANDLED. | 1216 | * shutdown, so we return BLK_EH_HANDLED. |
| 1217 | */ | 1217 | */ |
| 1218 | if (dev->ctrl.state == NVME_CTRL_RESETTING) { | 1218 | switch (dev->ctrl.state) { |
| 1219 | case NVME_CTRL_CONNECTING: | ||
| 1220 | case NVME_CTRL_RESETTING: | ||
| 1219 | dev_warn(dev->ctrl.device, | 1221 | dev_warn(dev->ctrl.device, |
| 1220 | "I/O %d QID %d timeout, disable controller\n", | 1222 | "I/O %d QID %d timeout, disable controller\n", |
| 1221 | req->tag, nvmeq->qid); | 1223 | req->tag, nvmeq->qid); |
| 1222 | nvme_dev_disable(dev, false); | 1224 | nvme_dev_disable(dev, false); |
| 1223 | nvme_req(req)->flags |= NVME_REQ_CANCELLED; | 1225 | nvme_req(req)->flags |= NVME_REQ_CANCELLED; |
| 1224 | return BLK_EH_HANDLED; | 1226 | return BLK_EH_HANDLED; |
| 1227 | default: | ||
| 1228 | break; | ||
| 1225 | } | 1229 | } |
| 1226 | 1230 | ||
| 1227 | /* | 1231 | /* |
| @@ -1364,18 +1368,14 @@ static int nvme_cmb_qdepth(struct nvme_dev *dev, int nr_io_queues, | |||
| 1364 | static int nvme_alloc_sq_cmds(struct nvme_dev *dev, struct nvme_queue *nvmeq, | 1368 | static int nvme_alloc_sq_cmds(struct nvme_dev *dev, struct nvme_queue *nvmeq, |
| 1365 | int qid, int depth) | 1369 | int qid, int depth) |
| 1366 | { | 1370 | { |
| 1367 | if (qid && dev->cmb && use_cmb_sqes && (dev->cmbsz & NVME_CMBSZ_SQS)) { | 1371 | /* CMB SQEs will be mapped before creation */ |
| 1368 | unsigned offset = (qid - 1) * roundup(SQ_SIZE(depth), | 1372 | if (qid && dev->cmb && use_cmb_sqes && (dev->cmbsz & NVME_CMBSZ_SQS)) |
| 1369 | dev->ctrl.page_size); | 1373 | return 0; |
| 1370 | nvmeq->sq_dma_addr = dev->cmb_bus_addr + offset; | ||
| 1371 | nvmeq->sq_cmds_io = dev->cmb + offset; | ||
| 1372 | } else { | ||
| 1373 | nvmeq->sq_cmds = dma_alloc_coherent(dev->dev, SQ_SIZE(depth), | ||
| 1374 | &nvmeq->sq_dma_addr, GFP_KERNEL); | ||
| 1375 | if (!nvmeq->sq_cmds) | ||
| 1376 | return -ENOMEM; | ||
| 1377 | } | ||
| 1378 | 1374 | ||
| 1375 | nvmeq->sq_cmds = dma_alloc_coherent(dev->dev, SQ_SIZE(depth), | ||
| 1376 | &nvmeq->sq_dma_addr, GFP_KERNEL); | ||
| 1377 | if (!nvmeq->sq_cmds) | ||
| 1378 | return -ENOMEM; | ||
| 1379 | return 0; | 1379 | return 0; |
| 1380 | } | 1380 | } |
| 1381 | 1381 | ||
| @@ -1449,6 +1449,13 @@ static int nvme_create_queue(struct nvme_queue *nvmeq, int qid) | |||
| 1449 | struct nvme_dev *dev = nvmeq->dev; | 1449 | struct nvme_dev *dev = nvmeq->dev; |
| 1450 | int result; | 1450 | int result; |
| 1451 | 1451 | ||
| 1452 | if (dev->cmb && use_cmb_sqes && (dev->cmbsz & NVME_CMBSZ_SQS)) { | ||
| 1453 | unsigned offset = (qid - 1) * roundup(SQ_SIZE(nvmeq->q_depth), | ||
| 1454 | dev->ctrl.page_size); | ||
| 1455 | nvmeq->sq_dma_addr = dev->cmb_bus_addr + offset; | ||
| 1456 | nvmeq->sq_cmds_io = dev->cmb + offset; | ||
| 1457 | } | ||
| 1458 | |||
| 1452 | nvmeq->cq_vector = qid - 1; | 1459 | nvmeq->cq_vector = qid - 1; |
| 1453 | result = adapter_alloc_cq(dev, qid, nvmeq); | 1460 | result = adapter_alloc_cq(dev, qid, nvmeq); |
| 1454 | if (result < 0) | 1461 | if (result < 0) |
| @@ -2288,12 +2295,12 @@ static void nvme_reset_work(struct work_struct *work) | |||
| 2288 | nvme_dev_disable(dev, false); | 2295 | nvme_dev_disable(dev, false); |
| 2289 | 2296 | ||
| 2290 | /* | 2297 | /* |
| 2291 | * Introduce RECONNECTING state from nvme-fc/rdma transports to mark the | 2298 | * Introduce CONNECTING state from nvme-fc/rdma transports to mark the |
| 2292 | * initializing procedure here. | 2299 | * initializing procedure here. |
| 2293 | */ | 2300 | */ |
| 2294 | if (!nvme_change_ctrl_state(&dev->ctrl, NVME_CTRL_RECONNECTING)) { | 2301 | if (!nvme_change_ctrl_state(&dev->ctrl, NVME_CTRL_CONNECTING)) { |
| 2295 | dev_warn(dev->ctrl.device, | 2302 | dev_warn(dev->ctrl.device, |
| 2296 | "failed to mark controller RECONNECTING\n"); | 2303 | "failed to mark controller CONNECTING\n"); |
| 2297 | goto out; | 2304 | goto out; |
| 2298 | } | 2305 | } |
| 2299 | 2306 | ||
diff --git a/drivers/nvme/host/rdma.c b/drivers/nvme/host/rdma.c index 2bc059f7d73c..3a51ed50eff2 100644 --- a/drivers/nvme/host/rdma.c +++ b/drivers/nvme/host/rdma.c | |||
| @@ -887,7 +887,7 @@ free_ctrl: | |||
| 887 | static void nvme_rdma_reconnect_or_remove(struct nvme_rdma_ctrl *ctrl) | 887 | static void nvme_rdma_reconnect_or_remove(struct nvme_rdma_ctrl *ctrl) |
| 888 | { | 888 | { |
| 889 | /* If we are resetting/deleting then do nothing */ | 889 | /* If we are resetting/deleting then do nothing */ |
| 890 | if (ctrl->ctrl.state != NVME_CTRL_RECONNECTING) { | 890 | if (ctrl->ctrl.state != NVME_CTRL_CONNECTING) { |
| 891 | WARN_ON_ONCE(ctrl->ctrl.state == NVME_CTRL_NEW || | 891 | WARN_ON_ONCE(ctrl->ctrl.state == NVME_CTRL_NEW || |
| 892 | ctrl->ctrl.state == NVME_CTRL_LIVE); | 892 | ctrl->ctrl.state == NVME_CTRL_LIVE); |
| 893 | return; | 893 | return; |
| @@ -973,7 +973,7 @@ static void nvme_rdma_error_recovery_work(struct work_struct *work) | |||
| 973 | blk_mq_unquiesce_queue(ctrl->ctrl.admin_q); | 973 | blk_mq_unquiesce_queue(ctrl->ctrl.admin_q); |
| 974 | nvme_start_queues(&ctrl->ctrl); | 974 | nvme_start_queues(&ctrl->ctrl); |
| 975 | 975 | ||
| 976 | if (!nvme_change_ctrl_state(&ctrl->ctrl, NVME_CTRL_RECONNECTING)) { | 976 | if (!nvme_change_ctrl_state(&ctrl->ctrl, NVME_CTRL_CONNECTING)) { |
| 977 | /* state change failure should never happen */ | 977 | /* state change failure should never happen */ |
| 978 | WARN_ON_ONCE(1); | 978 | WARN_ON_ONCE(1); |
| 979 | return; | 979 | return; |
| @@ -1756,7 +1756,7 @@ static void nvme_rdma_reset_ctrl_work(struct work_struct *work) | |||
| 1756 | nvme_stop_ctrl(&ctrl->ctrl); | 1756 | nvme_stop_ctrl(&ctrl->ctrl); |
| 1757 | nvme_rdma_shutdown_ctrl(ctrl, false); | 1757 | nvme_rdma_shutdown_ctrl(ctrl, false); |
| 1758 | 1758 | ||
| 1759 | if (!nvme_change_ctrl_state(&ctrl->ctrl, NVME_CTRL_RECONNECTING)) { | 1759 | if (!nvme_change_ctrl_state(&ctrl->ctrl, NVME_CTRL_CONNECTING)) { |
| 1760 | /* state change failure should never happen */ | 1760 | /* state change failure should never happen */ |
| 1761 | WARN_ON_ONCE(1); | 1761 | WARN_ON_ONCE(1); |
| 1762 | return; | 1762 | return; |
| @@ -1784,11 +1784,8 @@ static void nvme_rdma_reset_ctrl_work(struct work_struct *work) | |||
| 1784 | return; | 1784 | return; |
| 1785 | 1785 | ||
| 1786 | out_fail: | 1786 | out_fail: |
| 1787 | dev_warn(ctrl->ctrl.device, "Removing after reset failure\n"); | 1787 | ++ctrl->ctrl.nr_reconnects; |
| 1788 | nvme_remove_namespaces(&ctrl->ctrl); | 1788 | nvme_rdma_reconnect_or_remove(ctrl); |
| 1789 | nvme_rdma_shutdown_ctrl(ctrl, true); | ||
| 1790 | nvme_uninit_ctrl(&ctrl->ctrl); | ||
| 1791 | nvme_put_ctrl(&ctrl->ctrl); | ||
| 1792 | } | 1789 | } |
| 1793 | 1790 | ||
| 1794 | static const struct nvme_ctrl_ops nvme_rdma_ctrl_ops = { | 1791 | static const struct nvme_ctrl_ops nvme_rdma_ctrl_ops = { |
| @@ -1942,6 +1939,9 @@ static struct nvme_ctrl *nvme_rdma_create_ctrl(struct device *dev, | |||
| 1942 | if (!ctrl->queues) | 1939 | if (!ctrl->queues) |
| 1943 | goto out_uninit_ctrl; | 1940 | goto out_uninit_ctrl; |
| 1944 | 1941 | ||
| 1942 | changed = nvme_change_ctrl_state(&ctrl->ctrl, NVME_CTRL_CONNECTING); | ||
| 1943 | WARN_ON_ONCE(!changed); | ||
| 1944 | |||
| 1945 | ret = nvme_rdma_configure_admin_queue(ctrl, true); | 1945 | ret = nvme_rdma_configure_admin_queue(ctrl, true); |
| 1946 | if (ret) | 1946 | if (ret) |
| 1947 | goto out_kfree_queues; | 1947 | goto out_kfree_queues; |
diff --git a/drivers/nvme/target/io-cmd.c b/drivers/nvme/target/io-cmd.c index 0a4372a016f2..28bbdff4a88b 100644 --- a/drivers/nvme/target/io-cmd.c +++ b/drivers/nvme/target/io-cmd.c | |||
| @@ -105,10 +105,13 @@ static void nvmet_execute_flush(struct nvmet_req *req) | |||
| 105 | static u16 nvmet_discard_range(struct nvmet_ns *ns, | 105 | static u16 nvmet_discard_range(struct nvmet_ns *ns, |
| 106 | struct nvme_dsm_range *range, struct bio **bio) | 106 | struct nvme_dsm_range *range, struct bio **bio) |
| 107 | { | 107 | { |
| 108 | if (__blkdev_issue_discard(ns->bdev, | 108 | int ret; |
| 109 | |||
| 110 | ret = __blkdev_issue_discard(ns->bdev, | ||
| 109 | le64_to_cpu(range->slba) << (ns->blksize_shift - 9), | 111 | le64_to_cpu(range->slba) << (ns->blksize_shift - 9), |
| 110 | le32_to_cpu(range->nlb) << (ns->blksize_shift - 9), | 112 | le32_to_cpu(range->nlb) << (ns->blksize_shift - 9), |
| 111 | GFP_KERNEL, 0, bio)) | 113 | GFP_KERNEL, 0, bio); |
| 114 | if (ret && ret != -EOPNOTSUPP) | ||
| 112 | return NVME_SC_INTERNAL | NVME_SC_DNR; | 115 | return NVME_SC_INTERNAL | NVME_SC_DNR; |
| 113 | return 0; | 116 | return 0; |
| 114 | } | 117 | } |
diff --git a/drivers/of/property.c b/drivers/of/property.c index 36ed84e26d9c..f46828e3b082 100644 --- a/drivers/of/property.c +++ b/drivers/of/property.c | |||
| @@ -977,11 +977,11 @@ static int of_fwnode_graph_parse_endpoint(const struct fwnode_handle *fwnode, | |||
| 977 | return 0; | 977 | return 0; |
| 978 | } | 978 | } |
| 979 | 979 | ||
| 980 | static void * | 980 | static const void * |
| 981 | of_fwnode_device_get_match_data(const struct fwnode_handle *fwnode, | 981 | of_fwnode_device_get_match_data(const struct fwnode_handle *fwnode, |
| 982 | const struct device *dev) | 982 | const struct device *dev) |
| 983 | { | 983 | { |
| 984 | return (void *)of_device_get_match_data(dev); | 984 | return of_device_get_match_data(dev); |
| 985 | } | 985 | } |
| 986 | 986 | ||
| 987 | const struct fwnode_operations of_fwnode_ops = { | 987 | const struct fwnode_operations of_fwnode_ops = { |
diff --git a/drivers/opp/cpu.c b/drivers/opp/cpu.c index 2d87bc1adf38..0c0910709435 100644 --- a/drivers/opp/cpu.c +++ b/drivers/opp/cpu.c | |||
| @@ -55,7 +55,7 @@ int dev_pm_opp_init_cpufreq_table(struct device *dev, | |||
| 55 | if (max_opps <= 0) | 55 | if (max_opps <= 0) |
| 56 | return max_opps ? max_opps : -ENODATA; | 56 | return max_opps ? max_opps : -ENODATA; |
| 57 | 57 | ||
| 58 | freq_table = kcalloc((max_opps + 1), sizeof(*freq_table), GFP_ATOMIC); | 58 | freq_table = kcalloc((max_opps + 1), sizeof(*freq_table), GFP_KERNEL); |
| 59 | if (!freq_table) | 59 | if (!freq_table) |
| 60 | return -ENOMEM; | 60 | return -ENOMEM; |
| 61 | 61 | ||
diff --git a/drivers/pci/quirks.c b/drivers/pci/quirks.c index fc734014206f..8b14bd326d4a 100644 --- a/drivers/pci/quirks.c +++ b/drivers/pci/quirks.c | |||
| @@ -3419,22 +3419,29 @@ DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_INTEL, PCI_DEVICE_ID_INTEL_PORT_RIDGE, | |||
| 3419 | 3419 | ||
| 3420 | static void quirk_chelsio_extend_vpd(struct pci_dev *dev) | 3420 | static void quirk_chelsio_extend_vpd(struct pci_dev *dev) |
| 3421 | { | 3421 | { |
| 3422 | pci_set_vpd_size(dev, 8192); | 3422 | int chip = (dev->device & 0xf000) >> 12; |
| 3423 | } | 3423 | int func = (dev->device & 0x0f00) >> 8; |
| 3424 | 3424 | int prod = (dev->device & 0x00ff) >> 0; | |
| 3425 | DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_CHELSIO, 0x20, quirk_chelsio_extend_vpd); | 3425 | |
| 3426 | DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_CHELSIO, 0x21, quirk_chelsio_extend_vpd); | 3426 | /* |
| 3427 | DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_CHELSIO, 0x22, quirk_chelsio_extend_vpd); | 3427 | * If this is a T3-based adapter, there's a 1KB VPD area at offset |
| 3428 | DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_CHELSIO, 0x23, quirk_chelsio_extend_vpd); | 3428 | * 0xc00 which contains the preferred VPD values. If this is a T4 or |
| 3429 | DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_CHELSIO, 0x24, quirk_chelsio_extend_vpd); | 3429 | * later based adapter, the special VPD is at offset 0x400 for the |
| 3430 | DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_CHELSIO, 0x25, quirk_chelsio_extend_vpd); | 3430 | * Physical Functions (the SR-IOV Virtual Functions have no VPD |
| 3431 | DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_CHELSIO, 0x26, quirk_chelsio_extend_vpd); | 3431 | * Capabilities). The PCI VPD Access core routines will normally |
| 3432 | DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_CHELSIO, 0x30, quirk_chelsio_extend_vpd); | 3432 | * compute the size of the VPD by parsing the VPD Data Structure at |
| 3433 | DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_CHELSIO, 0x31, quirk_chelsio_extend_vpd); | 3433 | * offset 0x000. This will result in silent failures when attempting |
| 3434 | DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_CHELSIO, 0x32, quirk_chelsio_extend_vpd); | 3434 | * to accesses these other VPD areas which are beyond those computed |
| 3435 | DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_CHELSIO, 0x35, quirk_chelsio_extend_vpd); | 3435 | * limits. |
| 3436 | DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_CHELSIO, 0x36, quirk_chelsio_extend_vpd); | 3436 | */ |
| 3437 | DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_CHELSIO, 0x37, quirk_chelsio_extend_vpd); | 3437 | if (chip == 0x0 && prod >= 0x20) |
| 3438 | pci_set_vpd_size(dev, 8192); | ||
| 3439 | else if (chip >= 0x4 && func < 0x8) | ||
| 3440 | pci_set_vpd_size(dev, 2048); | ||
| 3441 | } | ||
| 3442 | |||
| 3443 | DECLARE_PCI_FIXUP_FINAL(PCI_VENDOR_ID_CHELSIO, PCI_ANY_ID, | ||
| 3444 | quirk_chelsio_extend_vpd); | ||
| 3438 | 3445 | ||
| 3439 | #ifdef CONFIG_ACPI | 3446 | #ifdef CONFIG_ACPI |
| 3440 | /* | 3447 | /* |
diff --git a/drivers/perf/arm_pmu.c b/drivers/perf/arm_pmu.c index 7bc5eee96b31..0c2ed11c0603 100644 --- a/drivers/perf/arm_pmu.c +++ b/drivers/perf/arm_pmu.c | |||
| @@ -17,7 +17,6 @@ | |||
| 17 | #include <linux/export.h> | 17 | #include <linux/export.h> |
| 18 | #include <linux/kernel.h> | 18 | #include <linux/kernel.h> |
| 19 | #include <linux/perf/arm_pmu.h> | 19 | #include <linux/perf/arm_pmu.h> |
| 20 | #include <linux/platform_device.h> | ||
| 21 | #include <linux/slab.h> | 20 | #include <linux/slab.h> |
| 22 | #include <linux/sched/clock.h> | 21 | #include <linux/sched/clock.h> |
| 23 | #include <linux/spinlock.h> | 22 | #include <linux/spinlock.h> |
| @@ -26,6 +25,9 @@ | |||
| 26 | 25 | ||
| 27 | #include <asm/irq_regs.h> | 26 | #include <asm/irq_regs.h> |
| 28 | 27 | ||
| 28 | static DEFINE_PER_CPU(struct arm_pmu *, cpu_armpmu); | ||
| 29 | static DEFINE_PER_CPU(int, cpu_irq); | ||
| 30 | |||
| 29 | static int | 31 | static int |
| 30 | armpmu_map_cache_event(const unsigned (*cache_map) | 32 | armpmu_map_cache_event(const unsigned (*cache_map) |
| 31 | [PERF_COUNT_HW_CACHE_MAX] | 33 | [PERF_COUNT_HW_CACHE_MAX] |
| @@ -320,17 +322,9 @@ validate_group(struct perf_event *event) | |||
| 320 | return 0; | 322 | return 0; |
| 321 | } | 323 | } |
| 322 | 324 | ||
| 323 | static struct arm_pmu_platdata *armpmu_get_platdata(struct arm_pmu *armpmu) | ||
| 324 | { | ||
| 325 | struct platform_device *pdev = armpmu->plat_device; | ||
| 326 | |||
| 327 | return pdev ? dev_get_platdata(&pdev->dev) : NULL; | ||
| 328 | } | ||
| 329 | |||
| 330 | static irqreturn_t armpmu_dispatch_irq(int irq, void *dev) | 325 | static irqreturn_t armpmu_dispatch_irq(int irq, void *dev) |
| 331 | { | 326 | { |
| 332 | struct arm_pmu *armpmu; | 327 | struct arm_pmu *armpmu; |
| 333 | struct arm_pmu_platdata *plat; | ||
| 334 | int ret; | 328 | int ret; |
| 335 | u64 start_clock, finish_clock; | 329 | u64 start_clock, finish_clock; |
| 336 | 330 | ||
| @@ -341,14 +335,11 @@ static irqreturn_t armpmu_dispatch_irq(int irq, void *dev) | |||
| 341 | * dereference. | 335 | * dereference. |
| 342 | */ | 336 | */ |
| 343 | armpmu = *(void **)dev; | 337 | armpmu = *(void **)dev; |
| 344 | 338 | if (WARN_ON_ONCE(!armpmu)) | |
| 345 | plat = armpmu_get_platdata(armpmu); | 339 | return IRQ_NONE; |
| 346 | 340 | ||
| 347 | start_clock = sched_clock(); | 341 | start_clock = sched_clock(); |
| 348 | if (plat && plat->handle_irq) | 342 | ret = armpmu->handle_irq(irq, armpmu); |
| 349 | ret = plat->handle_irq(irq, armpmu, armpmu->handle_irq); | ||
| 350 | else | ||
| 351 | ret = armpmu->handle_irq(irq, armpmu); | ||
| 352 | finish_clock = sched_clock(); | 343 | finish_clock = sched_clock(); |
| 353 | 344 | ||
| 354 | perf_sample_event_took(finish_clock - start_clock); | 345 | perf_sample_event_took(finish_clock - start_clock); |
| @@ -531,54 +522,41 @@ int perf_num_counters(void) | |||
| 531 | } | 522 | } |
| 532 | EXPORT_SYMBOL_GPL(perf_num_counters); | 523 | EXPORT_SYMBOL_GPL(perf_num_counters); |
| 533 | 524 | ||
| 534 | void armpmu_free_irq(struct arm_pmu *armpmu, int cpu) | 525 | static int armpmu_count_irq_users(const int irq) |
| 535 | { | 526 | { |
| 536 | struct pmu_hw_events __percpu *hw_events = armpmu->hw_events; | 527 | int cpu, count = 0; |
| 537 | int irq = per_cpu(hw_events->irq, cpu); | ||
| 538 | 528 | ||
| 539 | if (!cpumask_test_and_clear_cpu(cpu, &armpmu->active_irqs)) | 529 | for_each_possible_cpu(cpu) { |
| 540 | return; | 530 | if (per_cpu(cpu_irq, cpu) == irq) |
| 541 | 531 | count++; | |
| 542 | if (irq_is_percpu_devid(irq)) { | ||
| 543 | free_percpu_irq(irq, &hw_events->percpu_pmu); | ||
| 544 | cpumask_clear(&armpmu->active_irqs); | ||
| 545 | return; | ||
| 546 | } | 532 | } |
| 547 | 533 | ||
| 548 | free_irq(irq, per_cpu_ptr(&hw_events->percpu_pmu, cpu)); | 534 | return count; |
| 549 | } | 535 | } |
| 550 | 536 | ||
| 551 | void armpmu_free_irqs(struct arm_pmu *armpmu) | 537 | void armpmu_free_irq(int irq, int cpu) |
| 552 | { | 538 | { |
| 553 | int cpu; | 539 | if (per_cpu(cpu_irq, cpu) == 0) |
| 540 | return; | ||
| 541 | if (WARN_ON(irq != per_cpu(cpu_irq, cpu))) | ||
| 542 | return; | ||
| 543 | |||
| 544 | if (!irq_is_percpu_devid(irq)) | ||
| 545 | free_irq(irq, per_cpu_ptr(&cpu_armpmu, cpu)); | ||
| 546 | else if (armpmu_count_irq_users(irq) == 1) | ||
| 547 | free_percpu_irq(irq, &cpu_armpmu); | ||
| 554 | 548 | ||
| 555 | for_each_cpu(cpu, &armpmu->supported_cpus) | 549 | per_cpu(cpu_irq, cpu) = 0; |
| 556 | armpmu_free_irq(armpmu, cpu); | ||
| 557 | } | 550 | } |
| 558 | 551 | ||
| 559 | int armpmu_request_irq(struct arm_pmu *armpmu, int cpu) | 552 | int armpmu_request_irq(int irq, int cpu) |
| 560 | { | 553 | { |
| 561 | int err = 0; | 554 | int err = 0; |
| 562 | struct pmu_hw_events __percpu *hw_events = armpmu->hw_events; | ||
| 563 | const irq_handler_t handler = armpmu_dispatch_irq; | 555 | const irq_handler_t handler = armpmu_dispatch_irq; |
| 564 | int irq = per_cpu(hw_events->irq, cpu); | ||
| 565 | if (!irq) | 556 | if (!irq) |
| 566 | return 0; | 557 | return 0; |
| 567 | 558 | ||
| 568 | if (irq_is_percpu_devid(irq) && cpumask_empty(&armpmu->active_irqs)) { | 559 | if (!irq_is_percpu_devid(irq)) { |
| 569 | err = request_percpu_irq(irq, handler, "arm-pmu", | ||
| 570 | &hw_events->percpu_pmu); | ||
| 571 | } else if (irq_is_percpu_devid(irq)) { | ||
| 572 | int other_cpu = cpumask_first(&armpmu->active_irqs); | ||
| 573 | int other_irq = per_cpu(hw_events->irq, other_cpu); | ||
| 574 | |||
| 575 | if (irq != other_irq) { | ||
| 576 | pr_warn("mismatched PPIs detected.\n"); | ||
| 577 | err = -EINVAL; | ||
| 578 | goto err_out; | ||
| 579 | } | ||
| 580 | } else { | ||
| 581 | struct arm_pmu_platdata *platdata = armpmu_get_platdata(armpmu); | ||
| 582 | unsigned long irq_flags; | 560 | unsigned long irq_flags; |
| 583 | 561 | ||
| 584 | err = irq_force_affinity(irq, cpumask_of(cpu)); | 562 | err = irq_force_affinity(irq, cpumask_of(cpu)); |
| @@ -589,22 +567,22 @@ int armpmu_request_irq(struct arm_pmu *armpmu, int cpu) | |||
| 589 | goto err_out; | 567 | goto err_out; |
| 590 | } | 568 | } |
| 591 | 569 | ||
| 592 | if (platdata && platdata->irq_flags) { | 570 | irq_flags = IRQF_PERCPU | |
| 593 | irq_flags = platdata->irq_flags; | 571 | IRQF_NOBALANCING | |
| 594 | } else { | 572 | IRQF_NO_THREAD; |
| 595 | irq_flags = IRQF_PERCPU | | ||
| 596 | IRQF_NOBALANCING | | ||
| 597 | IRQF_NO_THREAD; | ||
| 598 | } | ||
| 599 | 573 | ||
| 574 | irq_set_status_flags(irq, IRQ_NOAUTOEN); | ||
| 600 | err = request_irq(irq, handler, irq_flags, "arm-pmu", | 575 | err = request_irq(irq, handler, irq_flags, "arm-pmu", |
| 601 | per_cpu_ptr(&hw_events->percpu_pmu, cpu)); | 576 | per_cpu_ptr(&cpu_armpmu, cpu)); |
| 577 | } else if (armpmu_count_irq_users(irq) == 0) { | ||
| 578 | err = request_percpu_irq(irq, handler, "arm-pmu", | ||
| 579 | &cpu_armpmu); | ||
| 602 | } | 580 | } |
| 603 | 581 | ||
| 604 | if (err) | 582 | if (err) |
| 605 | goto err_out; | 583 | goto err_out; |
| 606 | 584 | ||
| 607 | cpumask_set_cpu(cpu, &armpmu->active_irqs); | 585 | per_cpu(cpu_irq, cpu) = irq; |
| 608 | return 0; | 586 | return 0; |
| 609 | 587 | ||
| 610 | err_out: | 588 | err_out: |
| @@ -612,19 +590,6 @@ err_out: | |||
| 612 | return err; | 590 | return err; |
| 613 | } | 591 | } |
| 614 | 592 | ||
| 615 | int armpmu_request_irqs(struct arm_pmu *armpmu) | ||
| 616 | { | ||
| 617 | int cpu, err; | ||
| 618 | |||
| 619 | for_each_cpu(cpu, &armpmu->supported_cpus) { | ||
| 620 | err = armpmu_request_irq(armpmu, cpu); | ||
| 621 | if (err) | ||
| 622 | break; | ||
| 623 | } | ||
| 624 | |||
| 625 | return err; | ||
| 626 | } | ||
| 627 | |||
| 628 | static int armpmu_get_cpu_irq(struct arm_pmu *pmu, int cpu) | 593 | static int armpmu_get_cpu_irq(struct arm_pmu *pmu, int cpu) |
| 629 | { | 594 | { |
| 630 | struct pmu_hw_events __percpu *hw_events = pmu->hw_events; | 595 | struct pmu_hw_events __percpu *hw_events = pmu->hw_events; |
| @@ -647,12 +612,14 @@ static int arm_perf_starting_cpu(unsigned int cpu, struct hlist_node *node) | |||
| 647 | if (pmu->reset) | 612 | if (pmu->reset) |
| 648 | pmu->reset(pmu); | 613 | pmu->reset(pmu); |
| 649 | 614 | ||
| 615 | per_cpu(cpu_armpmu, cpu) = pmu; | ||
| 616 | |||
| 650 | irq = armpmu_get_cpu_irq(pmu, cpu); | 617 | irq = armpmu_get_cpu_irq(pmu, cpu); |
| 651 | if (irq) { | 618 | if (irq) { |
| 652 | if (irq_is_percpu_devid(irq)) { | 619 | if (irq_is_percpu_devid(irq)) |
| 653 | enable_percpu_irq(irq, IRQ_TYPE_NONE); | 620 | enable_percpu_irq(irq, IRQ_TYPE_NONE); |
| 654 | return 0; | 621 | else |
| 655 | } | 622 | enable_irq(irq); |
| 656 | } | 623 | } |
| 657 | 624 | ||
| 658 | return 0; | 625 | return 0; |
| @@ -667,8 +634,14 @@ static int arm_perf_teardown_cpu(unsigned int cpu, struct hlist_node *node) | |||
| 667 | return 0; | 634 | return 0; |
| 668 | 635 | ||
| 669 | irq = armpmu_get_cpu_irq(pmu, cpu); | 636 | irq = armpmu_get_cpu_irq(pmu, cpu); |
| 670 | if (irq && irq_is_percpu_devid(irq)) | 637 | if (irq) { |
| 671 | disable_percpu_irq(irq); | 638 | if (irq_is_percpu_devid(irq)) |
| 639 | disable_percpu_irq(irq); | ||
| 640 | else | ||
| 641 | disable_irq(irq); | ||
| 642 | } | ||
| 643 | |||
| 644 | per_cpu(cpu_armpmu, cpu) = NULL; | ||
| 672 | 645 | ||
| 673 | return 0; | 646 | return 0; |
| 674 | } | 647 | } |
| @@ -800,18 +773,18 @@ static void cpu_pmu_destroy(struct arm_pmu *cpu_pmu) | |||
| 800 | &cpu_pmu->node); | 773 | &cpu_pmu->node); |
| 801 | } | 774 | } |
| 802 | 775 | ||
| 803 | struct arm_pmu *armpmu_alloc(void) | 776 | static struct arm_pmu *__armpmu_alloc(gfp_t flags) |
| 804 | { | 777 | { |
| 805 | struct arm_pmu *pmu; | 778 | struct arm_pmu *pmu; |
| 806 | int cpu; | 779 | int cpu; |
| 807 | 780 | ||
| 808 | pmu = kzalloc(sizeof(*pmu), GFP_KERNEL); | 781 | pmu = kzalloc(sizeof(*pmu), flags); |
| 809 | if (!pmu) { | 782 | if (!pmu) { |
| 810 | pr_info("failed to allocate PMU device!\n"); | 783 | pr_info("failed to allocate PMU device!\n"); |
| 811 | goto out; | 784 | goto out; |
| 812 | } | 785 | } |
| 813 | 786 | ||
| 814 | pmu->hw_events = alloc_percpu(struct pmu_hw_events); | 787 | pmu->hw_events = alloc_percpu_gfp(struct pmu_hw_events, flags); |
| 815 | if (!pmu->hw_events) { | 788 | if (!pmu->hw_events) { |
| 816 | pr_info("failed to allocate per-cpu PMU data.\n"); | 789 | pr_info("failed to allocate per-cpu PMU data.\n"); |
| 817 | goto out_free_pmu; | 790 | goto out_free_pmu; |
| @@ -857,6 +830,17 @@ out: | |||
| 857 | return NULL; | 830 | return NULL; |
| 858 | } | 831 | } |
| 859 | 832 | ||
| 833 | struct arm_pmu *armpmu_alloc(void) | ||
| 834 | { | ||
| 835 | return __armpmu_alloc(GFP_KERNEL); | ||
| 836 | } | ||
| 837 | |||
| 838 | struct arm_pmu *armpmu_alloc_atomic(void) | ||
| 839 | { | ||
| 840 | return __armpmu_alloc(GFP_ATOMIC); | ||
| 841 | } | ||
| 842 | |||
| 843 | |||
| 860 | void armpmu_free(struct arm_pmu *pmu) | 844 | void armpmu_free(struct arm_pmu *pmu) |
| 861 | { | 845 | { |
| 862 | free_percpu(pmu->hw_events); | 846 | free_percpu(pmu->hw_events); |
diff --git a/drivers/perf/arm_pmu_acpi.c b/drivers/perf/arm_pmu_acpi.c index 705f1a390e31..0f197516d708 100644 --- a/drivers/perf/arm_pmu_acpi.c +++ b/drivers/perf/arm_pmu_acpi.c | |||
| @@ -11,6 +11,8 @@ | |||
| 11 | #include <linux/acpi.h> | 11 | #include <linux/acpi.h> |
| 12 | #include <linux/cpumask.h> | 12 | #include <linux/cpumask.h> |
| 13 | #include <linux/init.h> | 13 | #include <linux/init.h> |
| 14 | #include <linux/irq.h> | ||
| 15 | #include <linux/irqdesc.h> | ||
| 14 | #include <linux/percpu.h> | 16 | #include <linux/percpu.h> |
| 15 | #include <linux/perf/arm_pmu.h> | 17 | #include <linux/perf/arm_pmu.h> |
| 16 | 18 | ||
| @@ -87,7 +89,13 @@ static int arm_pmu_acpi_parse_irqs(void) | |||
| 87 | pr_warn("No ACPI PMU IRQ for CPU%d\n", cpu); | 89 | pr_warn("No ACPI PMU IRQ for CPU%d\n", cpu); |
| 88 | } | 90 | } |
| 89 | 91 | ||
| 92 | /* | ||
| 93 | * Log and request the IRQ so the core arm_pmu code can manage | ||
| 94 | * it. We'll have to sanity-check IRQs later when we associate | ||
| 95 | * them with their PMUs. | ||
| 96 | */ | ||
| 90 | per_cpu(pmu_irqs, cpu) = irq; | 97 | per_cpu(pmu_irqs, cpu) = irq; |
| 98 | armpmu_request_irq(irq, cpu); | ||
| 91 | } | 99 | } |
| 92 | 100 | ||
| 93 | return 0; | 101 | return 0; |
| @@ -127,7 +135,7 @@ static struct arm_pmu *arm_pmu_acpi_find_alloc_pmu(void) | |||
| 127 | return pmu; | 135 | return pmu; |
| 128 | } | 136 | } |
| 129 | 137 | ||
| 130 | pmu = armpmu_alloc(); | 138 | pmu = armpmu_alloc_atomic(); |
| 131 | if (!pmu) { | 139 | if (!pmu) { |
| 132 | pr_warn("Unable to allocate PMU for CPU%d\n", | 140 | pr_warn("Unable to allocate PMU for CPU%d\n", |
| 133 | smp_processor_id()); | 141 | smp_processor_id()); |
| @@ -140,6 +148,35 @@ static struct arm_pmu *arm_pmu_acpi_find_alloc_pmu(void) | |||
| 140 | } | 148 | } |
| 141 | 149 | ||
| 142 | /* | 150 | /* |
| 151 | * Check whether the new IRQ is compatible with those already associated with | ||
| 152 | * the PMU (e.g. we don't have mismatched PPIs). | ||
| 153 | */ | ||
| 154 | static bool pmu_irq_matches(struct arm_pmu *pmu, int irq) | ||
| 155 | { | ||
| 156 | struct pmu_hw_events __percpu *hw_events = pmu->hw_events; | ||
| 157 | int cpu; | ||
| 158 | |||
| 159 | if (!irq) | ||
| 160 | return true; | ||
| 161 | |||
| 162 | for_each_cpu(cpu, &pmu->supported_cpus) { | ||
| 163 | int other_irq = per_cpu(hw_events->irq, cpu); | ||
| 164 | if (!other_irq) | ||
| 165 | continue; | ||
| 166 | |||
| 167 | if (irq == other_irq) | ||
| 168 | continue; | ||
| 169 | if (!irq_is_percpu_devid(irq) && !irq_is_percpu_devid(other_irq)) | ||
| 170 | continue; | ||
| 171 | |||
| 172 | pr_warn("mismatched PPIs detected\n"); | ||
| 173 | return false; | ||
| 174 | } | ||
| 175 | |||
| 176 | return true; | ||
| 177 | } | ||
| 178 | |||
| 179 | /* | ||
| 143 | * This must run before the common arm_pmu hotplug logic, so that we can | 180 | * This must run before the common arm_pmu hotplug logic, so that we can |
| 144 | * associate a CPU and its interrupt before the common code tries to manage the | 181 | * associate a CPU and its interrupt before the common code tries to manage the |
| 145 | * affinity and so on. | 182 | * affinity and so on. |
| @@ -164,19 +201,14 @@ static int arm_pmu_acpi_cpu_starting(unsigned int cpu) | |||
| 164 | if (!pmu) | 201 | if (!pmu) |
| 165 | return -ENOMEM; | 202 | return -ENOMEM; |
| 166 | 203 | ||
| 167 | cpumask_set_cpu(cpu, &pmu->supported_cpus); | ||
| 168 | |||
| 169 | per_cpu(probed_pmus, cpu) = pmu; | 204 | per_cpu(probed_pmus, cpu) = pmu; |
| 170 | 205 | ||
| 171 | /* | 206 | if (pmu_irq_matches(pmu, irq)) { |
| 172 | * Log and request the IRQ so the core arm_pmu code can manage it. In | 207 | hw_events = pmu->hw_events; |
| 173 | * some situations (e.g. mismatched PPIs), we may fail to request the | 208 | per_cpu(hw_events->irq, cpu) = irq; |
| 174 | * IRQ. However, it may be too late for us to do anything about it. | 209 | } |
| 175 | * The common ARM PMU code will log a warning in this case. | 210 | |
| 176 | */ | 211 | cpumask_set_cpu(cpu, &pmu->supported_cpus); |
| 177 | hw_events = pmu->hw_events; | ||
| 178 | per_cpu(hw_events->irq, cpu) = irq; | ||
| 179 | armpmu_request_irq(pmu, cpu); | ||
| 180 | 212 | ||
| 181 | /* | 213 | /* |
| 182 | * Ideally, we'd probe the PMU here when we find the first matching | 214 | * Ideally, we'd probe the PMU here when we find the first matching |
| @@ -247,11 +279,6 @@ static int arm_pmu_acpi_init(void) | |||
| 247 | if (acpi_disabled) | 279 | if (acpi_disabled) |
| 248 | return 0; | 280 | return 0; |
| 249 | 281 | ||
| 250 | /* | ||
| 251 | * We can't request IRQs yet, since we don't know the cookie value | ||
| 252 | * until we know which CPUs share the same logical PMU. We'll handle | ||
| 253 | * that in arm_pmu_acpi_cpu_starting(). | ||
| 254 | */ | ||
| 255 | ret = arm_pmu_acpi_parse_irqs(); | 282 | ret = arm_pmu_acpi_parse_irqs(); |
| 256 | if (ret) | 283 | if (ret) |
| 257 | return ret; | 284 | return ret; |
diff --git a/drivers/perf/arm_pmu_platform.c b/drivers/perf/arm_pmu_platform.c index 46501cc79fd7..7729eda5909d 100644 --- a/drivers/perf/arm_pmu_platform.c +++ b/drivers/perf/arm_pmu_platform.c | |||
| @@ -127,13 +127,6 @@ static int pmu_parse_irqs(struct arm_pmu *pmu) | |||
| 127 | pdev->dev.of_node); | 127 | pdev->dev.of_node); |
| 128 | } | 128 | } |
| 129 | 129 | ||
| 130 | /* | ||
| 131 | * Some platforms have all PMU IRQs OR'd into a single IRQ, with a | ||
| 132 | * special platdata function that attempts to demux them. | ||
| 133 | */ | ||
| 134 | if (dev_get_platdata(&pdev->dev)) | ||
| 135 | cpumask_setall(&pmu->supported_cpus); | ||
| 136 | |||
| 137 | for (i = 0; i < num_irqs; i++) { | 130 | for (i = 0; i < num_irqs; i++) { |
| 138 | int cpu, irq; | 131 | int cpu, irq; |
| 139 | 132 | ||
| @@ -164,6 +157,36 @@ static int pmu_parse_irqs(struct arm_pmu *pmu) | |||
| 164 | return 0; | 157 | return 0; |
| 165 | } | 158 | } |
| 166 | 159 | ||
| 160 | static int armpmu_request_irqs(struct arm_pmu *armpmu) | ||
| 161 | { | ||
| 162 | struct pmu_hw_events __percpu *hw_events = armpmu->hw_events; | ||
| 163 | int cpu, err; | ||
| 164 | |||
| 165 | for_each_cpu(cpu, &armpmu->supported_cpus) { | ||
| 166 | int irq = per_cpu(hw_events->irq, cpu); | ||
| 167 | if (!irq) | ||
| 168 | continue; | ||
| 169 | |||
| 170 | err = armpmu_request_irq(irq, cpu); | ||
| 171 | if (err) | ||
| 172 | break; | ||
| 173 | } | ||
| 174 | |||
| 175 | return err; | ||
| 176 | } | ||
| 177 | |||
| 178 | static void armpmu_free_irqs(struct arm_pmu *armpmu) | ||
| 179 | { | ||
| 180 | int cpu; | ||
| 181 | struct pmu_hw_events __percpu *hw_events = armpmu->hw_events; | ||
| 182 | |||
| 183 | for_each_cpu(cpu, &armpmu->supported_cpus) { | ||
| 184 | int irq = per_cpu(hw_events->irq, cpu); | ||
| 185 | |||
| 186 | armpmu_free_irq(irq, cpu); | ||
| 187 | } | ||
| 188 | } | ||
| 189 | |||
| 167 | int arm_pmu_device_probe(struct platform_device *pdev, | 190 | int arm_pmu_device_probe(struct platform_device *pdev, |
| 168 | const struct of_device_id *of_table, | 191 | const struct of_device_id *of_table, |
| 169 | const struct pmu_probe_info *probe_table) | 192 | const struct pmu_probe_info *probe_table) |
diff --git a/drivers/platform/x86/dell-laptop.c b/drivers/platform/x86/dell-laptop.c index 2a68f59d2228..c52c6723374b 100644 --- a/drivers/platform/x86/dell-laptop.c +++ b/drivers/platform/x86/dell-laptop.c | |||
| @@ -127,24 +127,6 @@ static const struct dmi_system_id dell_device_table[] __initconst = { | |||
| 127 | }, | 127 | }, |
| 128 | }, | 128 | }, |
| 129 | { | 129 | { |
| 130 | .matches = { | ||
| 131 | DMI_MATCH(DMI_SYS_VENDOR, "Dell Inc."), | ||
| 132 | DMI_MATCH(DMI_CHASSIS_TYPE, "30"), /*Tablet*/ | ||
| 133 | }, | ||
| 134 | }, | ||
| 135 | { | ||
| 136 | .matches = { | ||
| 137 | DMI_MATCH(DMI_SYS_VENDOR, "Dell Inc."), | ||
| 138 | DMI_MATCH(DMI_CHASSIS_TYPE, "31"), /*Convertible*/ | ||
| 139 | }, | ||
| 140 | }, | ||
| 141 | { | ||
| 142 | .matches = { | ||
| 143 | DMI_MATCH(DMI_SYS_VENDOR, "Dell Inc."), | ||
| 144 | DMI_MATCH(DMI_CHASSIS_TYPE, "32"), /*Detachable*/ | ||
| 145 | }, | ||
| 146 | }, | ||
| 147 | { | ||
| 148 | .ident = "Dell Computer Corporation", | 130 | .ident = "Dell Computer Corporation", |
| 149 | .matches = { | 131 | .matches = { |
| 150 | DMI_MATCH(DMI_SYS_VENDOR, "Dell Computer Corporation"), | 132 | DMI_MATCH(DMI_SYS_VENDOR, "Dell Computer Corporation"), |
| @@ -1279,7 +1261,7 @@ static int kbd_get_state(struct kbd_state *state) | |||
| 1279 | struct calling_interface_buffer buffer; | 1261 | struct calling_interface_buffer buffer; |
| 1280 | int ret; | 1262 | int ret; |
| 1281 | 1263 | ||
| 1282 | dell_fill_request(&buffer, 0, 0, 0, 0); | 1264 | dell_fill_request(&buffer, 0x1, 0, 0, 0); |
| 1283 | ret = dell_send_request(&buffer, | 1265 | ret = dell_send_request(&buffer, |
| 1284 | CLASS_KBD_BACKLIGHT, SELECT_KBD_BACKLIGHT); | 1266 | CLASS_KBD_BACKLIGHT, SELECT_KBD_BACKLIGHT); |
| 1285 | if (ret) | 1267 | if (ret) |
diff --git a/drivers/platform/x86/ideapad-laptop.c b/drivers/platform/x86/ideapad-laptop.c index 5b6f18b18801..535199c9e6bc 100644 --- a/drivers/platform/x86/ideapad-laptop.c +++ b/drivers/platform/x86/ideapad-laptop.c | |||
| @@ -113,7 +113,7 @@ MODULE_PARM_DESC(no_bt_rfkill, "No rfkill for bluetooth."); | |||
| 113 | /* | 113 | /* |
| 114 | * ACPI Helpers | 114 | * ACPI Helpers |
| 115 | */ | 115 | */ |
| 116 | #define IDEAPAD_EC_TIMEOUT (100) /* in ms */ | 116 | #define IDEAPAD_EC_TIMEOUT (200) /* in ms */ |
| 117 | 117 | ||
| 118 | static int read_method_int(acpi_handle handle, const char *method, int *val) | 118 | static int read_method_int(acpi_handle handle, const char *method, int *val) |
| 119 | { | 119 | { |
diff --git a/drivers/platform/x86/wmi.c b/drivers/platform/x86/wmi.c index daa68acbc900..c0c8945603cb 100644 --- a/drivers/platform/x86/wmi.c +++ b/drivers/platform/x86/wmi.c | |||
| @@ -933,7 +933,7 @@ static int wmi_dev_probe(struct device *dev) | |||
| 933 | goto probe_failure; | 933 | goto probe_failure; |
| 934 | } | 934 | } |
| 935 | 935 | ||
| 936 | buf = kmalloc(strlen(wdriver->driver.name) + 4, GFP_KERNEL); | 936 | buf = kmalloc(strlen(wdriver->driver.name) + 5, GFP_KERNEL); |
| 937 | if (!buf) { | 937 | if (!buf) { |
| 938 | ret = -ENOMEM; | 938 | ret = -ENOMEM; |
| 939 | goto probe_string_failure; | 939 | goto probe_string_failure; |
diff --git a/drivers/s390/virtio/virtio_ccw.c b/drivers/s390/virtio/virtio_ccw.c index ba2e0856d22c..8f5c1d7f751a 100644 --- a/drivers/s390/virtio/virtio_ccw.c +++ b/drivers/s390/virtio/virtio_ccw.c | |||
| @@ -1297,6 +1297,9 @@ static int virtio_ccw_cio_notify(struct ccw_device *cdev, int event) | |||
| 1297 | vcdev->device_lost = true; | 1297 | vcdev->device_lost = true; |
| 1298 | rc = NOTIFY_DONE; | 1298 | rc = NOTIFY_DONE; |
| 1299 | break; | 1299 | break; |
| 1300 | case CIO_OPER: | ||
| 1301 | rc = NOTIFY_OK; | ||
| 1302 | break; | ||
| 1300 | default: | 1303 | default: |
| 1301 | rc = NOTIFY_DONE; | 1304 | rc = NOTIFY_DONE; |
| 1302 | break; | 1305 | break; |
| @@ -1309,6 +1312,27 @@ static struct ccw_device_id virtio_ids[] = { | |||
| 1309 | {}, | 1312 | {}, |
| 1310 | }; | 1313 | }; |
| 1311 | 1314 | ||
| 1315 | #ifdef CONFIG_PM_SLEEP | ||
| 1316 | static int virtio_ccw_freeze(struct ccw_device *cdev) | ||
| 1317 | { | ||
| 1318 | struct virtio_ccw_device *vcdev = dev_get_drvdata(&cdev->dev); | ||
| 1319 | |||
| 1320 | return virtio_device_freeze(&vcdev->vdev); | ||
| 1321 | } | ||
| 1322 | |||
| 1323 | static int virtio_ccw_restore(struct ccw_device *cdev) | ||
| 1324 | { | ||
| 1325 | struct virtio_ccw_device *vcdev = dev_get_drvdata(&cdev->dev); | ||
| 1326 | int ret; | ||
| 1327 | |||
| 1328 | ret = virtio_ccw_set_transport_rev(vcdev); | ||
| 1329 | if (ret) | ||
| 1330 | return ret; | ||
| 1331 | |||
| 1332 | return virtio_device_restore(&vcdev->vdev); | ||
| 1333 | } | ||
| 1334 | #endif | ||
| 1335 | |||
| 1312 | static struct ccw_driver virtio_ccw_driver = { | 1336 | static struct ccw_driver virtio_ccw_driver = { |
| 1313 | .driver = { | 1337 | .driver = { |
| 1314 | .owner = THIS_MODULE, | 1338 | .owner = THIS_MODULE, |
| @@ -1321,6 +1345,11 @@ static struct ccw_driver virtio_ccw_driver = { | |||
| 1321 | .set_online = virtio_ccw_online, | 1345 | .set_online = virtio_ccw_online, |
| 1322 | .notify = virtio_ccw_cio_notify, | 1346 | .notify = virtio_ccw_cio_notify, |
| 1323 | .int_class = IRQIO_VIR, | 1347 | .int_class = IRQIO_VIR, |
| 1348 | #ifdef CONFIG_PM_SLEEP | ||
| 1349 | .freeze = virtio_ccw_freeze, | ||
| 1350 | .thaw = virtio_ccw_restore, | ||
| 1351 | .restore = virtio_ccw_restore, | ||
| 1352 | #endif | ||
| 1324 | }; | 1353 | }; |
| 1325 | 1354 | ||
| 1326 | static int __init pure_hex(char **cp, unsigned int *val, int min_digit, | 1355 | static int __init pure_hex(char **cp, unsigned int *val, int min_digit, |
diff --git a/drivers/scsi/Makefile b/drivers/scsi/Makefile index fcfd28d2884c..de1b3fce936d 100644 --- a/drivers/scsi/Makefile +++ b/drivers/scsi/Makefile | |||
| @@ -185,7 +185,6 @@ ncr53c8xx-flags-$(CONFIG_SCSI_ZALON) \ | |||
| 185 | CFLAGS_ncr53c8xx.o := $(ncr53c8xx-flags-y) $(ncr53c8xx-flags-m) | 185 | CFLAGS_ncr53c8xx.o := $(ncr53c8xx-flags-y) $(ncr53c8xx-flags-m) |
| 186 | zalon7xx-objs := zalon.o ncr53c8xx.o | 186 | zalon7xx-objs := zalon.o ncr53c8xx.o |
| 187 | NCR_Q720_mod-objs := NCR_Q720.o ncr53c8xx.o | 187 | NCR_Q720_mod-objs := NCR_Q720.o ncr53c8xx.o |
| 188 | oktagon_esp_mod-objs := oktagon_esp.o oktagon_io.o | ||
| 189 | 188 | ||
| 190 | # Files generated that shall be removed upon make clean | 189 | # Files generated that shall be removed upon make clean |
| 191 | clean-files := 53c700_d.h 53c700_u.h | 190 | clean-files := 53c700_d.h 53c700_u.h |
diff --git a/drivers/scsi/aacraid/linit.c b/drivers/scsi/aacraid/linit.c index b3b931ab77eb..2664ea0df35f 100644 --- a/drivers/scsi/aacraid/linit.c +++ b/drivers/scsi/aacraid/linit.c | |||
| @@ -1693,8 +1693,10 @@ static int aac_probe_one(struct pci_dev *pdev, const struct pci_device_id *id) | |||
| 1693 | * Map in the registers from the adapter. | 1693 | * Map in the registers from the adapter. |
| 1694 | */ | 1694 | */ |
| 1695 | aac->base_size = AAC_MIN_FOOTPRINT_SIZE; | 1695 | aac->base_size = AAC_MIN_FOOTPRINT_SIZE; |
| 1696 | if ((*aac_drivers[index].init)(aac)) | 1696 | if ((*aac_drivers[index].init)(aac)) { |
| 1697 | error = -ENODEV; | ||
| 1697 | goto out_unmap; | 1698 | goto out_unmap; |
| 1699 | } | ||
| 1698 | 1700 | ||
| 1699 | if (aac->sync_mode) { | 1701 | if (aac->sync_mode) { |
| 1700 | if (aac_sync_mode) | 1702 | if (aac_sync_mode) |
diff --git a/drivers/scsi/aic7xxx/aiclib.c b/drivers/scsi/aic7xxx/aiclib.c deleted file mode 100644 index 828ae3d9a510..000000000000 --- a/drivers/scsi/aic7xxx/aiclib.c +++ /dev/null | |||
| @@ -1,34 +0,0 @@ | |||
| 1 | /* | ||
| 2 | * Implementation of Utility functions for all SCSI device types. | ||
| 3 | * | ||
| 4 | * Copyright (c) 1997, 1998, 1999 Justin T. Gibbs. | ||
| 5 | * Copyright (c) 1997, 1998 Kenneth D. Merry. | ||
| 6 | * All rights reserved. | ||
| 7 | * | ||
| 8 | * Redistribution and use in source and binary forms, with or without | ||
| 9 | * modification, are permitted provided that the following conditions | ||
| 10 | * are met: | ||
| 11 | * 1. Redistributions of source code must retain the above copyright | ||
| 12 | * notice, this list of conditions, and the following disclaimer, | ||
| 13 | * without modification, immediately at the beginning of the file. | ||
| 14 | * 2. The name of the author may not be used to endorse or promote products | ||
| 15 | * derived from this software without specific prior written permission. | ||
| 16 | * | ||
| 17 | * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND | ||
| 18 | * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE | ||
| 19 | * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE | ||
| 20 | * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE FOR | ||
| 21 | * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL | ||
| 22 | * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS | ||
| 23 | * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) | ||
| 24 | * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT | ||
| 25 | * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY | ||
| 26 | * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF | ||
| 27 | * SUCH DAMAGE. | ||
| 28 | * | ||
| 29 | * $FreeBSD: src/sys/cam/scsi/scsi_all.c,v 1.38 2002/09/23 04:56:35 mjacob Exp $ | ||
| 30 | * $Id$ | ||
| 31 | */ | ||
| 32 | |||
| 33 | #include "aiclib.h" | ||
| 34 | |||
diff --git a/drivers/scsi/bnx2fc/bnx2fc_io.c b/drivers/scsi/bnx2fc/bnx2fc_io.c index 8e2f767147cb..5a645b8b9af1 100644 --- a/drivers/scsi/bnx2fc/bnx2fc_io.c +++ b/drivers/scsi/bnx2fc/bnx2fc_io.c | |||
| @@ -1889,6 +1889,7 @@ void bnx2fc_process_scsi_cmd_compl(struct bnx2fc_cmd *io_req, | |||
| 1889 | /* we will not receive ABTS response for this IO */ | 1889 | /* we will not receive ABTS response for this IO */ |
| 1890 | BNX2FC_IO_DBG(io_req, "Timer context finished processing " | 1890 | BNX2FC_IO_DBG(io_req, "Timer context finished processing " |
| 1891 | "this scsi cmd\n"); | 1891 | "this scsi cmd\n"); |
| 1892 | return; | ||
| 1892 | } | 1893 | } |
| 1893 | 1894 | ||
| 1894 | /* Cancel the timeout_work, as we received IO completion */ | 1895 | /* Cancel the timeout_work, as we received IO completion */ |
diff --git a/drivers/scsi/csiostor/csio_lnode.c b/drivers/scsi/csiostor/csio_lnode.c index be5ee2d37815..7dbbbb81a1e7 100644 --- a/drivers/scsi/csiostor/csio_lnode.c +++ b/drivers/scsi/csiostor/csio_lnode.c | |||
| @@ -114,7 +114,7 @@ static enum csio_ln_ev fwevt_to_lnevt[] = { | |||
| 114 | static struct csio_lnode * | 114 | static struct csio_lnode * |
| 115 | csio_ln_lookup_by_portid(struct csio_hw *hw, uint8_t portid) | 115 | csio_ln_lookup_by_portid(struct csio_hw *hw, uint8_t portid) |
| 116 | { | 116 | { |
| 117 | struct csio_lnode *ln = hw->rln; | 117 | struct csio_lnode *ln; |
| 118 | struct list_head *tmp; | 118 | struct list_head *tmp; |
| 119 | 119 | ||
| 120 | /* Match siblings lnode with portid */ | 120 | /* Match siblings lnode with portid */ |
diff --git a/drivers/scsi/device_handler/scsi_dh_alua.c b/drivers/scsi/device_handler/scsi_dh_alua.c index 022e421c2185..4b44325d1a82 100644 --- a/drivers/scsi/device_handler/scsi_dh_alua.c +++ b/drivers/scsi/device_handler/scsi_dh_alua.c | |||
| @@ -876,6 +876,11 @@ static void alua_rtpg_work(struct work_struct *work) | |||
| 876 | 876 | ||
| 877 | /** | 877 | /** |
| 878 | * alua_rtpg_queue() - cause RTPG to be submitted asynchronously | 878 | * alua_rtpg_queue() - cause RTPG to be submitted asynchronously |
| 879 | * @pg: ALUA port group associated with @sdev. | ||
| 880 | * @sdev: SCSI device for which to submit an RTPG. | ||
| 881 | * @qdata: Information about the callback to invoke after the RTPG. | ||
| 882 | * @force: Whether or not to submit an RTPG if a work item that will submit an | ||
| 883 | * RTPG already has been scheduled. | ||
| 879 | * | 884 | * |
| 880 | * Returns true if and only if alua_rtpg_work() will be called asynchronously. | 885 | * Returns true if and only if alua_rtpg_work() will be called asynchronously. |
| 881 | * That function is responsible for calling @qdata->fn(). | 886 | * That function is responsible for calling @qdata->fn(). |
diff --git a/drivers/scsi/ibmvscsi/ibmvfc.h b/drivers/scsi/ibmvscsi/ibmvfc.h index 9a0696f68f37..b81a53c4a9a8 100644 --- a/drivers/scsi/ibmvscsi/ibmvfc.h +++ b/drivers/scsi/ibmvscsi/ibmvfc.h | |||
| @@ -367,7 +367,7 @@ enum ibmvfc_fcp_rsp_info_codes { | |||
| 367 | }; | 367 | }; |
| 368 | 368 | ||
| 369 | struct ibmvfc_fcp_rsp_info { | 369 | struct ibmvfc_fcp_rsp_info { |
| 370 | __be16 reserved; | 370 | u8 reserved[3]; |
| 371 | u8 rsp_code; | 371 | u8 rsp_code; |
| 372 | u8 reserved2[4]; | 372 | u8 reserved2[4]; |
| 373 | }__attribute__((packed, aligned (2))); | 373 | }__attribute__((packed, aligned (2))); |
diff --git a/drivers/scsi/mpt3sas/mpt3sas_base.c b/drivers/scsi/mpt3sas/mpt3sas_base.c index 13d6e4ec3022..59a87ca328d3 100644 --- a/drivers/scsi/mpt3sas/mpt3sas_base.c +++ b/drivers/scsi/mpt3sas/mpt3sas_base.c | |||
| @@ -2410,8 +2410,11 @@ _base_assign_reply_queues(struct MPT3SAS_ADAPTER *ioc) | |||
| 2410 | continue; | 2410 | continue; |
| 2411 | } | 2411 | } |
| 2412 | 2412 | ||
| 2413 | for_each_cpu(cpu, mask) | 2413 | for_each_cpu_and(cpu, mask, cpu_online_mask) { |
| 2414 | if (cpu >= ioc->cpu_msix_table_sz) | ||
| 2415 | break; | ||
| 2414 | ioc->cpu_msix_table[cpu] = reply_q->msix_index; | 2416 | ioc->cpu_msix_table[cpu] = reply_q->msix_index; |
| 2417 | } | ||
| 2415 | } | 2418 | } |
| 2416 | return; | 2419 | return; |
| 2417 | } | 2420 | } |
diff --git a/drivers/scsi/qedi/qedi_main.c b/drivers/scsi/qedi/qedi_main.c index 029e2e69b29f..f57a94b4f0d9 100644 --- a/drivers/scsi/qedi/qedi_main.c +++ b/drivers/scsi/qedi/qedi_main.c | |||
| @@ -1724,7 +1724,6 @@ static ssize_t qedi_show_boot_eth_info(void *data, int type, char *buf) | |||
| 1724 | { | 1724 | { |
| 1725 | struct qedi_ctx *qedi = data; | 1725 | struct qedi_ctx *qedi = data; |
| 1726 | struct nvm_iscsi_initiator *initiator; | 1726 | struct nvm_iscsi_initiator *initiator; |
| 1727 | char *str = buf; | ||
| 1728 | int rc = 1; | 1727 | int rc = 1; |
| 1729 | u32 ipv6_en, dhcp_en, ip_len; | 1728 | u32 ipv6_en, dhcp_en, ip_len; |
| 1730 | struct nvm_iscsi_block *block; | 1729 | struct nvm_iscsi_block *block; |
| @@ -1758,32 +1757,32 @@ static ssize_t qedi_show_boot_eth_info(void *data, int type, char *buf) | |||
| 1758 | 1757 | ||
| 1759 | switch (type) { | 1758 | switch (type) { |
| 1760 | case ISCSI_BOOT_ETH_IP_ADDR: | 1759 | case ISCSI_BOOT_ETH_IP_ADDR: |
| 1761 | rc = snprintf(str, ip_len, fmt, ip); | 1760 | rc = snprintf(buf, ip_len, fmt, ip); |
| 1762 | break; | 1761 | break; |
| 1763 | case ISCSI_BOOT_ETH_SUBNET_MASK: | 1762 | case ISCSI_BOOT_ETH_SUBNET_MASK: |
| 1764 | rc = snprintf(str, ip_len, fmt, sub); | 1763 | rc = snprintf(buf, ip_len, fmt, sub); |
| 1765 | break; | 1764 | break; |
| 1766 | case ISCSI_BOOT_ETH_GATEWAY: | 1765 | case ISCSI_BOOT_ETH_GATEWAY: |
| 1767 | rc = snprintf(str, ip_len, fmt, gw); | 1766 | rc = snprintf(buf, ip_len, fmt, gw); |
| 1768 | break; | 1767 | break; |
| 1769 | case ISCSI_BOOT_ETH_FLAGS: | 1768 | case ISCSI_BOOT_ETH_FLAGS: |
| 1770 | rc = snprintf(str, 3, "%hhd\n", | 1769 | rc = snprintf(buf, 3, "%hhd\n", |
| 1771 | SYSFS_FLAG_FW_SEL_BOOT); | 1770 | SYSFS_FLAG_FW_SEL_BOOT); |
| 1772 | break; | 1771 | break; |
| 1773 | case ISCSI_BOOT_ETH_INDEX: | 1772 | case ISCSI_BOOT_ETH_INDEX: |
| 1774 | rc = snprintf(str, 3, "0\n"); | 1773 | rc = snprintf(buf, 3, "0\n"); |
| 1775 | break; | 1774 | break; |
| 1776 | case ISCSI_BOOT_ETH_MAC: | 1775 | case ISCSI_BOOT_ETH_MAC: |
| 1777 | rc = sysfs_format_mac(str, qedi->mac, ETH_ALEN); | 1776 | rc = sysfs_format_mac(buf, qedi->mac, ETH_ALEN); |
| 1778 | break; | 1777 | break; |
| 1779 | case ISCSI_BOOT_ETH_VLAN: | 1778 | case ISCSI_BOOT_ETH_VLAN: |
| 1780 | rc = snprintf(str, 12, "%d\n", | 1779 | rc = snprintf(buf, 12, "%d\n", |
| 1781 | GET_FIELD2(initiator->generic_cont0, | 1780 | GET_FIELD2(initiator->generic_cont0, |
| 1782 | NVM_ISCSI_CFG_INITIATOR_VLAN)); | 1781 | NVM_ISCSI_CFG_INITIATOR_VLAN)); |
| 1783 | break; | 1782 | break; |
| 1784 | case ISCSI_BOOT_ETH_ORIGIN: | 1783 | case ISCSI_BOOT_ETH_ORIGIN: |
| 1785 | if (dhcp_en) | 1784 | if (dhcp_en) |
| 1786 | rc = snprintf(str, 3, "3\n"); | 1785 | rc = snprintf(buf, 3, "3\n"); |
| 1787 | break; | 1786 | break; |
| 1788 | default: | 1787 | default: |
| 1789 | rc = 0; | 1788 | rc = 0; |
| @@ -1819,7 +1818,6 @@ static ssize_t qedi_show_boot_ini_info(void *data, int type, char *buf) | |||
| 1819 | { | 1818 | { |
| 1820 | struct qedi_ctx *qedi = data; | 1819 | struct qedi_ctx *qedi = data; |
| 1821 | struct nvm_iscsi_initiator *initiator; | 1820 | struct nvm_iscsi_initiator *initiator; |
| 1822 | char *str = buf; | ||
| 1823 | int rc; | 1821 | int rc; |
| 1824 | struct nvm_iscsi_block *block; | 1822 | struct nvm_iscsi_block *block; |
| 1825 | 1823 | ||
| @@ -1831,8 +1829,8 @@ static ssize_t qedi_show_boot_ini_info(void *data, int type, char *buf) | |||
| 1831 | 1829 | ||
| 1832 | switch (type) { | 1830 | switch (type) { |
| 1833 | case ISCSI_BOOT_INI_INITIATOR_NAME: | 1831 | case ISCSI_BOOT_INI_INITIATOR_NAME: |
| 1834 | rc = snprintf(str, NVM_ISCSI_CFG_ISCSI_NAME_MAX_LEN, "%s\n", | 1832 | rc = sprintf(buf, "%.*s\n", NVM_ISCSI_CFG_ISCSI_NAME_MAX_LEN, |
| 1835 | initiator->initiator_name.byte); | 1833 | initiator->initiator_name.byte); |
| 1836 | break; | 1834 | break; |
| 1837 | default: | 1835 | default: |
| 1838 | rc = 0; | 1836 | rc = 0; |
| @@ -1860,7 +1858,6 @@ static ssize_t | |||
| 1860 | qedi_show_boot_tgt_info(struct qedi_ctx *qedi, int type, | 1858 | qedi_show_boot_tgt_info(struct qedi_ctx *qedi, int type, |
| 1861 | char *buf, enum qedi_nvm_tgts idx) | 1859 | char *buf, enum qedi_nvm_tgts idx) |
| 1862 | { | 1860 | { |
| 1863 | char *str = buf; | ||
| 1864 | int rc = 1; | 1861 | int rc = 1; |
| 1865 | u32 ctrl_flags, ipv6_en, chap_en, mchap_en, ip_len; | 1862 | u32 ctrl_flags, ipv6_en, chap_en, mchap_en, ip_len; |
| 1866 | struct nvm_iscsi_block *block; | 1863 | struct nvm_iscsi_block *block; |
| @@ -1899,48 +1896,48 @@ qedi_show_boot_tgt_info(struct qedi_ctx *qedi, int type, | |||
| 1899 | 1896 | ||
| 1900 | switch (type) { | 1897 | switch (type) { |
| 1901 | case ISCSI_BOOT_TGT_NAME: | 1898 | case ISCSI_BOOT_TGT_NAME: |
| 1902 | rc = snprintf(str, NVM_ISCSI_CFG_ISCSI_NAME_MAX_LEN, "%s\n", | 1899 | rc = sprintf(buf, "%.*s\n", NVM_ISCSI_CFG_ISCSI_NAME_MAX_LEN, |
| 1903 | block->target[idx].target_name.byte); | 1900 | block->target[idx].target_name.byte); |
| 1904 | break; | 1901 | break; |
| 1905 | case ISCSI_BOOT_TGT_IP_ADDR: | 1902 | case ISCSI_BOOT_TGT_IP_ADDR: |
| 1906 | if (ipv6_en) | 1903 | if (ipv6_en) |
| 1907 | rc = snprintf(str, ip_len, "%pI6\n", | 1904 | rc = snprintf(buf, ip_len, "%pI6\n", |
| 1908 | block->target[idx].ipv6_addr.byte); | 1905 | block->target[idx].ipv6_addr.byte); |
| 1909 | else | 1906 | else |
| 1910 | rc = snprintf(str, ip_len, "%pI4\n", | 1907 | rc = snprintf(buf, ip_len, "%pI4\n", |
| 1911 | block->target[idx].ipv4_addr.byte); | 1908 | block->target[idx].ipv4_addr.byte); |
| 1912 | break; | 1909 | break; |
| 1913 | case ISCSI_BOOT_TGT_PORT: | 1910 | case ISCSI_BOOT_TGT_PORT: |
| 1914 | rc = snprintf(str, 12, "%d\n", | 1911 | rc = snprintf(buf, 12, "%d\n", |
| 1915 | GET_FIELD2(block->target[idx].generic_cont0, | 1912 | GET_FIELD2(block->target[idx].generic_cont0, |
| 1916 | NVM_ISCSI_CFG_TARGET_TCP_PORT)); | 1913 | NVM_ISCSI_CFG_TARGET_TCP_PORT)); |
| 1917 | break; | 1914 | break; |
| 1918 | case ISCSI_BOOT_TGT_LUN: | 1915 | case ISCSI_BOOT_TGT_LUN: |
| 1919 | rc = snprintf(str, 22, "%.*d\n", | 1916 | rc = snprintf(buf, 22, "%.*d\n", |
| 1920 | block->target[idx].lun.value[1], | 1917 | block->target[idx].lun.value[1], |
| 1921 | block->target[idx].lun.value[0]); | 1918 | block->target[idx].lun.value[0]); |
| 1922 | break; | 1919 | break; |
| 1923 | case ISCSI_BOOT_TGT_CHAP_NAME: | 1920 | case ISCSI_BOOT_TGT_CHAP_NAME: |
| 1924 | rc = snprintf(str, NVM_ISCSI_CFG_CHAP_NAME_MAX_LEN, "%s\n", | 1921 | rc = sprintf(buf, "%.*s\n", NVM_ISCSI_CFG_CHAP_NAME_MAX_LEN, |
| 1925 | chap_name); | 1922 | chap_name); |
| 1926 | break; | 1923 | break; |
| 1927 | case ISCSI_BOOT_TGT_CHAP_SECRET: | 1924 | case ISCSI_BOOT_TGT_CHAP_SECRET: |
| 1928 | rc = snprintf(str, NVM_ISCSI_CFG_CHAP_PWD_MAX_LEN, "%s\n", | 1925 | rc = sprintf(buf, "%.*s\n", NVM_ISCSI_CFG_CHAP_NAME_MAX_LEN, |
| 1929 | chap_secret); | 1926 | chap_secret); |
| 1930 | break; | 1927 | break; |
| 1931 | case ISCSI_BOOT_TGT_REV_CHAP_NAME: | 1928 | case ISCSI_BOOT_TGT_REV_CHAP_NAME: |
| 1932 | rc = snprintf(str, NVM_ISCSI_CFG_CHAP_NAME_MAX_LEN, "%s\n", | 1929 | rc = sprintf(buf, "%.*s\n", NVM_ISCSI_CFG_CHAP_NAME_MAX_LEN, |
| 1933 | mchap_name); | 1930 | mchap_name); |
| 1934 | break; | 1931 | break; |
| 1935 | case ISCSI_BOOT_TGT_REV_CHAP_SECRET: | 1932 | case ISCSI_BOOT_TGT_REV_CHAP_SECRET: |
| 1936 | rc = snprintf(str, NVM_ISCSI_CFG_CHAP_PWD_MAX_LEN, "%s\n", | 1933 | rc = sprintf(buf, "%.*s\n", NVM_ISCSI_CFG_CHAP_NAME_MAX_LEN, |
| 1937 | mchap_secret); | 1934 | mchap_secret); |
| 1938 | break; | 1935 | break; |
| 1939 | case ISCSI_BOOT_TGT_FLAGS: | 1936 | case ISCSI_BOOT_TGT_FLAGS: |
| 1940 | rc = snprintf(str, 3, "%hhd\n", SYSFS_FLAG_FW_SEL_BOOT); | 1937 | rc = snprintf(buf, 3, "%hhd\n", SYSFS_FLAG_FW_SEL_BOOT); |
| 1941 | break; | 1938 | break; |
| 1942 | case ISCSI_BOOT_TGT_NIC_ASSOC: | 1939 | case ISCSI_BOOT_TGT_NIC_ASSOC: |
| 1943 | rc = snprintf(str, 3, "0\n"); | 1940 | rc = snprintf(buf, 3, "0\n"); |
| 1944 | break; | 1941 | break; |
| 1945 | default: | 1942 | default: |
| 1946 | rc = 0; | 1943 | rc = 0; |
diff --git a/drivers/scsi/qla2xxx/qla_init.c b/drivers/scsi/qla2xxx/qla_init.c index aececf664654..2dea1129d396 100644 --- a/drivers/scsi/qla2xxx/qla_init.c +++ b/drivers/scsi/qla2xxx/qla_init.c | |||
| @@ -59,8 +59,6 @@ qla2x00_sp_timeout(struct timer_list *t) | |||
| 59 | req->outstanding_cmds[sp->handle] = NULL; | 59 | req->outstanding_cmds[sp->handle] = NULL; |
| 60 | iocb = &sp->u.iocb_cmd; | 60 | iocb = &sp->u.iocb_cmd; |
| 61 | iocb->timeout(sp); | 61 | iocb->timeout(sp); |
| 62 | if (sp->type != SRB_ELS_DCMD) | ||
| 63 | sp->free(sp); | ||
| 64 | spin_unlock_irqrestore(&vha->hw->hardware_lock, flags); | 62 | spin_unlock_irqrestore(&vha->hw->hardware_lock, flags); |
| 65 | } | 63 | } |
| 66 | 64 | ||
| @@ -102,7 +100,6 @@ qla2x00_async_iocb_timeout(void *data) | |||
| 102 | srb_t *sp = data; | 100 | srb_t *sp = data; |
| 103 | fc_port_t *fcport = sp->fcport; | 101 | fc_port_t *fcport = sp->fcport; |
| 104 | struct srb_iocb *lio = &sp->u.iocb_cmd; | 102 | struct srb_iocb *lio = &sp->u.iocb_cmd; |
| 105 | struct event_arg ea; | ||
| 106 | 103 | ||
| 107 | if (fcport) { | 104 | if (fcport) { |
| 108 | ql_dbg(ql_dbg_disc, fcport->vha, 0x2071, | 105 | ql_dbg(ql_dbg_disc, fcport->vha, 0x2071, |
| @@ -117,25 +114,13 @@ qla2x00_async_iocb_timeout(void *data) | |||
| 117 | 114 | ||
| 118 | switch (sp->type) { | 115 | switch (sp->type) { |
| 119 | case SRB_LOGIN_CMD: | 116 | case SRB_LOGIN_CMD: |
| 120 | if (!fcport) | ||
| 121 | break; | ||
| 122 | /* Retry as needed. */ | 117 | /* Retry as needed. */ |
| 123 | lio->u.logio.data[0] = MBS_COMMAND_ERROR; | 118 | lio->u.logio.data[0] = MBS_COMMAND_ERROR; |
| 124 | lio->u.logio.data[1] = lio->u.logio.flags & SRB_LOGIN_RETRIED ? | 119 | lio->u.logio.data[1] = lio->u.logio.flags & SRB_LOGIN_RETRIED ? |
| 125 | QLA_LOGIO_LOGIN_RETRIED : 0; | 120 | QLA_LOGIO_LOGIN_RETRIED : 0; |
| 126 | memset(&ea, 0, sizeof(ea)); | 121 | sp->done(sp, QLA_FUNCTION_TIMEOUT); |
| 127 | ea.event = FCME_PLOGI_DONE; | ||
| 128 | ea.fcport = sp->fcport; | ||
| 129 | ea.data[0] = lio->u.logio.data[0]; | ||
| 130 | ea.data[1] = lio->u.logio.data[1]; | ||
| 131 | ea.sp = sp; | ||
| 132 | qla24xx_handle_plogi_done_event(fcport->vha, &ea); | ||
| 133 | break; | 122 | break; |
| 134 | case SRB_LOGOUT_CMD: | 123 | case SRB_LOGOUT_CMD: |
| 135 | if (!fcport) | ||
| 136 | break; | ||
| 137 | qlt_logo_completion_handler(fcport, QLA_FUNCTION_TIMEOUT); | ||
| 138 | break; | ||
| 139 | case SRB_CT_PTHRU_CMD: | 124 | case SRB_CT_PTHRU_CMD: |
| 140 | case SRB_MB_IOCB: | 125 | case SRB_MB_IOCB: |
| 141 | case SRB_NACK_PLOGI: | 126 | case SRB_NACK_PLOGI: |
| @@ -235,12 +220,10 @@ static void | |||
| 235 | qla2x00_async_logout_sp_done(void *ptr, int res) | 220 | qla2x00_async_logout_sp_done(void *ptr, int res) |
| 236 | { | 221 | { |
| 237 | srb_t *sp = ptr; | 222 | srb_t *sp = ptr; |
| 238 | struct srb_iocb *lio = &sp->u.iocb_cmd; | ||
| 239 | 223 | ||
| 240 | sp->fcport->flags &= ~(FCF_ASYNC_SENT | FCF_ASYNC_ACTIVE); | 224 | sp->fcport->flags &= ~(FCF_ASYNC_SENT | FCF_ASYNC_ACTIVE); |
| 241 | if (!test_bit(UNLOADING, &sp->vha->dpc_flags)) | 225 | sp->fcport->login_gen++; |
| 242 | qla2x00_post_async_logout_done_work(sp->vha, sp->fcport, | 226 | qlt_logo_completion_handler(sp->fcport, res); |
| 243 | lio->u.logio.data); | ||
| 244 | sp->free(sp); | 227 | sp->free(sp); |
| 245 | } | 228 | } |
| 246 | 229 | ||
diff --git a/drivers/scsi/qla2xxx/qla_iocb.c b/drivers/scsi/qla2xxx/qla_iocb.c index 1b62e943ec49..8d00d559bd26 100644 --- a/drivers/scsi/qla2xxx/qla_iocb.c +++ b/drivers/scsi/qla2xxx/qla_iocb.c | |||
| @@ -3275,12 +3275,11 @@ qla24xx_abort_iocb(srb_t *sp, struct abort_entry_24xx *abt_iocb) | |||
| 3275 | memset(abt_iocb, 0, sizeof(struct abort_entry_24xx)); | 3275 | memset(abt_iocb, 0, sizeof(struct abort_entry_24xx)); |
| 3276 | abt_iocb->entry_type = ABORT_IOCB_TYPE; | 3276 | abt_iocb->entry_type = ABORT_IOCB_TYPE; |
| 3277 | abt_iocb->entry_count = 1; | 3277 | abt_iocb->entry_count = 1; |
| 3278 | abt_iocb->handle = | 3278 | abt_iocb->handle = cpu_to_le32(MAKE_HANDLE(req->id, sp->handle)); |
| 3279 | cpu_to_le32(MAKE_HANDLE(aio->u.abt.req_que_no, | ||
| 3280 | aio->u.abt.cmd_hndl)); | ||
| 3281 | abt_iocb->nport_handle = cpu_to_le16(sp->fcport->loop_id); | 3279 | abt_iocb->nport_handle = cpu_to_le16(sp->fcport->loop_id); |
| 3282 | abt_iocb->handle_to_abort = | 3280 | abt_iocb->handle_to_abort = |
| 3283 | cpu_to_le32(MAKE_HANDLE(req->id, aio->u.abt.cmd_hndl)); | 3281 | cpu_to_le32(MAKE_HANDLE(aio->u.abt.req_que_no, |
| 3282 | aio->u.abt.cmd_hndl)); | ||
| 3284 | abt_iocb->port_id[0] = sp->fcport->d_id.b.al_pa; | 3283 | abt_iocb->port_id[0] = sp->fcport->d_id.b.al_pa; |
| 3285 | abt_iocb->port_id[1] = sp->fcport->d_id.b.area; | 3284 | abt_iocb->port_id[1] = sp->fcport->d_id.b.area; |
| 3286 | abt_iocb->port_id[2] = sp->fcport->d_id.b.domain; | 3285 | abt_iocb->port_id[2] = sp->fcport->d_id.b.domain; |
diff --git a/drivers/scsi/qla2xxx/qla_isr.c b/drivers/scsi/qla2xxx/qla_isr.c index 14109d86c3f6..89f93ebd819d 100644 --- a/drivers/scsi/qla2xxx/qla_isr.c +++ b/drivers/scsi/qla2xxx/qla_isr.c | |||
| @@ -272,7 +272,8 @@ qla2x00_mbx_completion(scsi_qla_host_t *vha, uint16_t mb0) | |||
| 272 | struct device_reg_2xxx __iomem *reg = &ha->iobase->isp; | 272 | struct device_reg_2xxx __iomem *reg = &ha->iobase->isp; |
| 273 | 273 | ||
| 274 | /* Read all mbox registers? */ | 274 | /* Read all mbox registers? */ |
| 275 | mboxes = (1 << ha->mbx_count) - 1; | 275 | WARN_ON_ONCE(ha->mbx_count > 32); |
| 276 | mboxes = (1ULL << ha->mbx_count) - 1; | ||
| 276 | if (!ha->mcp) | 277 | if (!ha->mcp) |
| 277 | ql_dbg(ql_dbg_async, vha, 0x5001, "MBX pointer ERROR.\n"); | 278 | ql_dbg(ql_dbg_async, vha, 0x5001, "MBX pointer ERROR.\n"); |
| 278 | else | 279 | else |
| @@ -2880,7 +2881,8 @@ qla24xx_mbx_completion(scsi_qla_host_t *vha, uint16_t mb0) | |||
| 2880 | struct device_reg_24xx __iomem *reg = &ha->iobase->isp24; | 2881 | struct device_reg_24xx __iomem *reg = &ha->iobase->isp24; |
| 2881 | 2882 | ||
| 2882 | /* Read all mbox registers? */ | 2883 | /* Read all mbox registers? */ |
| 2883 | mboxes = (1 << ha->mbx_count) - 1; | 2884 | WARN_ON_ONCE(ha->mbx_count > 32); |
| 2885 | mboxes = (1ULL << ha->mbx_count) - 1; | ||
| 2884 | if (!ha->mcp) | 2886 | if (!ha->mcp) |
| 2885 | ql_dbg(ql_dbg_async, vha, 0x504e, "MBX pointer ERROR.\n"); | 2887 | ql_dbg(ql_dbg_async, vha, 0x504e, "MBX pointer ERROR.\n"); |
| 2886 | else | 2888 | else |
diff --git a/drivers/scsi/qla2xxx/qla_os.c b/drivers/scsi/qla2xxx/qla_os.c index 12ee6e02d146..afcb5567998a 100644 --- a/drivers/scsi/qla2xxx/qla_os.c +++ b/drivers/scsi/qla2xxx/qla_os.c | |||
| @@ -3625,6 +3625,8 @@ qla2x00_remove_one(struct pci_dev *pdev) | |||
| 3625 | } | 3625 | } |
| 3626 | qla2x00_wait_for_hba_ready(base_vha); | 3626 | qla2x00_wait_for_hba_ready(base_vha); |
| 3627 | 3627 | ||
| 3628 | qla2x00_wait_for_sess_deletion(base_vha); | ||
| 3629 | |||
| 3628 | /* | 3630 | /* |
| 3629 | * if UNLOAD flag is already set, then continue unload, | 3631 | * if UNLOAD flag is already set, then continue unload, |
| 3630 | * where it was set first. | 3632 | * where it was set first. |
diff --git a/drivers/scsi/qla2xxx/qla_target.c b/drivers/scsi/qla2xxx/qla_target.c index fc89af8fe256..896b2d8bd803 100644 --- a/drivers/scsi/qla2xxx/qla_target.c +++ b/drivers/scsi/qla2xxx/qla_target.c | |||
| @@ -4871,8 +4871,6 @@ static int qlt_24xx_handle_els(struct scsi_qla_host *vha, | |||
| 4871 | sess); | 4871 | sess); |
| 4872 | qlt_send_term_imm_notif(vha, iocb, 1); | 4872 | qlt_send_term_imm_notif(vha, iocb, 1); |
| 4873 | res = 0; | 4873 | res = 0; |
| 4874 | spin_lock_irqsave(&tgt->ha->tgt.sess_lock, | ||
| 4875 | flags); | ||
| 4876 | break; | 4874 | break; |
| 4877 | } | 4875 | } |
| 4878 | 4876 | ||
diff --git a/drivers/scsi/qla4xxx/ql4_def.h b/drivers/scsi/qla4xxx/ql4_def.h index fc233717355f..817f312023a9 100644 --- a/drivers/scsi/qla4xxx/ql4_def.h +++ b/drivers/scsi/qla4xxx/ql4_def.h | |||
| @@ -168,6 +168,8 @@ | |||
| 168 | #define DEV_DB_NON_PERSISTENT 0 | 168 | #define DEV_DB_NON_PERSISTENT 0 |
| 169 | #define DEV_DB_PERSISTENT 1 | 169 | #define DEV_DB_PERSISTENT 1 |
| 170 | 170 | ||
| 171 | #define QL4_ISP_REG_DISCONNECT 0xffffffffU | ||
| 172 | |||
| 171 | #define COPY_ISID(dst_isid, src_isid) { \ | 173 | #define COPY_ISID(dst_isid, src_isid) { \ |
| 172 | int i, j; \ | 174 | int i, j; \ |
| 173 | for (i = 0, j = ISID_SIZE - 1; i < ISID_SIZE;) \ | 175 | for (i = 0, j = ISID_SIZE - 1; i < ISID_SIZE;) \ |
diff --git a/drivers/scsi/qla4xxx/ql4_os.c b/drivers/scsi/qla4xxx/ql4_os.c index 82e889bbe0ed..fc2c97d9a0d6 100644 --- a/drivers/scsi/qla4xxx/ql4_os.c +++ b/drivers/scsi/qla4xxx/ql4_os.c | |||
| @@ -262,6 +262,24 @@ static struct iscsi_transport qla4xxx_iscsi_transport = { | |||
| 262 | 262 | ||
| 263 | static struct scsi_transport_template *qla4xxx_scsi_transport; | 263 | static struct scsi_transport_template *qla4xxx_scsi_transport; |
| 264 | 264 | ||
| 265 | static int qla4xxx_isp_check_reg(struct scsi_qla_host *ha) | ||
| 266 | { | ||
| 267 | u32 reg_val = 0; | ||
| 268 | int rval = QLA_SUCCESS; | ||
| 269 | |||
| 270 | if (is_qla8022(ha)) | ||
| 271 | reg_val = readl(&ha->qla4_82xx_reg->host_status); | ||
| 272 | else if (is_qla8032(ha) || is_qla8042(ha)) | ||
| 273 | reg_val = qla4_8xxx_rd_direct(ha, QLA8XXX_PEG_ALIVE_COUNTER); | ||
| 274 | else | ||
| 275 | reg_val = readw(&ha->reg->ctrl_status); | ||
| 276 | |||
| 277 | if (reg_val == QL4_ISP_REG_DISCONNECT) | ||
| 278 | rval = QLA_ERROR; | ||
| 279 | |||
| 280 | return rval; | ||
| 281 | } | ||
| 282 | |||
| 265 | static int qla4xxx_send_ping(struct Scsi_Host *shost, uint32_t iface_num, | 283 | static int qla4xxx_send_ping(struct Scsi_Host *shost, uint32_t iface_num, |
| 266 | uint32_t iface_type, uint32_t payload_size, | 284 | uint32_t iface_type, uint32_t payload_size, |
| 267 | uint32_t pid, struct sockaddr *dst_addr) | 285 | uint32_t pid, struct sockaddr *dst_addr) |
| @@ -9186,10 +9204,17 @@ static int qla4xxx_eh_abort(struct scsi_cmnd *cmd) | |||
| 9186 | struct srb *srb = NULL; | 9204 | struct srb *srb = NULL; |
| 9187 | int ret = SUCCESS; | 9205 | int ret = SUCCESS; |
| 9188 | int wait = 0; | 9206 | int wait = 0; |
| 9207 | int rval; | ||
| 9189 | 9208 | ||
| 9190 | ql4_printk(KERN_INFO, ha, "scsi%ld:%d:%llu: Abort command issued cmd=%p, cdb=0x%x\n", | 9209 | ql4_printk(KERN_INFO, ha, "scsi%ld:%d:%llu: Abort command issued cmd=%p, cdb=0x%x\n", |
| 9191 | ha->host_no, id, lun, cmd, cmd->cmnd[0]); | 9210 | ha->host_no, id, lun, cmd, cmd->cmnd[0]); |
| 9192 | 9211 | ||
| 9212 | rval = qla4xxx_isp_check_reg(ha); | ||
| 9213 | if (rval != QLA_SUCCESS) { | ||
| 9214 | ql4_printk(KERN_INFO, ha, "PCI/Register disconnect, exiting.\n"); | ||
| 9215 | return FAILED; | ||
| 9216 | } | ||
| 9217 | |||
| 9193 | spin_lock_irqsave(&ha->hardware_lock, flags); | 9218 | spin_lock_irqsave(&ha->hardware_lock, flags); |
| 9194 | srb = (struct srb *) CMD_SP(cmd); | 9219 | srb = (struct srb *) CMD_SP(cmd); |
| 9195 | if (!srb) { | 9220 | if (!srb) { |
| @@ -9241,6 +9266,7 @@ static int qla4xxx_eh_device_reset(struct scsi_cmnd *cmd) | |||
| 9241 | struct scsi_qla_host *ha = to_qla_host(cmd->device->host); | 9266 | struct scsi_qla_host *ha = to_qla_host(cmd->device->host); |
| 9242 | struct ddb_entry *ddb_entry = cmd->device->hostdata; | 9267 | struct ddb_entry *ddb_entry = cmd->device->hostdata; |
| 9243 | int ret = FAILED, stat; | 9268 | int ret = FAILED, stat; |
| 9269 | int rval; | ||
| 9244 | 9270 | ||
| 9245 | if (!ddb_entry) | 9271 | if (!ddb_entry) |
| 9246 | return ret; | 9272 | return ret; |
| @@ -9260,6 +9286,12 @@ static int qla4xxx_eh_device_reset(struct scsi_cmnd *cmd) | |||
| 9260 | cmd, jiffies, cmd->request->timeout / HZ, | 9286 | cmd, jiffies, cmd->request->timeout / HZ, |
| 9261 | ha->dpc_flags, cmd->result, cmd->allowed)); | 9287 | ha->dpc_flags, cmd->result, cmd->allowed)); |
| 9262 | 9288 | ||
| 9289 | rval = qla4xxx_isp_check_reg(ha); | ||
| 9290 | if (rval != QLA_SUCCESS) { | ||
| 9291 | ql4_printk(KERN_INFO, ha, "PCI/Register disconnect, exiting.\n"); | ||
| 9292 | return FAILED; | ||
| 9293 | } | ||
| 9294 | |||
| 9263 | /* FIXME: wait for hba to go online */ | 9295 | /* FIXME: wait for hba to go online */ |
| 9264 | stat = qla4xxx_reset_lun(ha, ddb_entry, cmd->device->lun); | 9296 | stat = qla4xxx_reset_lun(ha, ddb_entry, cmd->device->lun); |
| 9265 | if (stat != QLA_SUCCESS) { | 9297 | if (stat != QLA_SUCCESS) { |
| @@ -9303,6 +9335,7 @@ static int qla4xxx_eh_target_reset(struct scsi_cmnd *cmd) | |||
| 9303 | struct scsi_qla_host *ha = to_qla_host(cmd->device->host); | 9335 | struct scsi_qla_host *ha = to_qla_host(cmd->device->host); |
| 9304 | struct ddb_entry *ddb_entry = cmd->device->hostdata; | 9336 | struct ddb_entry *ddb_entry = cmd->device->hostdata; |
| 9305 | int stat, ret; | 9337 | int stat, ret; |
| 9338 | int rval; | ||
| 9306 | 9339 | ||
| 9307 | if (!ddb_entry) | 9340 | if (!ddb_entry) |
| 9308 | return FAILED; | 9341 | return FAILED; |
| @@ -9320,6 +9353,12 @@ static int qla4xxx_eh_target_reset(struct scsi_cmnd *cmd) | |||
| 9320 | ha->host_no, cmd, jiffies, cmd->request->timeout / HZ, | 9353 | ha->host_no, cmd, jiffies, cmd->request->timeout / HZ, |
| 9321 | ha->dpc_flags, cmd->result, cmd->allowed)); | 9354 | ha->dpc_flags, cmd->result, cmd->allowed)); |
| 9322 | 9355 | ||
| 9356 | rval = qla4xxx_isp_check_reg(ha); | ||
| 9357 | if (rval != QLA_SUCCESS) { | ||
| 9358 | ql4_printk(KERN_INFO, ha, "PCI/Register disconnect, exiting.\n"); | ||
| 9359 | return FAILED; | ||
| 9360 | } | ||
| 9361 | |||
| 9323 | stat = qla4xxx_reset_target(ha, ddb_entry); | 9362 | stat = qla4xxx_reset_target(ha, ddb_entry); |
| 9324 | if (stat != QLA_SUCCESS) { | 9363 | if (stat != QLA_SUCCESS) { |
| 9325 | starget_printk(KERN_INFO, scsi_target(cmd->device), | 9364 | starget_printk(KERN_INFO, scsi_target(cmd->device), |
| @@ -9374,9 +9413,16 @@ static int qla4xxx_eh_host_reset(struct scsi_cmnd *cmd) | |||
| 9374 | { | 9413 | { |
| 9375 | int return_status = FAILED; | 9414 | int return_status = FAILED; |
| 9376 | struct scsi_qla_host *ha; | 9415 | struct scsi_qla_host *ha; |
| 9416 | int rval; | ||
| 9377 | 9417 | ||
| 9378 | ha = to_qla_host(cmd->device->host); | 9418 | ha = to_qla_host(cmd->device->host); |
| 9379 | 9419 | ||
| 9420 | rval = qla4xxx_isp_check_reg(ha); | ||
| 9421 | if (rval != QLA_SUCCESS) { | ||
| 9422 | ql4_printk(KERN_INFO, ha, "PCI/Register disconnect, exiting.\n"); | ||
| 9423 | return FAILED; | ||
| 9424 | } | ||
| 9425 | |||
| 9380 | if ((is_qla8032(ha) || is_qla8042(ha)) && ql4xdontresethba) | 9426 | if ((is_qla8032(ha) || is_qla8042(ha)) && ql4xdontresethba) |
| 9381 | qla4_83xx_set_idc_dontreset(ha); | 9427 | qla4_83xx_set_idc_dontreset(ha); |
| 9382 | 9428 | ||
diff --git a/drivers/scsi/storvsc_drv.c b/drivers/scsi/storvsc_drv.c index 40fc7a590e81..6be5ab32c94f 100644 --- a/drivers/scsi/storvsc_drv.c +++ b/drivers/scsi/storvsc_drv.c | |||
| @@ -1657,7 +1657,7 @@ static struct scsi_host_template scsi_driver = { | |||
| 1657 | .eh_timed_out = storvsc_eh_timed_out, | 1657 | .eh_timed_out = storvsc_eh_timed_out, |
| 1658 | .slave_alloc = storvsc_device_alloc, | 1658 | .slave_alloc = storvsc_device_alloc, |
| 1659 | .slave_configure = storvsc_device_configure, | 1659 | .slave_configure = storvsc_device_configure, |
| 1660 | .cmd_per_lun = 255, | 1660 | .cmd_per_lun = 2048, |
| 1661 | .this_id = -1, | 1661 | .this_id = -1, |
| 1662 | .use_clustering = ENABLE_CLUSTERING, | 1662 | .use_clustering = ENABLE_CLUSTERING, |
| 1663 | /* Make sure we dont get a sg segment crosses a page boundary */ | 1663 | /* Make sure we dont get a sg segment crosses a page boundary */ |
diff --git a/drivers/scsi/sym53c8xx_2/sym_hipd.c b/drivers/scsi/sym53c8xx_2/sym_hipd.c index ca360daa6a25..378af306fda1 100644 --- a/drivers/scsi/sym53c8xx_2/sym_hipd.c +++ b/drivers/scsi/sym53c8xx_2/sym_hipd.c | |||
| @@ -536,7 +536,7 @@ sym_getsync(struct sym_hcb *np, u_char dt, u_char sfac, u_char *divp, u_char *fa | |||
| 536 | * Look for the greatest clock divisor that allows an | 536 | * Look for the greatest clock divisor that allows an |
| 537 | * input speed faster than the period. | 537 | * input speed faster than the period. |
| 538 | */ | 538 | */ |
| 539 | while (div-- > 0) | 539 | while (--div > 0) |
| 540 | if (kpc >= (div_10M[div] << 2)) break; | 540 | if (kpc >= (div_10M[div] << 2)) break; |
| 541 | 541 | ||
| 542 | /* | 542 | /* |
diff --git a/drivers/scsi/ufs/ufshcd.c b/drivers/scsi/ufs/ufshcd.c index a355d989b414..c7da2c185990 100644 --- a/drivers/scsi/ufs/ufshcd.c +++ b/drivers/scsi/ufs/ufshcd.c | |||
| @@ -4352,6 +4352,8 @@ static int ufshcd_slave_alloc(struct scsi_device *sdev) | |||
| 4352 | /* REPORT SUPPORTED OPERATION CODES is not supported */ | 4352 | /* REPORT SUPPORTED OPERATION CODES is not supported */ |
| 4353 | sdev->no_report_opcodes = 1; | 4353 | sdev->no_report_opcodes = 1; |
| 4354 | 4354 | ||
| 4355 | /* WRITE_SAME command is not supported */ | ||
| 4356 | sdev->no_write_same = 1; | ||
| 4355 | 4357 | ||
| 4356 | ufshcd_set_queue_depth(sdev); | 4358 | ufshcd_set_queue_depth(sdev); |
| 4357 | 4359 | ||
diff --git a/drivers/soc/imx/gpc.c b/drivers/soc/imx/gpc.c index 53f7275d6cbd..cfb42f5eccb2 100644 --- a/drivers/soc/imx/gpc.c +++ b/drivers/soc/imx/gpc.c | |||
| @@ -348,7 +348,7 @@ static int imx_gpc_old_dt_init(struct device *dev, struct regmap *regmap, | |||
| 348 | if (i == 1) { | 348 | if (i == 1) { |
| 349 | domain->supply = devm_regulator_get(dev, "pu"); | 349 | domain->supply = devm_regulator_get(dev, "pu"); |
| 350 | if (IS_ERR(domain->supply)) | 350 | if (IS_ERR(domain->supply)) |
| 351 | return PTR_ERR(domain->supply);; | 351 | return PTR_ERR(domain->supply); |
| 352 | 352 | ||
| 353 | ret = imx_pgc_get_clocks(dev, domain); | 353 | ret = imx_pgc_get_clocks(dev, domain); |
| 354 | if (ret) | 354 | if (ret) |
diff --git a/drivers/staging/android/ashmem.c b/drivers/staging/android/ashmem.c index bbdc53b686dd..6dbba5aff191 100644 --- a/drivers/staging/android/ashmem.c +++ b/drivers/staging/android/ashmem.c | |||
| @@ -702,30 +702,32 @@ static int ashmem_pin_unpin(struct ashmem_area *asma, unsigned long cmd, | |||
| 702 | size_t pgstart, pgend; | 702 | size_t pgstart, pgend; |
| 703 | int ret = -EINVAL; | 703 | int ret = -EINVAL; |
| 704 | 704 | ||
| 705 | mutex_lock(&ashmem_mutex); | ||
| 706 | |||
| 705 | if (unlikely(!asma->file)) | 707 | if (unlikely(!asma->file)) |
| 706 | return -EINVAL; | 708 | goto out_unlock; |
| 707 | 709 | ||
| 708 | if (unlikely(copy_from_user(&pin, p, sizeof(pin)))) | 710 | if (unlikely(copy_from_user(&pin, p, sizeof(pin)))) { |
| 709 | return -EFAULT; | 711 | ret = -EFAULT; |
| 712 | goto out_unlock; | ||
| 713 | } | ||
| 710 | 714 | ||
| 711 | /* per custom, you can pass zero for len to mean "everything onward" */ | 715 | /* per custom, you can pass zero for len to mean "everything onward" */ |
| 712 | if (!pin.len) | 716 | if (!pin.len) |
| 713 | pin.len = PAGE_ALIGN(asma->size) - pin.offset; | 717 | pin.len = PAGE_ALIGN(asma->size) - pin.offset; |
| 714 | 718 | ||
| 715 | if (unlikely((pin.offset | pin.len) & ~PAGE_MASK)) | 719 | if (unlikely((pin.offset | pin.len) & ~PAGE_MASK)) |
| 716 | return -EINVAL; | 720 | goto out_unlock; |
| 717 | 721 | ||
| 718 | if (unlikely(((__u32)-1) - pin.offset < pin.len)) | 722 | if (unlikely(((__u32)-1) - pin.offset < pin.len)) |
| 719 | return -EINVAL; | 723 | goto out_unlock; |
| 720 | 724 | ||
| 721 | if (unlikely(PAGE_ALIGN(asma->size) < pin.offset + pin.len)) | 725 | if (unlikely(PAGE_ALIGN(asma->size) < pin.offset + pin.len)) |
| 722 | return -EINVAL; | 726 | goto out_unlock; |
| 723 | 727 | ||
| 724 | pgstart = pin.offset / PAGE_SIZE; | 728 | pgstart = pin.offset / PAGE_SIZE; |
| 725 | pgend = pgstart + (pin.len / PAGE_SIZE) - 1; | 729 | pgend = pgstart + (pin.len / PAGE_SIZE) - 1; |
| 726 | 730 | ||
| 727 | mutex_lock(&ashmem_mutex); | ||
| 728 | |||
| 729 | switch (cmd) { | 731 | switch (cmd) { |
| 730 | case ASHMEM_PIN: | 732 | case ASHMEM_PIN: |
| 731 | ret = ashmem_pin(asma, pgstart, pgend); | 733 | ret = ashmem_pin(asma, pgstart, pgend); |
| @@ -738,6 +740,7 @@ static int ashmem_pin_unpin(struct ashmem_area *asma, unsigned long cmd, | |||
| 738 | break; | 740 | break; |
| 739 | } | 741 | } |
| 740 | 742 | ||
| 743 | out_unlock: | ||
| 741 | mutex_unlock(&ashmem_mutex); | 744 | mutex_unlock(&ashmem_mutex); |
| 742 | 745 | ||
| 743 | return ret; | 746 | return ret; |
diff --git a/drivers/staging/android/ion/ion_cma_heap.c b/drivers/staging/android/ion/ion_cma_heap.c index 94e06925c712..49718c96bf9e 100644 --- a/drivers/staging/android/ion/ion_cma_heap.c +++ b/drivers/staging/android/ion/ion_cma_heap.c | |||
| @@ -12,6 +12,7 @@ | |||
| 12 | #include <linux/err.h> | 12 | #include <linux/err.h> |
| 13 | #include <linux/cma.h> | 13 | #include <linux/cma.h> |
| 14 | #include <linux/scatterlist.h> | 14 | #include <linux/scatterlist.h> |
| 15 | #include <linux/highmem.h> | ||
| 15 | 16 | ||
| 16 | #include "ion.h" | 17 | #include "ion.h" |
| 17 | 18 | ||
| @@ -42,6 +43,22 @@ static int ion_cma_allocate(struct ion_heap *heap, struct ion_buffer *buffer, | |||
| 42 | if (!pages) | 43 | if (!pages) |
| 43 | return -ENOMEM; | 44 | return -ENOMEM; |
| 44 | 45 | ||
| 46 | if (PageHighMem(pages)) { | ||
| 47 | unsigned long nr_clear_pages = nr_pages; | ||
| 48 | struct page *page = pages; | ||
| 49 | |||
| 50 | while (nr_clear_pages > 0) { | ||
| 51 | void *vaddr = kmap_atomic(page); | ||
| 52 | |||
| 53 | memset(vaddr, 0, PAGE_SIZE); | ||
| 54 | kunmap_atomic(vaddr); | ||
| 55 | page++; | ||
| 56 | nr_clear_pages--; | ||
| 57 | } | ||
| 58 | } else { | ||
| 59 | memset(page_address(pages), 0, size); | ||
| 60 | } | ||
| 61 | |||
| 45 | table = kmalloc(sizeof(*table), GFP_KERNEL); | 62 | table = kmalloc(sizeof(*table), GFP_KERNEL); |
| 46 | if (!table) | 63 | if (!table) |
| 47 | goto err; | 64 | goto err; |
diff --git a/drivers/staging/fsl-mc/bus/Kconfig b/drivers/staging/fsl-mc/bus/Kconfig index 1f9100049176..b35ef7ee6901 100644 --- a/drivers/staging/fsl-mc/bus/Kconfig +++ b/drivers/staging/fsl-mc/bus/Kconfig | |||
| @@ -7,7 +7,7 @@ | |||
| 7 | 7 | ||
| 8 | config FSL_MC_BUS | 8 | config FSL_MC_BUS |
| 9 | bool "QorIQ DPAA2 fsl-mc bus driver" | 9 | bool "QorIQ DPAA2 fsl-mc bus driver" |
| 10 | depends on OF && (ARCH_LAYERSCAPE || (COMPILE_TEST && (ARM || ARM64 || X86 || PPC))) | 10 | depends on OF && (ARCH_LAYERSCAPE || (COMPILE_TEST && (ARM || ARM64 || X86_LOCAL_APIC || PPC))) |
| 11 | select GENERIC_MSI_IRQ_DOMAIN | 11 | select GENERIC_MSI_IRQ_DOMAIN |
| 12 | help | 12 | help |
| 13 | Driver to enable the bus infrastructure for the QorIQ DPAA2 | 13 | Driver to enable the bus infrastructure for the QorIQ DPAA2 |
diff --git a/drivers/staging/fsl-mc/bus/irq-gic-v3-its-fsl-mc-msi.c b/drivers/staging/fsl-mc/bus/irq-gic-v3-its-fsl-mc-msi.c index 5064d5ddf581..fc2013aade51 100644 --- a/drivers/staging/fsl-mc/bus/irq-gic-v3-its-fsl-mc-msi.c +++ b/drivers/staging/fsl-mc/bus/irq-gic-v3-its-fsl-mc-msi.c | |||
| @@ -73,6 +73,8 @@ static int __init its_fsl_mc_msi_init(void) | |||
| 73 | 73 | ||
| 74 | for (np = of_find_matching_node(NULL, its_device_id); np; | 74 | for (np = of_find_matching_node(NULL, its_device_id); np; |
| 75 | np = of_find_matching_node(np, its_device_id)) { | 75 | np = of_find_matching_node(np, its_device_id)) { |
| 76 | if (!of_device_is_available(np)) | ||
| 77 | continue; | ||
| 76 | if (!of_property_read_bool(np, "msi-controller")) | 78 | if (!of_property_read_bool(np, "msi-controller")) |
| 77 | continue; | 79 | continue; |
| 78 | 80 | ||
diff --git a/drivers/staging/iio/adc/ad7192.c b/drivers/staging/iio/adc/ad7192.c index f01595593ce2..425e8b82533b 100644 --- a/drivers/staging/iio/adc/ad7192.c +++ b/drivers/staging/iio/adc/ad7192.c | |||
| @@ -141,6 +141,8 @@ | |||
| 141 | #define AD7192_GPOCON_P1DAT BIT(1) /* P1 state */ | 141 | #define AD7192_GPOCON_P1DAT BIT(1) /* P1 state */ |
| 142 | #define AD7192_GPOCON_P0DAT BIT(0) /* P0 state */ | 142 | #define AD7192_GPOCON_P0DAT BIT(0) /* P0 state */ |
| 143 | 143 | ||
| 144 | #define AD7192_EXT_FREQ_MHZ_MIN 2457600 | ||
| 145 | #define AD7192_EXT_FREQ_MHZ_MAX 5120000 | ||
| 144 | #define AD7192_INT_FREQ_MHZ 4915200 | 146 | #define AD7192_INT_FREQ_MHZ 4915200 |
| 145 | 147 | ||
| 146 | /* NOTE: | 148 | /* NOTE: |
| @@ -218,6 +220,12 @@ static int ad7192_calibrate_all(struct ad7192_state *st) | |||
| 218 | ARRAY_SIZE(ad7192_calib_arr)); | 220 | ARRAY_SIZE(ad7192_calib_arr)); |
| 219 | } | 221 | } |
| 220 | 222 | ||
| 223 | static inline bool ad7192_valid_external_frequency(u32 freq) | ||
| 224 | { | ||
| 225 | return (freq >= AD7192_EXT_FREQ_MHZ_MIN && | ||
| 226 | freq <= AD7192_EXT_FREQ_MHZ_MAX); | ||
| 227 | } | ||
| 228 | |||
| 221 | static int ad7192_setup(struct ad7192_state *st, | 229 | static int ad7192_setup(struct ad7192_state *st, |
| 222 | const struct ad7192_platform_data *pdata) | 230 | const struct ad7192_platform_data *pdata) |
| 223 | { | 231 | { |
| @@ -243,17 +251,20 @@ static int ad7192_setup(struct ad7192_state *st, | |||
| 243 | id); | 251 | id); |
| 244 | 252 | ||
| 245 | switch (pdata->clock_source_sel) { | 253 | switch (pdata->clock_source_sel) { |
| 246 | case AD7192_CLK_EXT_MCLK1_2: | ||
| 247 | case AD7192_CLK_EXT_MCLK2: | ||
| 248 | st->mclk = AD7192_INT_FREQ_MHZ; | ||
| 249 | break; | ||
| 250 | case AD7192_CLK_INT: | 254 | case AD7192_CLK_INT: |
| 251 | case AD7192_CLK_INT_CO: | 255 | case AD7192_CLK_INT_CO: |
| 252 | if (pdata->ext_clk_hz) | 256 | st->mclk = AD7192_INT_FREQ_MHZ; |
| 253 | st->mclk = pdata->ext_clk_hz; | ||
| 254 | else | ||
| 255 | st->mclk = AD7192_INT_FREQ_MHZ; | ||
| 256 | break; | 257 | break; |
| 258 | case AD7192_CLK_EXT_MCLK1_2: | ||
| 259 | case AD7192_CLK_EXT_MCLK2: | ||
| 260 | if (ad7192_valid_external_frequency(pdata->ext_clk_hz)) { | ||
| 261 | st->mclk = pdata->ext_clk_hz; | ||
| 262 | break; | ||
| 263 | } | ||
| 264 | dev_err(&st->sd.spi->dev, "Invalid frequency setting %u\n", | ||
| 265 | pdata->ext_clk_hz); | ||
| 266 | ret = -EINVAL; | ||
| 267 | goto out; | ||
| 257 | default: | 268 | default: |
| 258 | ret = -EINVAL; | 269 | ret = -EINVAL; |
| 259 | goto out; | 270 | goto out; |
diff --git a/drivers/staging/iio/impedance-analyzer/ad5933.c b/drivers/staging/iio/impedance-analyzer/ad5933.c index 2b28fb9c0048..3bcf49466361 100644 --- a/drivers/staging/iio/impedance-analyzer/ad5933.c +++ b/drivers/staging/iio/impedance-analyzer/ad5933.c | |||
| @@ -648,8 +648,6 @@ static int ad5933_register_ring_funcs_and_init(struct iio_dev *indio_dev) | |||
| 648 | /* Ring buffer functions - here trigger setup related */ | 648 | /* Ring buffer functions - here trigger setup related */ |
| 649 | indio_dev->setup_ops = &ad5933_ring_setup_ops; | 649 | indio_dev->setup_ops = &ad5933_ring_setup_ops; |
| 650 | 650 | ||
| 651 | indio_dev->modes |= INDIO_BUFFER_HARDWARE; | ||
| 652 | |||
| 653 | return 0; | 651 | return 0; |
| 654 | } | 652 | } |
| 655 | 653 | ||
| @@ -762,7 +760,7 @@ static int ad5933_probe(struct i2c_client *client, | |||
| 762 | indio_dev->dev.parent = &client->dev; | 760 | indio_dev->dev.parent = &client->dev; |
| 763 | indio_dev->info = &ad5933_info; | 761 | indio_dev->info = &ad5933_info; |
| 764 | indio_dev->name = id->name; | 762 | indio_dev->name = id->name; |
| 765 | indio_dev->modes = INDIO_DIRECT_MODE; | 763 | indio_dev->modes = (INDIO_BUFFER_SOFTWARE | INDIO_DIRECT_MODE); |
| 766 | indio_dev->channels = ad5933_channels; | 764 | indio_dev->channels = ad5933_channels; |
| 767 | indio_dev->num_channels = ARRAY_SIZE(ad5933_channels); | 765 | indio_dev->num_channels = ARRAY_SIZE(ad5933_channels); |
| 768 | 766 | ||
diff --git a/drivers/usb/Kconfig b/drivers/usb/Kconfig index f699abab1787..148f3ee70286 100644 --- a/drivers/usb/Kconfig +++ b/drivers/usb/Kconfig | |||
| @@ -19,6 +19,12 @@ config USB_EHCI_BIG_ENDIAN_MMIO | |||
| 19 | config USB_EHCI_BIG_ENDIAN_DESC | 19 | config USB_EHCI_BIG_ENDIAN_DESC |
| 20 | bool | 20 | bool |
| 21 | 21 | ||
| 22 | config USB_UHCI_BIG_ENDIAN_MMIO | ||
| 23 | bool | ||
| 24 | |||
| 25 | config USB_UHCI_BIG_ENDIAN_DESC | ||
| 26 | bool | ||
| 27 | |||
| 22 | menuconfig USB_SUPPORT | 28 | menuconfig USB_SUPPORT |
| 23 | bool "USB support" | 29 | bool "USB support" |
| 24 | depends on HAS_IOMEM | 30 | depends on HAS_IOMEM |
diff --git a/drivers/usb/class/cdc-acm.c b/drivers/usb/class/cdc-acm.c index 06b3b54a0e68..7b366a6c0b49 100644 --- a/drivers/usb/class/cdc-acm.c +++ b/drivers/usb/class/cdc-acm.c | |||
| @@ -174,6 +174,7 @@ static int acm_wb_alloc(struct acm *acm) | |||
| 174 | wb = &acm->wb[wbn]; | 174 | wb = &acm->wb[wbn]; |
| 175 | if (!wb->use) { | 175 | if (!wb->use) { |
| 176 | wb->use = 1; | 176 | wb->use = 1; |
| 177 | wb->len = 0; | ||
| 177 | return wbn; | 178 | return wbn; |
| 178 | } | 179 | } |
| 179 | wbn = (wbn + 1) % ACM_NW; | 180 | wbn = (wbn + 1) % ACM_NW; |
| @@ -805,16 +806,18 @@ static int acm_tty_write(struct tty_struct *tty, | |||
| 805 | static void acm_tty_flush_chars(struct tty_struct *tty) | 806 | static void acm_tty_flush_chars(struct tty_struct *tty) |
| 806 | { | 807 | { |
| 807 | struct acm *acm = tty->driver_data; | 808 | struct acm *acm = tty->driver_data; |
| 808 | struct acm_wb *cur = acm->putbuffer; | 809 | struct acm_wb *cur; |
| 809 | int err; | 810 | int err; |
| 810 | unsigned long flags; | 811 | unsigned long flags; |
| 811 | 812 | ||
| 813 | spin_lock_irqsave(&acm->write_lock, flags); | ||
| 814 | |||
| 815 | cur = acm->putbuffer; | ||
| 812 | if (!cur) /* nothing to do */ | 816 | if (!cur) /* nothing to do */ |
| 813 | return; | 817 | goto out; |
| 814 | 818 | ||
| 815 | acm->putbuffer = NULL; | 819 | acm->putbuffer = NULL; |
| 816 | err = usb_autopm_get_interface_async(acm->control); | 820 | err = usb_autopm_get_interface_async(acm->control); |
| 817 | spin_lock_irqsave(&acm->write_lock, flags); | ||
| 818 | if (err < 0) { | 821 | if (err < 0) { |
| 819 | cur->use = 0; | 822 | cur->use = 0; |
| 820 | acm->putbuffer = cur; | 823 | acm->putbuffer = cur; |
diff --git a/drivers/usb/core/quirks.c b/drivers/usb/core/quirks.c index 4024926c1d68..f4a548471f0f 100644 --- a/drivers/usb/core/quirks.c +++ b/drivers/usb/core/quirks.c | |||
| @@ -226,6 +226,9 @@ static const struct usb_device_id usb_quirk_list[] = { | |||
| 226 | { USB_DEVICE(0x1a0a, 0x0200), .driver_info = | 226 | { USB_DEVICE(0x1a0a, 0x0200), .driver_info = |
| 227 | USB_QUIRK_LINEAR_UFRAME_INTR_BINTERVAL }, | 227 | USB_QUIRK_LINEAR_UFRAME_INTR_BINTERVAL }, |
| 228 | 228 | ||
| 229 | /* Corsair K70 RGB */ | ||
| 230 | { USB_DEVICE(0x1b1c, 0x1b13), .driver_info = USB_QUIRK_DELAY_INIT }, | ||
| 231 | |||
| 229 | /* Corsair Strafe RGB */ | 232 | /* Corsair Strafe RGB */ |
| 230 | { USB_DEVICE(0x1b1c, 0x1b20), .driver_info = USB_QUIRK_DELAY_INIT }, | 233 | { USB_DEVICE(0x1b1c, 0x1b20), .driver_info = USB_QUIRK_DELAY_INIT }, |
| 231 | 234 | ||
diff --git a/drivers/usb/dwc2/gadget.c b/drivers/usb/dwc2/gadget.c index e4c3ce0de5de..5bcad1d869b5 100644 --- a/drivers/usb/dwc2/gadget.c +++ b/drivers/usb/dwc2/gadget.c | |||
| @@ -1917,7 +1917,9 @@ static void dwc2_hsotg_program_zlp(struct dwc2_hsotg *hsotg, | |||
| 1917 | /* Not specific buffer needed for ep0 ZLP */ | 1917 | /* Not specific buffer needed for ep0 ZLP */ |
| 1918 | dma_addr_t dma = hs_ep->desc_list_dma; | 1918 | dma_addr_t dma = hs_ep->desc_list_dma; |
| 1919 | 1919 | ||
| 1920 | dwc2_gadget_set_ep0_desc_chain(hsotg, hs_ep); | 1920 | if (!index) |
| 1921 | dwc2_gadget_set_ep0_desc_chain(hsotg, hs_ep); | ||
| 1922 | |||
| 1921 | dwc2_gadget_config_nonisoc_xfer_ddma(hs_ep, dma, 0); | 1923 | dwc2_gadget_config_nonisoc_xfer_ddma(hs_ep, dma, 0); |
| 1922 | } else { | 1924 | } else { |
| 1923 | dwc2_writel(DXEPTSIZ_MC(1) | DXEPTSIZ_PKTCNT(1) | | 1925 | dwc2_writel(DXEPTSIZ_MC(1) | DXEPTSIZ_PKTCNT(1) | |
| @@ -2974,9 +2976,13 @@ static void dwc2_hsotg_epint(struct dwc2_hsotg *hsotg, unsigned int idx, | |||
| 2974 | if (ints & DXEPINT_STSPHSERCVD) { | 2976 | if (ints & DXEPINT_STSPHSERCVD) { |
| 2975 | dev_dbg(hsotg->dev, "%s: StsPhseRcvd\n", __func__); | 2977 | dev_dbg(hsotg->dev, "%s: StsPhseRcvd\n", __func__); |
| 2976 | 2978 | ||
| 2977 | /* Move to STATUS IN for DDMA */ | 2979 | /* Safety check EP0 state when STSPHSERCVD asserted */ |
| 2978 | if (using_desc_dma(hsotg)) | 2980 | if (hsotg->ep0_state == DWC2_EP0_DATA_OUT) { |
| 2979 | dwc2_hsotg_ep0_zlp(hsotg, true); | 2981 | /* Move to STATUS IN for DDMA */ |
| 2982 | if (using_desc_dma(hsotg)) | ||
| 2983 | dwc2_hsotg_ep0_zlp(hsotg, true); | ||
| 2984 | } | ||
| 2985 | |||
| 2980 | } | 2986 | } |
| 2981 | 2987 | ||
| 2982 | if (ints & DXEPINT_BACK2BACKSETUP) | 2988 | if (ints & DXEPINT_BACK2BACKSETUP) |
| @@ -3375,12 +3381,6 @@ void dwc2_hsotg_core_init_disconnected(struct dwc2_hsotg *hsotg, | |||
| 3375 | dwc2_writel(dwc2_hsotg_ep0_mps(hsotg->eps_out[0]->ep.maxpacket) | | 3381 | dwc2_writel(dwc2_hsotg_ep0_mps(hsotg->eps_out[0]->ep.maxpacket) | |
| 3376 | DXEPCTL_USBACTEP, hsotg->regs + DIEPCTL0); | 3382 | DXEPCTL_USBACTEP, hsotg->regs + DIEPCTL0); |
| 3377 | 3383 | ||
| 3378 | dwc2_hsotg_enqueue_setup(hsotg); | ||
| 3379 | |||
| 3380 | dev_dbg(hsotg->dev, "EP0: DIEPCTL0=0x%08x, DOEPCTL0=0x%08x\n", | ||
| 3381 | dwc2_readl(hsotg->regs + DIEPCTL0), | ||
| 3382 | dwc2_readl(hsotg->regs + DOEPCTL0)); | ||
| 3383 | |||
| 3384 | /* clear global NAKs */ | 3384 | /* clear global NAKs */ |
| 3385 | val = DCTL_CGOUTNAK | DCTL_CGNPINNAK; | 3385 | val = DCTL_CGOUTNAK | DCTL_CGNPINNAK; |
| 3386 | if (!is_usb_reset) | 3386 | if (!is_usb_reset) |
| @@ -3391,6 +3391,12 @@ void dwc2_hsotg_core_init_disconnected(struct dwc2_hsotg *hsotg, | |||
| 3391 | mdelay(3); | 3391 | mdelay(3); |
| 3392 | 3392 | ||
| 3393 | hsotg->lx_state = DWC2_L0; | 3393 | hsotg->lx_state = DWC2_L0; |
| 3394 | |||
| 3395 | dwc2_hsotg_enqueue_setup(hsotg); | ||
| 3396 | |||
| 3397 | dev_dbg(hsotg->dev, "EP0: DIEPCTL0=0x%08x, DOEPCTL0=0x%08x\n", | ||
| 3398 | dwc2_readl(hsotg->regs + DIEPCTL0), | ||
| 3399 | dwc2_readl(hsotg->regs + DOEPCTL0)); | ||
| 3394 | } | 3400 | } |
| 3395 | 3401 | ||
| 3396 | static void dwc2_hsotg_core_disconnect(struct dwc2_hsotg *hsotg) | 3402 | static void dwc2_hsotg_core_disconnect(struct dwc2_hsotg *hsotg) |
diff --git a/drivers/usb/dwc3/core.c b/drivers/usb/dwc3/core.c index ade2ab00d37a..f1d838a4acd6 100644 --- a/drivers/usb/dwc3/core.c +++ b/drivers/usb/dwc3/core.c | |||
| @@ -100,6 +100,8 @@ static void dwc3_set_prtcap(struct dwc3 *dwc, u32 mode) | |||
| 100 | reg &= ~(DWC3_GCTL_PRTCAPDIR(DWC3_GCTL_PRTCAP_OTG)); | 100 | reg &= ~(DWC3_GCTL_PRTCAPDIR(DWC3_GCTL_PRTCAP_OTG)); |
| 101 | reg |= DWC3_GCTL_PRTCAPDIR(mode); | 101 | reg |= DWC3_GCTL_PRTCAPDIR(mode); |
| 102 | dwc3_writel(dwc->regs, DWC3_GCTL, reg); | 102 | dwc3_writel(dwc->regs, DWC3_GCTL, reg); |
| 103 | |||
| 104 | dwc->current_dr_role = mode; | ||
| 103 | } | 105 | } |
| 104 | 106 | ||
| 105 | static void __dwc3_set_mode(struct work_struct *work) | 107 | static void __dwc3_set_mode(struct work_struct *work) |
| @@ -133,8 +135,6 @@ static void __dwc3_set_mode(struct work_struct *work) | |||
| 133 | 135 | ||
| 134 | dwc3_set_prtcap(dwc, dwc->desired_dr_role); | 136 | dwc3_set_prtcap(dwc, dwc->desired_dr_role); |
| 135 | 137 | ||
| 136 | dwc->current_dr_role = dwc->desired_dr_role; | ||
| 137 | |||
| 138 | spin_unlock_irqrestore(&dwc->lock, flags); | 138 | spin_unlock_irqrestore(&dwc->lock, flags); |
| 139 | 139 | ||
| 140 | switch (dwc->desired_dr_role) { | 140 | switch (dwc->desired_dr_role) { |
| @@ -219,7 +219,7 @@ static int dwc3_core_soft_reset(struct dwc3 *dwc) | |||
| 219 | * XHCI driver will reset the host block. If dwc3 was configured for | 219 | * XHCI driver will reset the host block. If dwc3 was configured for |
| 220 | * host-only mode, then we can return early. | 220 | * host-only mode, then we can return early. |
| 221 | */ | 221 | */ |
| 222 | if (dwc->dr_mode == USB_DR_MODE_HOST) | 222 | if (dwc->current_dr_role == DWC3_GCTL_PRTCAP_HOST) |
| 223 | return 0; | 223 | return 0; |
| 224 | 224 | ||
| 225 | reg = dwc3_readl(dwc->regs, DWC3_DCTL); | 225 | reg = dwc3_readl(dwc->regs, DWC3_DCTL); |
| @@ -234,6 +234,9 @@ static int dwc3_core_soft_reset(struct dwc3 *dwc) | |||
| 234 | udelay(1); | 234 | udelay(1); |
| 235 | } while (--retries); | 235 | } while (--retries); |
| 236 | 236 | ||
| 237 | phy_exit(dwc->usb3_generic_phy); | ||
| 238 | phy_exit(dwc->usb2_generic_phy); | ||
| 239 | |||
| 237 | return -ETIMEDOUT; | 240 | return -ETIMEDOUT; |
| 238 | } | 241 | } |
| 239 | 242 | ||
| @@ -483,6 +486,22 @@ static void dwc3_cache_hwparams(struct dwc3 *dwc) | |||
| 483 | parms->hwparams8 = dwc3_readl(dwc->regs, DWC3_GHWPARAMS8); | 486 | parms->hwparams8 = dwc3_readl(dwc->regs, DWC3_GHWPARAMS8); |
| 484 | } | 487 | } |
| 485 | 488 | ||
| 489 | static int dwc3_core_ulpi_init(struct dwc3 *dwc) | ||
| 490 | { | ||
| 491 | int intf; | ||
| 492 | int ret = 0; | ||
| 493 | |||
| 494 | intf = DWC3_GHWPARAMS3_HSPHY_IFC(dwc->hwparams.hwparams3); | ||
| 495 | |||
| 496 | if (intf == DWC3_GHWPARAMS3_HSPHY_IFC_ULPI || | ||
| 497 | (intf == DWC3_GHWPARAMS3_HSPHY_IFC_UTMI_ULPI && | ||
| 498 | dwc->hsphy_interface && | ||
| 499 | !strncmp(dwc->hsphy_interface, "ulpi", 4))) | ||
| 500 | ret = dwc3_ulpi_init(dwc); | ||
| 501 | |||
| 502 | return ret; | ||
| 503 | } | ||
| 504 | |||
| 486 | /** | 505 | /** |
| 487 | * dwc3_phy_setup - Configure USB PHY Interface of DWC3 Core | 506 | * dwc3_phy_setup - Configure USB PHY Interface of DWC3 Core |
| 488 | * @dwc: Pointer to our controller context structure | 507 | * @dwc: Pointer to our controller context structure |
| @@ -494,7 +513,6 @@ static void dwc3_cache_hwparams(struct dwc3 *dwc) | |||
| 494 | static int dwc3_phy_setup(struct dwc3 *dwc) | 513 | static int dwc3_phy_setup(struct dwc3 *dwc) |
| 495 | { | 514 | { |
| 496 | u32 reg; | 515 | u32 reg; |
| 497 | int ret; | ||
| 498 | 516 | ||
| 499 | reg = dwc3_readl(dwc->regs, DWC3_GUSB3PIPECTL(0)); | 517 | reg = dwc3_readl(dwc->regs, DWC3_GUSB3PIPECTL(0)); |
| 500 | 518 | ||
| @@ -565,9 +583,6 @@ static int dwc3_phy_setup(struct dwc3 *dwc) | |||
| 565 | } | 583 | } |
| 566 | /* FALLTHROUGH */ | 584 | /* FALLTHROUGH */ |
| 567 | case DWC3_GHWPARAMS3_HSPHY_IFC_ULPI: | 585 | case DWC3_GHWPARAMS3_HSPHY_IFC_ULPI: |
| 568 | ret = dwc3_ulpi_init(dwc); | ||
| 569 | if (ret) | ||
| 570 | return ret; | ||
| 571 | /* FALLTHROUGH */ | 586 | /* FALLTHROUGH */ |
| 572 | default: | 587 | default: |
| 573 | break; | 588 | break; |
| @@ -724,6 +739,7 @@ static void dwc3_core_setup_global_control(struct dwc3 *dwc) | |||
| 724 | } | 739 | } |
| 725 | 740 | ||
| 726 | static int dwc3_core_get_phy(struct dwc3 *dwc); | 741 | static int dwc3_core_get_phy(struct dwc3 *dwc); |
| 742 | static int dwc3_core_ulpi_init(struct dwc3 *dwc); | ||
| 727 | 743 | ||
| 728 | /** | 744 | /** |
| 729 | * dwc3_core_init - Low-level initialization of DWC3 Core | 745 | * dwc3_core_init - Low-level initialization of DWC3 Core |
| @@ -755,17 +771,27 @@ static int dwc3_core_init(struct dwc3 *dwc) | |||
| 755 | dwc->maximum_speed = USB_SPEED_HIGH; | 771 | dwc->maximum_speed = USB_SPEED_HIGH; |
| 756 | } | 772 | } |
| 757 | 773 | ||
| 758 | ret = dwc3_core_get_phy(dwc); | 774 | ret = dwc3_phy_setup(dwc); |
| 759 | if (ret) | 775 | if (ret) |
| 760 | goto err0; | 776 | goto err0; |
| 761 | 777 | ||
| 762 | ret = dwc3_core_soft_reset(dwc); | 778 | if (!dwc->ulpi_ready) { |
| 763 | if (ret) | 779 | ret = dwc3_core_ulpi_init(dwc); |
| 764 | goto err0; | 780 | if (ret) |
| 781 | goto err0; | ||
| 782 | dwc->ulpi_ready = true; | ||
| 783 | } | ||
| 765 | 784 | ||
| 766 | ret = dwc3_phy_setup(dwc); | 785 | if (!dwc->phys_ready) { |
| 786 | ret = dwc3_core_get_phy(dwc); | ||
| 787 | if (ret) | ||
| 788 | goto err0a; | ||
| 789 | dwc->phys_ready = true; | ||
| 790 | } | ||
| 791 | |||
| 792 | ret = dwc3_core_soft_reset(dwc); | ||
| 767 | if (ret) | 793 | if (ret) |
| 768 | goto err0; | 794 | goto err0a; |
| 769 | 795 | ||
| 770 | dwc3_core_setup_global_control(dwc); | 796 | dwc3_core_setup_global_control(dwc); |
| 771 | dwc3_core_num_eps(dwc); | 797 | dwc3_core_num_eps(dwc); |
| @@ -838,6 +864,9 @@ err1: | |||
| 838 | phy_exit(dwc->usb2_generic_phy); | 864 | phy_exit(dwc->usb2_generic_phy); |
| 839 | phy_exit(dwc->usb3_generic_phy); | 865 | phy_exit(dwc->usb3_generic_phy); |
| 840 | 866 | ||
| 867 | err0a: | ||
| 868 | dwc3_ulpi_exit(dwc); | ||
| 869 | |||
| 841 | err0: | 870 | err0: |
| 842 | return ret; | 871 | return ret; |
| 843 | } | 872 | } |
| @@ -916,7 +945,6 @@ static int dwc3_core_init_mode(struct dwc3 *dwc) | |||
| 916 | 945 | ||
| 917 | switch (dwc->dr_mode) { | 946 | switch (dwc->dr_mode) { |
| 918 | case USB_DR_MODE_PERIPHERAL: | 947 | case USB_DR_MODE_PERIPHERAL: |
| 919 | dwc->current_dr_role = DWC3_GCTL_PRTCAP_DEVICE; | ||
| 920 | dwc3_set_prtcap(dwc, DWC3_GCTL_PRTCAP_DEVICE); | 948 | dwc3_set_prtcap(dwc, DWC3_GCTL_PRTCAP_DEVICE); |
| 921 | 949 | ||
| 922 | if (dwc->usb2_phy) | 950 | if (dwc->usb2_phy) |
| @@ -932,7 +960,6 @@ static int dwc3_core_init_mode(struct dwc3 *dwc) | |||
| 932 | } | 960 | } |
| 933 | break; | 961 | break; |
| 934 | case USB_DR_MODE_HOST: | 962 | case USB_DR_MODE_HOST: |
| 935 | dwc->current_dr_role = DWC3_GCTL_PRTCAP_HOST; | ||
| 936 | dwc3_set_prtcap(dwc, DWC3_GCTL_PRTCAP_HOST); | 963 | dwc3_set_prtcap(dwc, DWC3_GCTL_PRTCAP_HOST); |
| 937 | 964 | ||
| 938 | if (dwc->usb2_phy) | 965 | if (dwc->usb2_phy) |
| @@ -1234,7 +1261,6 @@ err4: | |||
| 1234 | 1261 | ||
| 1235 | err3: | 1262 | err3: |
| 1236 | dwc3_free_event_buffers(dwc); | 1263 | dwc3_free_event_buffers(dwc); |
| 1237 | dwc3_ulpi_exit(dwc); | ||
| 1238 | 1264 | ||
| 1239 | err2: | 1265 | err2: |
| 1240 | pm_runtime_allow(&pdev->dev); | 1266 | pm_runtime_allow(&pdev->dev); |
| @@ -1284,7 +1310,7 @@ static int dwc3_remove(struct platform_device *pdev) | |||
| 1284 | } | 1310 | } |
| 1285 | 1311 | ||
| 1286 | #ifdef CONFIG_PM | 1312 | #ifdef CONFIG_PM |
| 1287 | static int dwc3_suspend_common(struct dwc3 *dwc) | 1313 | static int dwc3_suspend_common(struct dwc3 *dwc, pm_message_t msg) |
| 1288 | { | 1314 | { |
| 1289 | unsigned long flags; | 1315 | unsigned long flags; |
| 1290 | 1316 | ||
| @@ -1296,6 +1322,10 @@ static int dwc3_suspend_common(struct dwc3 *dwc) | |||
| 1296 | dwc3_core_exit(dwc); | 1322 | dwc3_core_exit(dwc); |
| 1297 | break; | 1323 | break; |
| 1298 | case DWC3_GCTL_PRTCAP_HOST: | 1324 | case DWC3_GCTL_PRTCAP_HOST: |
| 1325 | /* do nothing during host runtime_suspend */ | ||
| 1326 | if (!PMSG_IS_AUTO(msg)) | ||
| 1327 | dwc3_core_exit(dwc); | ||
| 1328 | break; | ||
| 1299 | default: | 1329 | default: |
| 1300 | /* do nothing */ | 1330 | /* do nothing */ |
| 1301 | break; | 1331 | break; |
| @@ -1304,7 +1334,7 @@ static int dwc3_suspend_common(struct dwc3 *dwc) | |||
| 1304 | return 0; | 1334 | return 0; |
| 1305 | } | 1335 | } |
| 1306 | 1336 | ||
| 1307 | static int dwc3_resume_common(struct dwc3 *dwc) | 1337 | static int dwc3_resume_common(struct dwc3 *dwc, pm_message_t msg) |
| 1308 | { | 1338 | { |
| 1309 | unsigned long flags; | 1339 | unsigned long flags; |
| 1310 | int ret; | 1340 | int ret; |
| @@ -1320,6 +1350,13 @@ static int dwc3_resume_common(struct dwc3 *dwc) | |||
| 1320 | spin_unlock_irqrestore(&dwc->lock, flags); | 1350 | spin_unlock_irqrestore(&dwc->lock, flags); |
| 1321 | break; | 1351 | break; |
| 1322 | case DWC3_GCTL_PRTCAP_HOST: | 1352 | case DWC3_GCTL_PRTCAP_HOST: |
| 1353 | /* nothing to do on host runtime_resume */ | ||
| 1354 | if (!PMSG_IS_AUTO(msg)) { | ||
| 1355 | ret = dwc3_core_init(dwc); | ||
| 1356 | if (ret) | ||
| 1357 | return ret; | ||
| 1358 | } | ||
| 1359 | break; | ||
| 1323 | default: | 1360 | default: |
| 1324 | /* do nothing */ | 1361 | /* do nothing */ |
| 1325 | break; | 1362 | break; |
| @@ -1331,12 +1368,11 @@ static int dwc3_resume_common(struct dwc3 *dwc) | |||
| 1331 | static int dwc3_runtime_checks(struct dwc3 *dwc) | 1368 | static int dwc3_runtime_checks(struct dwc3 *dwc) |
| 1332 | { | 1369 | { |
| 1333 | switch (dwc->current_dr_role) { | 1370 | switch (dwc->current_dr_role) { |
| 1334 | case USB_DR_MODE_PERIPHERAL: | 1371 | case DWC3_GCTL_PRTCAP_DEVICE: |
| 1335 | case USB_DR_MODE_OTG: | ||
| 1336 | if (dwc->connected) | 1372 | if (dwc->connected) |
| 1337 | return -EBUSY; | 1373 | return -EBUSY; |
| 1338 | break; | 1374 | break; |
| 1339 | case USB_DR_MODE_HOST: | 1375 | case DWC3_GCTL_PRTCAP_HOST: |
| 1340 | default: | 1376 | default: |
| 1341 | /* do nothing */ | 1377 | /* do nothing */ |
| 1342 | break; | 1378 | break; |
| @@ -1353,7 +1389,7 @@ static int dwc3_runtime_suspend(struct device *dev) | |||
| 1353 | if (dwc3_runtime_checks(dwc)) | 1389 | if (dwc3_runtime_checks(dwc)) |
| 1354 | return -EBUSY; | 1390 | return -EBUSY; |
| 1355 | 1391 | ||
| 1356 | ret = dwc3_suspend_common(dwc); | 1392 | ret = dwc3_suspend_common(dwc, PMSG_AUTO_SUSPEND); |
| 1357 | if (ret) | 1393 | if (ret) |
| 1358 | return ret; | 1394 | return ret; |
| 1359 | 1395 | ||
| @@ -1369,7 +1405,7 @@ static int dwc3_runtime_resume(struct device *dev) | |||
| 1369 | 1405 | ||
| 1370 | device_init_wakeup(dev, false); | 1406 | device_init_wakeup(dev, false); |
| 1371 | 1407 | ||
| 1372 | ret = dwc3_resume_common(dwc); | 1408 | ret = dwc3_resume_common(dwc, PMSG_AUTO_RESUME); |
| 1373 | if (ret) | 1409 | if (ret) |
| 1374 | return ret; | 1410 | return ret; |
| 1375 | 1411 | ||
| @@ -1416,7 +1452,7 @@ static int dwc3_suspend(struct device *dev) | |||
| 1416 | struct dwc3 *dwc = dev_get_drvdata(dev); | 1452 | struct dwc3 *dwc = dev_get_drvdata(dev); |
| 1417 | int ret; | 1453 | int ret; |
| 1418 | 1454 | ||
| 1419 | ret = dwc3_suspend_common(dwc); | 1455 | ret = dwc3_suspend_common(dwc, PMSG_SUSPEND); |
| 1420 | if (ret) | 1456 | if (ret) |
| 1421 | return ret; | 1457 | return ret; |
| 1422 | 1458 | ||
| @@ -1432,7 +1468,7 @@ static int dwc3_resume(struct device *dev) | |||
| 1432 | 1468 | ||
| 1433 | pinctrl_pm_select_default_state(dev); | 1469 | pinctrl_pm_select_default_state(dev); |
| 1434 | 1470 | ||
| 1435 | ret = dwc3_resume_common(dwc); | 1471 | ret = dwc3_resume_common(dwc, PMSG_RESUME); |
| 1436 | if (ret) | 1472 | if (ret) |
| 1437 | return ret; | 1473 | return ret; |
| 1438 | 1474 | ||
diff --git a/drivers/usb/dwc3/core.h b/drivers/usb/dwc3/core.h index 03c7aaaac926..860d2bc184d1 100644 --- a/drivers/usb/dwc3/core.h +++ b/drivers/usb/dwc3/core.h | |||
| @@ -158,13 +158,15 @@ | |||
| 158 | #define DWC3_GDBGFIFOSPACE_TYPE(n) (((n) << 5) & 0x1e0) | 158 | #define DWC3_GDBGFIFOSPACE_TYPE(n) (((n) << 5) & 0x1e0) |
| 159 | #define DWC3_GDBGFIFOSPACE_SPACE_AVAILABLE(n) (((n) >> 16) & 0xffff) | 159 | #define DWC3_GDBGFIFOSPACE_SPACE_AVAILABLE(n) (((n) >> 16) & 0xffff) |
| 160 | 160 | ||
| 161 | #define DWC3_TXFIFOQ 1 | 161 | #define DWC3_TXFIFOQ 0 |
| 162 | #define DWC3_RXFIFOQ 3 | 162 | #define DWC3_RXFIFOQ 1 |
| 163 | #define DWC3_TXREQQ 5 | 163 | #define DWC3_TXREQQ 2 |
| 164 | #define DWC3_RXREQQ 7 | 164 | #define DWC3_RXREQQ 3 |
| 165 | #define DWC3_RXINFOQ 9 | 165 | #define DWC3_RXINFOQ 4 |
| 166 | #define DWC3_DESCFETCHQ 13 | 166 | #define DWC3_PSTATQ 5 |
| 167 | #define DWC3_EVENTQ 15 | 167 | #define DWC3_DESCFETCHQ 6 |
| 168 | #define DWC3_EVENTQ 7 | ||
| 169 | #define DWC3_AUXEVENTQ 8 | ||
| 168 | 170 | ||
| 169 | /* Global RX Threshold Configuration Register */ | 171 | /* Global RX Threshold Configuration Register */ |
| 170 | #define DWC3_GRXTHRCFG_MAXRXBURSTSIZE(n) (((n) & 0x1f) << 19) | 172 | #define DWC3_GRXTHRCFG_MAXRXBURSTSIZE(n) (((n) & 0x1f) << 19) |
| @@ -795,7 +797,9 @@ struct dwc3_scratchpad_array { | |||
| 795 | * @usb3_phy: pointer to USB3 PHY | 797 | * @usb3_phy: pointer to USB3 PHY |
| 796 | * @usb2_generic_phy: pointer to USB2 PHY | 798 | * @usb2_generic_phy: pointer to USB2 PHY |
| 797 | * @usb3_generic_phy: pointer to USB3 PHY | 799 | * @usb3_generic_phy: pointer to USB3 PHY |
| 800 | * @phys_ready: flag to indicate that PHYs are ready | ||
| 798 | * @ulpi: pointer to ulpi interface | 801 | * @ulpi: pointer to ulpi interface |
| 802 | * @ulpi_ready: flag to indicate that ULPI is initialized | ||
| 799 | * @u2sel: parameter from Set SEL request. | 803 | * @u2sel: parameter from Set SEL request. |
| 800 | * @u2pel: parameter from Set SEL request. | 804 | * @u2pel: parameter from Set SEL request. |
| 801 | * @u1sel: parameter from Set SEL request. | 805 | * @u1sel: parameter from Set SEL request. |
| @@ -893,7 +897,10 @@ struct dwc3 { | |||
| 893 | struct phy *usb2_generic_phy; | 897 | struct phy *usb2_generic_phy; |
| 894 | struct phy *usb3_generic_phy; | 898 | struct phy *usb3_generic_phy; |
| 895 | 899 | ||
| 900 | bool phys_ready; | ||
| 901 | |||
| 896 | struct ulpi *ulpi; | 902 | struct ulpi *ulpi; |
| 903 | bool ulpi_ready; | ||
| 897 | 904 | ||
| 898 | void __iomem *regs; | 905 | void __iomem *regs; |
| 899 | size_t regs_size; | 906 | size_t regs_size; |
diff --git a/drivers/usb/dwc3/dwc3-of-simple.c b/drivers/usb/dwc3/dwc3-of-simple.c index 7ae0eefc7cc7..e54c3622eb28 100644 --- a/drivers/usb/dwc3/dwc3-of-simple.c +++ b/drivers/usb/dwc3/dwc3-of-simple.c | |||
| @@ -143,6 +143,7 @@ static int dwc3_of_simple_remove(struct platform_device *pdev) | |||
| 143 | clk_disable_unprepare(simple->clks[i]); | 143 | clk_disable_unprepare(simple->clks[i]); |
| 144 | clk_put(simple->clks[i]); | 144 | clk_put(simple->clks[i]); |
| 145 | } | 145 | } |
| 146 | simple->num_clocks = 0; | ||
| 146 | 147 | ||
| 147 | reset_control_assert(simple->resets); | 148 | reset_control_assert(simple->resets); |
| 148 | reset_control_put(simple->resets); | 149 | reset_control_put(simple->resets); |
diff --git a/drivers/usb/dwc3/dwc3-omap.c b/drivers/usb/dwc3/dwc3-omap.c index a4719e853b85..ed8b86517675 100644 --- a/drivers/usb/dwc3/dwc3-omap.c +++ b/drivers/usb/dwc3/dwc3-omap.c | |||
| @@ -582,9 +582,25 @@ static int dwc3_omap_resume(struct device *dev) | |||
| 582 | return 0; | 582 | return 0; |
| 583 | } | 583 | } |
| 584 | 584 | ||
| 585 | static void dwc3_omap_complete(struct device *dev) | ||
| 586 | { | ||
| 587 | struct dwc3_omap *omap = dev_get_drvdata(dev); | ||
| 588 | |||
| 589 | if (extcon_get_state(omap->edev, EXTCON_USB)) | ||
| 590 | dwc3_omap_set_mailbox(omap, OMAP_DWC3_VBUS_VALID); | ||
| 591 | else | ||
| 592 | dwc3_omap_set_mailbox(omap, OMAP_DWC3_VBUS_OFF); | ||
| 593 | |||
| 594 | if (extcon_get_state(omap->edev, EXTCON_USB_HOST)) | ||
| 595 | dwc3_omap_set_mailbox(omap, OMAP_DWC3_ID_GROUND); | ||
| 596 | else | ||
| 597 | dwc3_omap_set_mailbox(omap, OMAP_DWC3_ID_FLOAT); | ||
| 598 | } | ||
| 599 | |||
| 585 | static const struct dev_pm_ops dwc3_omap_dev_pm_ops = { | 600 | static const struct dev_pm_ops dwc3_omap_dev_pm_ops = { |
| 586 | 601 | ||
| 587 | SET_SYSTEM_SLEEP_PM_OPS(dwc3_omap_suspend, dwc3_omap_resume) | 602 | SET_SYSTEM_SLEEP_PM_OPS(dwc3_omap_suspend, dwc3_omap_resume) |
| 603 | .complete = dwc3_omap_complete, | ||
| 588 | }; | 604 | }; |
| 589 | 605 | ||
| 590 | #define DEV_PM_OPS (&dwc3_omap_dev_pm_ops) | 606 | #define DEV_PM_OPS (&dwc3_omap_dev_pm_ops) |
diff --git a/drivers/usb/dwc3/ep0.c b/drivers/usb/dwc3/ep0.c index 9c2e4a17918e..18be31d5743a 100644 --- a/drivers/usb/dwc3/ep0.c +++ b/drivers/usb/dwc3/ep0.c | |||
| @@ -854,7 +854,12 @@ static void dwc3_ep0_complete_data(struct dwc3 *dwc, | |||
| 854 | trb++; | 854 | trb++; |
| 855 | trb->ctrl &= ~DWC3_TRB_CTRL_HWO; | 855 | trb->ctrl &= ~DWC3_TRB_CTRL_HWO; |
| 856 | trace_dwc3_complete_trb(ep0, trb); | 856 | trace_dwc3_complete_trb(ep0, trb); |
| 857 | ep0->trb_enqueue = 0; | 857 | |
| 858 | if (r->direction) | ||
| 859 | dwc->eps[1]->trb_enqueue = 0; | ||
| 860 | else | ||
| 861 | dwc->eps[0]->trb_enqueue = 0; | ||
| 862 | |||
| 858 | dwc->ep0_bounced = false; | 863 | dwc->ep0_bounced = false; |
| 859 | } | 864 | } |
| 860 | 865 | ||
diff --git a/drivers/usb/dwc3/gadget.c b/drivers/usb/dwc3/gadget.c index 616ef49ccb49..2bda4eb1e9ac 100644 --- a/drivers/usb/dwc3/gadget.c +++ b/drivers/usb/dwc3/gadget.c | |||
| @@ -2745,6 +2745,8 @@ static void dwc3_gadget_conndone_interrupt(struct dwc3 *dwc) | |||
| 2745 | break; | 2745 | break; |
| 2746 | } | 2746 | } |
| 2747 | 2747 | ||
| 2748 | dwc->eps[1]->endpoint.maxpacket = dwc->gadget.ep0->maxpacket; | ||
| 2749 | |||
| 2748 | /* Enable USB2 LPM Capability */ | 2750 | /* Enable USB2 LPM Capability */ |
| 2749 | 2751 | ||
| 2750 | if ((dwc->revision > DWC3_REVISION_194A) && | 2752 | if ((dwc->revision > DWC3_REVISION_194A) && |
diff --git a/drivers/usb/gadget/function/f_fs.c b/drivers/usb/gadget/function/f_fs.c index 8f2cf3baa19c..c2592d883f67 100644 --- a/drivers/usb/gadget/function/f_fs.c +++ b/drivers/usb/gadget/function/f_fs.c | |||
| @@ -1855,44 +1855,20 @@ static int ffs_func_eps_enable(struct ffs_function *func) | |||
| 1855 | 1855 | ||
| 1856 | spin_lock_irqsave(&func->ffs->eps_lock, flags); | 1856 | spin_lock_irqsave(&func->ffs->eps_lock, flags); |
| 1857 | while(count--) { | 1857 | while(count--) { |
| 1858 | struct usb_endpoint_descriptor *ds; | ||
| 1859 | struct usb_ss_ep_comp_descriptor *comp_desc = NULL; | ||
| 1860 | int needs_comp_desc = false; | ||
| 1861 | int desc_idx; | ||
| 1862 | |||
| 1863 | if (ffs->gadget->speed == USB_SPEED_SUPER) { | ||
| 1864 | desc_idx = 2; | ||
| 1865 | needs_comp_desc = true; | ||
| 1866 | } else if (ffs->gadget->speed == USB_SPEED_HIGH) | ||
| 1867 | desc_idx = 1; | ||
| 1868 | else | ||
| 1869 | desc_idx = 0; | ||
| 1870 | |||
| 1871 | /* fall-back to lower speed if desc missing for current speed */ | ||
| 1872 | do { | ||
| 1873 | ds = ep->descs[desc_idx]; | ||
| 1874 | } while (!ds && --desc_idx >= 0); | ||
| 1875 | |||
| 1876 | if (!ds) { | ||
| 1877 | ret = -EINVAL; | ||
| 1878 | break; | ||
| 1879 | } | ||
| 1880 | |||
| 1881 | ep->ep->driver_data = ep; | 1858 | ep->ep->driver_data = ep; |
| 1882 | ep->ep->desc = ds; | ||
| 1883 | 1859 | ||
| 1884 | if (needs_comp_desc) { | 1860 | ret = config_ep_by_speed(func->gadget, &func->function, ep->ep); |
| 1885 | comp_desc = (struct usb_ss_ep_comp_descriptor *)(ds + | 1861 | if (ret) { |
| 1886 | USB_DT_ENDPOINT_SIZE); | 1862 | pr_err("%s: config_ep_by_speed(%s) returned %d\n", |
| 1887 | ep->ep->maxburst = comp_desc->bMaxBurst + 1; | 1863 | __func__, ep->ep->name, ret); |
| 1888 | ep->ep->comp_desc = comp_desc; | 1864 | break; |
| 1889 | } | 1865 | } |
| 1890 | 1866 | ||
| 1891 | ret = usb_ep_enable(ep->ep); | 1867 | ret = usb_ep_enable(ep->ep); |
| 1892 | if (likely(!ret)) { | 1868 | if (likely(!ret)) { |
| 1893 | epfile->ep = ep; | 1869 | epfile->ep = ep; |
| 1894 | epfile->in = usb_endpoint_dir_in(ds); | 1870 | epfile->in = usb_endpoint_dir_in(ep->ep->desc); |
| 1895 | epfile->isoc = usb_endpoint_xfer_isoc(ds); | 1871 | epfile->isoc = usb_endpoint_xfer_isoc(ep->ep->desc); |
| 1896 | } else { | 1872 | } else { |
| 1897 | break; | 1873 | break; |
| 1898 | } | 1874 | } |
| @@ -2979,10 +2955,8 @@ static int _ffs_func_bind(struct usb_configuration *c, | |||
| 2979 | struct ffs_data *ffs = func->ffs; | 2955 | struct ffs_data *ffs = func->ffs; |
| 2980 | 2956 | ||
| 2981 | const int full = !!func->ffs->fs_descs_count; | 2957 | const int full = !!func->ffs->fs_descs_count; |
| 2982 | const int high = gadget_is_dualspeed(func->gadget) && | 2958 | const int high = !!func->ffs->hs_descs_count; |
| 2983 | func->ffs->hs_descs_count; | 2959 | const int super = !!func->ffs->ss_descs_count; |
| 2984 | const int super = gadget_is_superspeed(func->gadget) && | ||
| 2985 | func->ffs->ss_descs_count; | ||
| 2986 | 2960 | ||
| 2987 | int fs_len, hs_len, ss_len, ret, i; | 2961 | int fs_len, hs_len, ss_len, ret, i; |
| 2988 | struct ffs_ep *eps_ptr; | 2962 | struct ffs_ep *eps_ptr; |
diff --git a/drivers/usb/gadget/function/f_uac2.c b/drivers/usb/gadget/function/f_uac2.c index 11fe788b4308..d2dc1f00180b 100644 --- a/drivers/usb/gadget/function/f_uac2.c +++ b/drivers/usb/gadget/function/f_uac2.c | |||
| @@ -524,6 +524,8 @@ afunc_bind(struct usb_configuration *cfg, struct usb_function *fn) | |||
| 524 | dev_err(dev, "%s:%d Error!\n", __func__, __LINE__); | 524 | dev_err(dev, "%s:%d Error!\n", __func__, __LINE__); |
| 525 | return ret; | 525 | return ret; |
| 526 | } | 526 | } |
| 527 | iad_desc.bFirstInterface = ret; | ||
| 528 | |||
| 527 | std_ac_if_desc.bInterfaceNumber = ret; | 529 | std_ac_if_desc.bInterfaceNumber = ret; |
| 528 | uac2->ac_intf = ret; | 530 | uac2->ac_intf = ret; |
| 529 | uac2->ac_alt = 0; | 531 | uac2->ac_alt = 0; |
diff --git a/drivers/usb/gadget/udc/Kconfig b/drivers/usb/gadget/udc/Kconfig index 1e9567091d86..0875d38476ee 100644 --- a/drivers/usb/gadget/udc/Kconfig +++ b/drivers/usb/gadget/udc/Kconfig | |||
| @@ -274,7 +274,6 @@ config USB_SNP_UDC_PLAT | |||
| 274 | tristate "Synopsys USB 2.0 Device controller" | 274 | tristate "Synopsys USB 2.0 Device controller" |
| 275 | depends on USB_GADGET && OF && HAS_DMA | 275 | depends on USB_GADGET && OF && HAS_DMA |
| 276 | depends on EXTCON || EXTCON=n | 276 | depends on EXTCON || EXTCON=n |
| 277 | select USB_GADGET_DUALSPEED | ||
| 278 | select USB_SNP_CORE | 277 | select USB_SNP_CORE |
| 279 | default ARCH_BCM_IPROC | 278 | default ARCH_BCM_IPROC |
| 280 | help | 279 | help |
diff --git a/drivers/usb/gadget/udc/bdc/bdc_pci.c b/drivers/usb/gadget/udc/bdc/bdc_pci.c index 1e940f054cb8..6dbc489513cd 100644 --- a/drivers/usb/gadget/udc/bdc/bdc_pci.c +++ b/drivers/usb/gadget/udc/bdc/bdc_pci.c | |||
| @@ -77,6 +77,7 @@ static int bdc_pci_probe(struct pci_dev *pci, const struct pci_device_id *id) | |||
| 77 | if (ret) { | 77 | if (ret) { |
| 78 | dev_err(&pci->dev, | 78 | dev_err(&pci->dev, |
| 79 | "couldn't add resources to bdc device\n"); | 79 | "couldn't add resources to bdc device\n"); |
| 80 | platform_device_put(bdc); | ||
| 80 | return ret; | 81 | return ret; |
| 81 | } | 82 | } |
| 82 | 83 | ||
diff --git a/drivers/usb/gadget/udc/core.c b/drivers/usb/gadget/udc/core.c index 859d5b11ba4c..1f8b19d9cf97 100644 --- a/drivers/usb/gadget/udc/core.c +++ b/drivers/usb/gadget/udc/core.c | |||
| @@ -180,8 +180,8 @@ EXPORT_SYMBOL_GPL(usb_ep_alloc_request); | |||
| 180 | void usb_ep_free_request(struct usb_ep *ep, | 180 | void usb_ep_free_request(struct usb_ep *ep, |
| 181 | struct usb_request *req) | 181 | struct usb_request *req) |
| 182 | { | 182 | { |
| 183 | ep->ops->free_request(ep, req); | ||
| 184 | trace_usb_ep_free_request(ep, req, 0); | 183 | trace_usb_ep_free_request(ep, req, 0); |
| 184 | ep->ops->free_request(ep, req); | ||
| 185 | } | 185 | } |
| 186 | EXPORT_SYMBOL_GPL(usb_ep_free_request); | 186 | EXPORT_SYMBOL_GPL(usb_ep_free_request); |
| 187 | 187 | ||
diff --git a/drivers/usb/gadget/udc/fsl_udc_core.c b/drivers/usb/gadget/udc/fsl_udc_core.c index e5b4ee96c4bf..56b517a38865 100644 --- a/drivers/usb/gadget/udc/fsl_udc_core.c +++ b/drivers/usb/gadget/udc/fsl_udc_core.c | |||
| @@ -1305,7 +1305,7 @@ static void udc_reset_ep_queue(struct fsl_udc *udc, u8 pipe) | |||
| 1305 | { | 1305 | { |
| 1306 | struct fsl_ep *ep = get_ep_by_pipe(udc, pipe); | 1306 | struct fsl_ep *ep = get_ep_by_pipe(udc, pipe); |
| 1307 | 1307 | ||
| 1308 | if (ep->name) | 1308 | if (ep->ep.name) |
| 1309 | nuke(ep, -ESHUTDOWN); | 1309 | nuke(ep, -ESHUTDOWN); |
| 1310 | } | 1310 | } |
| 1311 | 1311 | ||
| @@ -1693,7 +1693,7 @@ static void dtd_complete_irq(struct fsl_udc *udc) | |||
| 1693 | curr_ep = get_ep_by_pipe(udc, i); | 1693 | curr_ep = get_ep_by_pipe(udc, i); |
| 1694 | 1694 | ||
| 1695 | /* If the ep is configured */ | 1695 | /* If the ep is configured */ |
| 1696 | if (curr_ep->name == NULL) { | 1696 | if (!curr_ep->ep.name) { |
| 1697 | WARNING("Invalid EP?"); | 1697 | WARNING("Invalid EP?"); |
| 1698 | continue; | 1698 | continue; |
| 1699 | } | 1699 | } |
diff --git a/drivers/usb/gadget/udc/renesas_usb3.c b/drivers/usb/gadget/udc/renesas_usb3.c index 6e87af248367..409cde4e6a51 100644 --- a/drivers/usb/gadget/udc/renesas_usb3.c +++ b/drivers/usb/gadget/udc/renesas_usb3.c | |||
| @@ -2410,7 +2410,7 @@ static int renesas_usb3_remove(struct platform_device *pdev) | |||
| 2410 | __renesas_usb3_ep_free_request(usb3->ep0_req); | 2410 | __renesas_usb3_ep_free_request(usb3->ep0_req); |
| 2411 | if (usb3->phy) | 2411 | if (usb3->phy) |
| 2412 | phy_put(usb3->phy); | 2412 | phy_put(usb3->phy); |
| 2413 | pm_runtime_disable(usb3_to_dev(usb3)); | 2413 | pm_runtime_disable(&pdev->dev); |
| 2414 | 2414 | ||
| 2415 | return 0; | 2415 | return 0; |
| 2416 | } | 2416 | } |
diff --git a/drivers/usb/host/Kconfig b/drivers/usb/host/Kconfig index 6150bed7cfa8..4fcfb3084b36 100644 --- a/drivers/usb/host/Kconfig +++ b/drivers/usb/host/Kconfig | |||
| @@ -633,14 +633,6 @@ config USB_UHCI_ASPEED | |||
| 633 | bool | 633 | bool |
| 634 | default y if ARCH_ASPEED | 634 | default y if ARCH_ASPEED |
| 635 | 635 | ||
| 636 | config USB_UHCI_BIG_ENDIAN_MMIO | ||
| 637 | bool | ||
| 638 | default y if SPARC_LEON | ||
| 639 | |||
| 640 | config USB_UHCI_BIG_ENDIAN_DESC | ||
| 641 | bool | ||
| 642 | default y if SPARC_LEON | ||
| 643 | |||
| 644 | config USB_FHCI_HCD | 636 | config USB_FHCI_HCD |
| 645 | tristate "Freescale QE USB Host Controller support" | 637 | tristate "Freescale QE USB Host Controller support" |
| 646 | depends on OF_GPIO && QE_GPIO && QUICC_ENGINE | 638 | depends on OF_GPIO && QE_GPIO && QUICC_ENGINE |
diff --git a/drivers/usb/host/ehci-hub.c b/drivers/usb/host/ehci-hub.c index facafdf8fb95..d7641cbdee43 100644 --- a/drivers/usb/host/ehci-hub.c +++ b/drivers/usb/host/ehci-hub.c | |||
| @@ -774,12 +774,12 @@ static struct urb *request_single_step_set_feature_urb( | |||
| 774 | atomic_inc(&urb->use_count); | 774 | atomic_inc(&urb->use_count); |
| 775 | atomic_inc(&urb->dev->urbnum); | 775 | atomic_inc(&urb->dev->urbnum); |
| 776 | urb->setup_dma = dma_map_single( | 776 | urb->setup_dma = dma_map_single( |
| 777 | hcd->self.controller, | 777 | hcd->self.sysdev, |
| 778 | urb->setup_packet, | 778 | urb->setup_packet, |
| 779 | sizeof(struct usb_ctrlrequest), | 779 | sizeof(struct usb_ctrlrequest), |
| 780 | DMA_TO_DEVICE); | 780 | DMA_TO_DEVICE); |
| 781 | urb->transfer_dma = dma_map_single( | 781 | urb->transfer_dma = dma_map_single( |
| 782 | hcd->self.controller, | 782 | hcd->self.sysdev, |
| 783 | urb->transfer_buffer, | 783 | urb->transfer_buffer, |
| 784 | urb->transfer_buffer_length, | 784 | urb->transfer_buffer_length, |
| 785 | DMA_FROM_DEVICE); | 785 | DMA_FROM_DEVICE); |
diff --git a/drivers/usb/host/ehci-q.c b/drivers/usb/host/ehci-q.c index 88158324dcae..327630405695 100644 --- a/drivers/usb/host/ehci-q.c +++ b/drivers/usb/host/ehci-q.c | |||
| @@ -1188,10 +1188,10 @@ static int submit_single_step_set_feature( | |||
| 1188 | * 15 secs after the setup | 1188 | * 15 secs after the setup |
| 1189 | */ | 1189 | */ |
| 1190 | if (is_setup) { | 1190 | if (is_setup) { |
| 1191 | /* SETUP pid */ | 1191 | /* SETUP pid, and interrupt after SETUP completion */ |
| 1192 | qtd_fill(ehci, qtd, urb->setup_dma, | 1192 | qtd_fill(ehci, qtd, urb->setup_dma, |
| 1193 | sizeof(struct usb_ctrlrequest), | 1193 | sizeof(struct usb_ctrlrequest), |
| 1194 | token | (2 /* "setup" */ << 8), 8); | 1194 | QTD_IOC | token | (2 /* "setup" */ << 8), 8); |
| 1195 | 1195 | ||
| 1196 | submit_async(ehci, urb, &qtd_list, GFP_ATOMIC); | 1196 | submit_async(ehci, urb, &qtd_list, GFP_ATOMIC); |
| 1197 | return 0; /*Return now; we shall come back after 15 seconds*/ | 1197 | return 0; /*Return now; we shall come back after 15 seconds*/ |
| @@ -1228,12 +1228,8 @@ static int submit_single_step_set_feature( | |||
| 1228 | qtd_prev->hw_next = QTD_NEXT(ehci, qtd->qtd_dma); | 1228 | qtd_prev->hw_next = QTD_NEXT(ehci, qtd->qtd_dma); |
| 1229 | list_add_tail(&qtd->qtd_list, head); | 1229 | list_add_tail(&qtd->qtd_list, head); |
| 1230 | 1230 | ||
| 1231 | /* dont fill any data in such packets */ | 1231 | /* Interrupt after STATUS completion */ |
| 1232 | qtd_fill(ehci, qtd, 0, 0, token, 0); | 1232 | qtd_fill(ehci, qtd, 0, 0, token | QTD_IOC, 0); |
| 1233 | |||
| 1234 | /* by default, enable interrupt on urb completion */ | ||
| 1235 | if (likely(!(urb->transfer_flags & URB_NO_INTERRUPT))) | ||
| 1236 | qtd->hw_token |= cpu_to_hc32(ehci, QTD_IOC); | ||
| 1237 | 1233 | ||
| 1238 | submit_async(ehci, urb, &qtd_list, GFP_KERNEL); | 1234 | submit_async(ehci, urb, &qtd_list, GFP_KERNEL); |
| 1239 | 1235 | ||
diff --git a/drivers/usb/host/ohci-hcd.c b/drivers/usb/host/ohci-hcd.c index ee9676349333..84f88fa411cd 100644 --- a/drivers/usb/host/ohci-hcd.c +++ b/drivers/usb/host/ohci-hcd.c | |||
| @@ -74,6 +74,7 @@ static const char hcd_name [] = "ohci_hcd"; | |||
| 74 | 74 | ||
| 75 | #define STATECHANGE_DELAY msecs_to_jiffies(300) | 75 | #define STATECHANGE_DELAY msecs_to_jiffies(300) |
| 76 | #define IO_WATCHDOG_DELAY msecs_to_jiffies(275) | 76 | #define IO_WATCHDOG_DELAY msecs_to_jiffies(275) |
| 77 | #define IO_WATCHDOG_OFF 0xffffff00 | ||
| 77 | 78 | ||
| 78 | #include "ohci.h" | 79 | #include "ohci.h" |
| 79 | #include "pci-quirks.h" | 80 | #include "pci-quirks.h" |
| @@ -231,7 +232,7 @@ static int ohci_urb_enqueue ( | |||
| 231 | } | 232 | } |
| 232 | 233 | ||
| 233 | /* Start up the I/O watchdog timer, if it's not running */ | 234 | /* Start up the I/O watchdog timer, if it's not running */ |
| 234 | if (!timer_pending(&ohci->io_watchdog) && | 235 | if (ohci->prev_frame_no == IO_WATCHDOG_OFF && |
| 235 | list_empty(&ohci->eds_in_use) && | 236 | list_empty(&ohci->eds_in_use) && |
| 236 | !(ohci->flags & OHCI_QUIRK_QEMU)) { | 237 | !(ohci->flags & OHCI_QUIRK_QEMU)) { |
| 237 | ohci->prev_frame_no = ohci_frame_no(ohci); | 238 | ohci->prev_frame_no = ohci_frame_no(ohci); |
| @@ -501,6 +502,7 @@ static int ohci_init (struct ohci_hcd *ohci) | |||
| 501 | return 0; | 502 | return 0; |
| 502 | 503 | ||
| 503 | timer_setup(&ohci->io_watchdog, io_watchdog_func, 0); | 504 | timer_setup(&ohci->io_watchdog, io_watchdog_func, 0); |
| 505 | ohci->prev_frame_no = IO_WATCHDOG_OFF; | ||
| 504 | 506 | ||
| 505 | ohci->hcca = dma_alloc_coherent (hcd->self.controller, | 507 | ohci->hcca = dma_alloc_coherent (hcd->self.controller, |
| 506 | sizeof(*ohci->hcca), &ohci->hcca_dma, GFP_KERNEL); | 508 | sizeof(*ohci->hcca), &ohci->hcca_dma, GFP_KERNEL); |
| @@ -730,7 +732,7 @@ static void io_watchdog_func(struct timer_list *t) | |||
| 730 | u32 head; | 732 | u32 head; |
| 731 | struct ed *ed; | 733 | struct ed *ed; |
| 732 | struct td *td, *td_start, *td_next; | 734 | struct td *td, *td_start, *td_next; |
| 733 | unsigned frame_no; | 735 | unsigned frame_no, prev_frame_no = IO_WATCHDOG_OFF; |
| 734 | unsigned long flags; | 736 | unsigned long flags; |
| 735 | 737 | ||
| 736 | spin_lock_irqsave(&ohci->lock, flags); | 738 | spin_lock_irqsave(&ohci->lock, flags); |
| @@ -835,7 +837,7 @@ static void io_watchdog_func(struct timer_list *t) | |||
| 835 | } | 837 | } |
| 836 | } | 838 | } |
| 837 | if (!list_empty(&ohci->eds_in_use)) { | 839 | if (!list_empty(&ohci->eds_in_use)) { |
| 838 | ohci->prev_frame_no = frame_no; | 840 | prev_frame_no = frame_no; |
| 839 | ohci->prev_wdh_cnt = ohci->wdh_cnt; | 841 | ohci->prev_wdh_cnt = ohci->wdh_cnt; |
| 840 | ohci->prev_donehead = ohci_readl(ohci, | 842 | ohci->prev_donehead = ohci_readl(ohci, |
| 841 | &ohci->regs->donehead); | 843 | &ohci->regs->donehead); |
| @@ -845,6 +847,7 @@ static void io_watchdog_func(struct timer_list *t) | |||
| 845 | } | 847 | } |
| 846 | 848 | ||
| 847 | done: | 849 | done: |
| 850 | ohci->prev_frame_no = prev_frame_no; | ||
| 848 | spin_unlock_irqrestore(&ohci->lock, flags); | 851 | spin_unlock_irqrestore(&ohci->lock, flags); |
| 849 | } | 852 | } |
| 850 | 853 | ||
| @@ -973,6 +976,7 @@ static void ohci_stop (struct usb_hcd *hcd) | |||
| 973 | if (quirk_nec(ohci)) | 976 | if (quirk_nec(ohci)) |
| 974 | flush_work(&ohci->nec_work); | 977 | flush_work(&ohci->nec_work); |
| 975 | del_timer_sync(&ohci->io_watchdog); | 978 | del_timer_sync(&ohci->io_watchdog); |
| 979 | ohci->prev_frame_no = IO_WATCHDOG_OFF; | ||
| 976 | 980 | ||
| 977 | ohci_writel (ohci, OHCI_INTR_MIE, &ohci->regs->intrdisable); | 981 | ohci_writel (ohci, OHCI_INTR_MIE, &ohci->regs->intrdisable); |
| 978 | ohci_usb_reset(ohci); | 982 | ohci_usb_reset(ohci); |
diff --git a/drivers/usb/host/ohci-hub.c b/drivers/usb/host/ohci-hub.c index fb7aaa3b9d06..634f3c7bf774 100644 --- a/drivers/usb/host/ohci-hub.c +++ b/drivers/usb/host/ohci-hub.c | |||
| @@ -311,8 +311,10 @@ static int ohci_bus_suspend (struct usb_hcd *hcd) | |||
| 311 | rc = ohci_rh_suspend (ohci, 0); | 311 | rc = ohci_rh_suspend (ohci, 0); |
| 312 | spin_unlock_irq (&ohci->lock); | 312 | spin_unlock_irq (&ohci->lock); |
| 313 | 313 | ||
| 314 | if (rc == 0) | 314 | if (rc == 0) { |
| 315 | del_timer_sync(&ohci->io_watchdog); | 315 | del_timer_sync(&ohci->io_watchdog); |
| 316 | ohci->prev_frame_no = IO_WATCHDOG_OFF; | ||
| 317 | } | ||
| 316 | return rc; | 318 | return rc; |
| 317 | } | 319 | } |
| 318 | 320 | ||
diff --git a/drivers/usb/host/ohci-q.c b/drivers/usb/host/ohci-q.c index b2ec8c399363..4ccb85a67bb3 100644 --- a/drivers/usb/host/ohci-q.c +++ b/drivers/usb/host/ohci-q.c | |||
| @@ -1019,6 +1019,8 @@ skip_ed: | |||
| 1019 | * have modified this list. normally it's just prepending | 1019 | * have modified this list. normally it's just prepending |
| 1020 | * entries (which we'd ignore), but paranoia won't hurt. | 1020 | * entries (which we'd ignore), but paranoia won't hurt. |
| 1021 | */ | 1021 | */ |
| 1022 | *last = ed->ed_next; | ||
| 1023 | ed->ed_next = NULL; | ||
| 1022 | modified = 0; | 1024 | modified = 0; |
| 1023 | 1025 | ||
| 1024 | /* unlink urbs as requested, but rescan the list after | 1026 | /* unlink urbs as requested, but rescan the list after |
| @@ -1077,21 +1079,22 @@ rescan_this: | |||
| 1077 | goto rescan_this; | 1079 | goto rescan_this; |
| 1078 | 1080 | ||
| 1079 | /* | 1081 | /* |
| 1080 | * If no TDs are queued, take ED off the ed_rm_list. | 1082 | * If no TDs are queued, ED is now idle. |
| 1081 | * Otherwise, if the HC is running, reschedule. | 1083 | * Otherwise, if the HC is running, reschedule. |
| 1082 | * If not, leave it on the list for further dequeues. | 1084 | * If the HC isn't running, add ED back to the |
| 1085 | * start of the list for later processing. | ||
| 1083 | */ | 1086 | */ |
| 1084 | if (list_empty(&ed->td_list)) { | 1087 | if (list_empty(&ed->td_list)) { |
| 1085 | *last = ed->ed_next; | ||
| 1086 | ed->ed_next = NULL; | ||
| 1087 | ed->state = ED_IDLE; | 1088 | ed->state = ED_IDLE; |
| 1088 | list_del(&ed->in_use_list); | 1089 | list_del(&ed->in_use_list); |
| 1089 | } else if (ohci->rh_state == OHCI_RH_RUNNING) { | 1090 | } else if (ohci->rh_state == OHCI_RH_RUNNING) { |
| 1090 | *last = ed->ed_next; | ||
| 1091 | ed->ed_next = NULL; | ||
| 1092 | ed_schedule(ohci, ed); | 1091 | ed_schedule(ohci, ed); |
| 1093 | } else { | 1092 | } else { |
| 1094 | last = &ed->ed_next; | 1093 | ed->ed_next = ohci->ed_rm_list; |
| 1094 | ohci->ed_rm_list = ed; | ||
| 1095 | /* Don't loop on the same ED */ | ||
| 1096 | if (last == &ohci->ed_rm_list) | ||
| 1097 | last = &ed->ed_next; | ||
| 1095 | } | 1098 | } |
| 1096 | 1099 | ||
| 1097 | if (modified) | 1100 | if (modified) |
diff --git a/drivers/usb/host/pci-quirks.c b/drivers/usb/host/pci-quirks.c index 161536717025..67ad4bb6919a 100644 --- a/drivers/usb/host/pci-quirks.c +++ b/drivers/usb/host/pci-quirks.c | |||
| @@ -66,6 +66,23 @@ | |||
| 66 | #define AX_INDXC 0x30 | 66 | #define AX_INDXC 0x30 |
| 67 | #define AX_DATAC 0x34 | 67 | #define AX_DATAC 0x34 |
| 68 | 68 | ||
| 69 | #define PT_ADDR_INDX 0xE8 | ||
| 70 | #define PT_READ_INDX 0xE4 | ||
| 71 | #define PT_SIG_1_ADDR 0xA520 | ||
| 72 | #define PT_SIG_2_ADDR 0xA521 | ||
| 73 | #define PT_SIG_3_ADDR 0xA522 | ||
| 74 | #define PT_SIG_4_ADDR 0xA523 | ||
| 75 | #define PT_SIG_1_DATA 0x78 | ||
| 76 | #define PT_SIG_2_DATA 0x56 | ||
| 77 | #define PT_SIG_3_DATA 0x34 | ||
| 78 | #define PT_SIG_4_DATA 0x12 | ||
| 79 | #define PT4_P1_REG 0xB521 | ||
| 80 | #define PT4_P2_REG 0xB522 | ||
| 81 | #define PT2_P1_REG 0xD520 | ||
| 82 | #define PT2_P2_REG 0xD521 | ||
| 83 | #define PT1_P1_REG 0xD522 | ||
| 84 | #define PT1_P2_REG 0xD523 | ||
| 85 | |||
| 69 | #define NB_PCIE_INDX_ADDR 0xe0 | 86 | #define NB_PCIE_INDX_ADDR 0xe0 |
| 70 | #define NB_PCIE_INDX_DATA 0xe4 | 87 | #define NB_PCIE_INDX_DATA 0xe4 |
| 71 | #define PCIE_P_CNTL 0x10040 | 88 | #define PCIE_P_CNTL 0x10040 |
| @@ -513,6 +530,98 @@ void usb_amd_dev_put(void) | |||
| 513 | EXPORT_SYMBOL_GPL(usb_amd_dev_put); | 530 | EXPORT_SYMBOL_GPL(usb_amd_dev_put); |
| 514 | 531 | ||
| 515 | /* | 532 | /* |
| 533 | * Check if port is disabled in BIOS on AMD Promontory host. | ||
| 534 | * BIOS Disabled ports may wake on connect/disconnect and need | ||
| 535 | * driver workaround to keep them disabled. | ||
| 536 | * Returns true if port is marked disabled. | ||
| 537 | */ | ||
| 538 | bool usb_amd_pt_check_port(struct device *device, int port) | ||
| 539 | { | ||
| 540 | unsigned char value, port_shift; | ||
| 541 | struct pci_dev *pdev; | ||
| 542 | u16 reg; | ||
| 543 | |||
| 544 | pdev = to_pci_dev(device); | ||
| 545 | pci_write_config_word(pdev, PT_ADDR_INDX, PT_SIG_1_ADDR); | ||
| 546 | |||
| 547 | pci_read_config_byte(pdev, PT_READ_INDX, &value); | ||
| 548 | if (value != PT_SIG_1_DATA) | ||
| 549 | return false; | ||
| 550 | |||
| 551 | pci_write_config_word(pdev, PT_ADDR_INDX, PT_SIG_2_ADDR); | ||
| 552 | |||
| 553 | pci_read_config_byte(pdev, PT_READ_INDX, &value); | ||
| 554 | if (value != PT_SIG_2_DATA) | ||
| 555 | return false; | ||
| 556 | |||
| 557 | pci_write_config_word(pdev, PT_ADDR_INDX, PT_SIG_3_ADDR); | ||
| 558 | |||
| 559 | pci_read_config_byte(pdev, PT_READ_INDX, &value); | ||
| 560 | if (value != PT_SIG_3_DATA) | ||
| 561 | return false; | ||
| 562 | |||
| 563 | pci_write_config_word(pdev, PT_ADDR_INDX, PT_SIG_4_ADDR); | ||
| 564 | |||
| 565 | pci_read_config_byte(pdev, PT_READ_INDX, &value); | ||
| 566 | if (value != PT_SIG_4_DATA) | ||
| 567 | return false; | ||
| 568 | |||
| 569 | /* Check disabled port setting, if bit is set port is enabled */ | ||
| 570 | switch (pdev->device) { | ||
| 571 | case 0x43b9: | ||
| 572 | case 0x43ba: | ||
| 573 | /* | ||
| 574 | * device is AMD_PROMONTORYA_4(0x43b9) or PROMONTORYA_3(0x43ba) | ||
| 575 | * PT4_P1_REG bits[7..1] represents USB2.0 ports 6 to 0 | ||
| 576 | * PT4_P2_REG bits[6..0] represents ports 13 to 7 | ||
| 577 | */ | ||
| 578 | if (port > 6) { | ||
| 579 | reg = PT4_P2_REG; | ||
| 580 | port_shift = port - 7; | ||
| 581 | } else { | ||
| 582 | reg = PT4_P1_REG; | ||
| 583 | port_shift = port + 1; | ||
| 584 | } | ||
| 585 | break; | ||
| 586 | case 0x43bb: | ||
| 587 | /* | ||
| 588 | * device is AMD_PROMONTORYA_2(0x43bb) | ||
| 589 | * PT2_P1_REG bits[7..5] represents USB2.0 ports 2 to 0 | ||
| 590 | * PT2_P2_REG bits[5..0] represents ports 9 to 3 | ||
| 591 | */ | ||
| 592 | if (port > 2) { | ||
| 593 | reg = PT2_P2_REG; | ||
| 594 | port_shift = port - 3; | ||
| 595 | } else { | ||
| 596 | reg = PT2_P1_REG; | ||
| 597 | port_shift = port + 5; | ||
| 598 | } | ||
| 599 | break; | ||
| 600 | case 0x43bc: | ||
| 601 | /* | ||
| 602 | * device is AMD_PROMONTORYA_1(0x43bc) | ||
| 603 | * PT1_P1_REG[7..4] represents USB2.0 ports 3 to 0 | ||
| 604 | * PT1_P2_REG[5..0] represents ports 9 to 4 | ||
| 605 | */ | ||
| 606 | if (port > 3) { | ||
| 607 | reg = PT1_P2_REG; | ||
| 608 | port_shift = port - 4; | ||
| 609 | } else { | ||
| 610 | reg = PT1_P1_REG; | ||
| 611 | port_shift = port + 4; | ||
| 612 | } | ||
| 613 | break; | ||
| 614 | default: | ||
| 615 | return false; | ||
| 616 | } | ||
| 617 | pci_write_config_word(pdev, PT_ADDR_INDX, reg); | ||
| 618 | pci_read_config_byte(pdev, PT_READ_INDX, &value); | ||
| 619 | |||
| 620 | return !(value & BIT(port_shift)); | ||
| 621 | } | ||
| 622 | EXPORT_SYMBOL_GPL(usb_amd_pt_check_port); | ||
| 623 | |||
| 624 | /* | ||
| 516 | * Make sure the controller is completely inactive, unable to | 625 | * Make sure the controller is completely inactive, unable to |
| 517 | * generate interrupts or do DMA. | 626 | * generate interrupts or do DMA. |
| 518 | */ | 627 | */ |
diff --git a/drivers/usb/host/pci-quirks.h b/drivers/usb/host/pci-quirks.h index b68dcb5dd0fd..4ca0d9b7e463 100644 --- a/drivers/usb/host/pci-quirks.h +++ b/drivers/usb/host/pci-quirks.h | |||
| @@ -17,6 +17,7 @@ void usb_enable_intel_xhci_ports(struct pci_dev *xhci_pdev); | |||
| 17 | void usb_disable_xhci_ports(struct pci_dev *xhci_pdev); | 17 | void usb_disable_xhci_ports(struct pci_dev *xhci_pdev); |
| 18 | void sb800_prefetch(struct device *dev, int on); | 18 | void sb800_prefetch(struct device *dev, int on); |
| 19 | bool usb_xhci_needs_pci_reset(struct pci_dev *pdev); | 19 | bool usb_xhci_needs_pci_reset(struct pci_dev *pdev); |
| 20 | bool usb_amd_pt_check_port(struct device *device, int port); | ||
| 20 | #else | 21 | #else |
| 21 | struct pci_dev; | 22 | struct pci_dev; |
| 22 | static inline void usb_amd_quirk_pll_disable(void) {} | 23 | static inline void usb_amd_quirk_pll_disable(void) {} |
| @@ -25,6 +26,10 @@ static inline void usb_asmedia_modifyflowcontrol(struct pci_dev *pdev) {} | |||
| 25 | static inline void usb_amd_dev_put(void) {} | 26 | static inline void usb_amd_dev_put(void) {} |
| 26 | static inline void usb_disable_xhci_ports(struct pci_dev *xhci_pdev) {} | 27 | static inline void usb_disable_xhci_ports(struct pci_dev *xhci_pdev) {} |
| 27 | static inline void sb800_prefetch(struct device *dev, int on) {} | 28 | static inline void sb800_prefetch(struct device *dev, int on) {} |
| 29 | static inline bool usb_amd_pt_check_port(struct device *device, int port) | ||
| 30 | { | ||
| 31 | return false; | ||
| 32 | } | ||
| 28 | #endif /* CONFIG_USB_PCI */ | 33 | #endif /* CONFIG_USB_PCI */ |
| 29 | 34 | ||
| 30 | #endif /* __LINUX_USB_PCI_QUIRKS_H */ | 35 | #endif /* __LINUX_USB_PCI_QUIRKS_H */ |
diff --git a/drivers/usb/host/xhci-debugfs.c b/drivers/usb/host/xhci-debugfs.c index e26e685d8a57..5851052d4668 100644 --- a/drivers/usb/host/xhci-debugfs.c +++ b/drivers/usb/host/xhci-debugfs.c | |||
| @@ -211,7 +211,7 @@ static void xhci_ring_dump_segment(struct seq_file *s, | |||
| 211 | static int xhci_ring_trb_show(struct seq_file *s, void *unused) | 211 | static int xhci_ring_trb_show(struct seq_file *s, void *unused) |
| 212 | { | 212 | { |
| 213 | int i; | 213 | int i; |
| 214 | struct xhci_ring *ring = s->private; | 214 | struct xhci_ring *ring = *(struct xhci_ring **)s->private; |
| 215 | struct xhci_segment *seg = ring->first_seg; | 215 | struct xhci_segment *seg = ring->first_seg; |
| 216 | 216 | ||
| 217 | for (i = 0; i < ring->num_segs; i++) { | 217 | for (i = 0; i < ring->num_segs; i++) { |
| @@ -387,7 +387,7 @@ void xhci_debugfs_create_endpoint(struct xhci_hcd *xhci, | |||
| 387 | 387 | ||
| 388 | snprintf(epriv->name, sizeof(epriv->name), "ep%02d", ep_index); | 388 | snprintf(epriv->name, sizeof(epriv->name), "ep%02d", ep_index); |
| 389 | epriv->root = xhci_debugfs_create_ring_dir(xhci, | 389 | epriv->root = xhci_debugfs_create_ring_dir(xhci, |
| 390 | &dev->eps[ep_index].new_ring, | 390 | &dev->eps[ep_index].ring, |
| 391 | epriv->name, | 391 | epriv->name, |
| 392 | spriv->root); | 392 | spriv->root); |
| 393 | spriv->eps[ep_index] = epriv; | 393 | spriv->eps[ep_index] = epriv; |
diff --git a/drivers/usb/host/xhci-hub.c b/drivers/usb/host/xhci-hub.c index 46d5e08f05f1..72ebbc908e19 100644 --- a/drivers/usb/host/xhci-hub.c +++ b/drivers/usb/host/xhci-hub.c | |||
| @@ -1224,17 +1224,17 @@ int xhci_hub_control(struct usb_hcd *hcd, u16 typeReq, u16 wValue, | |||
| 1224 | temp = readl(port_array[wIndex]); | 1224 | temp = readl(port_array[wIndex]); |
| 1225 | break; | 1225 | break; |
| 1226 | } | 1226 | } |
| 1227 | 1227 | /* Port must be enabled */ | |
| 1228 | /* Software should not attempt to set | 1228 | if (!(temp & PORT_PE)) { |
| 1229 | * port link state above '3' (U3) and the port | 1229 | retval = -ENODEV; |
| 1230 | * must be enabled. | 1230 | break; |
| 1231 | */ | 1231 | } |
| 1232 | if ((temp & PORT_PE) == 0 || | 1232 | /* Can't set port link state above '3' (U3) */ |
| 1233 | (link_state > USB_SS_PORT_LS_U3)) { | 1233 | if (link_state > USB_SS_PORT_LS_U3) { |
| 1234 | xhci_warn(xhci, "Cannot set link state.\n"); | 1234 | xhci_warn(xhci, "Cannot set port %d link state %d\n", |
| 1235 | wIndex, link_state); | ||
| 1235 | goto error; | 1236 | goto error; |
| 1236 | } | 1237 | } |
| 1237 | |||
| 1238 | if (link_state == USB_SS_PORT_LS_U3) { | 1238 | if (link_state == USB_SS_PORT_LS_U3) { |
| 1239 | slot_id = xhci_find_slot_id_by_port(hcd, xhci, | 1239 | slot_id = xhci_find_slot_id_by_port(hcd, xhci, |
| 1240 | wIndex + 1); | 1240 | wIndex + 1); |
| @@ -1522,6 +1522,13 @@ int xhci_bus_suspend(struct usb_hcd *hcd) | |||
| 1522 | t2 |= PORT_WKOC_E | PORT_WKCONN_E; | 1522 | t2 |= PORT_WKOC_E | PORT_WKCONN_E; |
| 1523 | t2 &= ~PORT_WKDISC_E; | 1523 | t2 &= ~PORT_WKDISC_E; |
| 1524 | } | 1524 | } |
| 1525 | |||
| 1526 | if ((xhci->quirks & XHCI_U2_DISABLE_WAKE) && | ||
| 1527 | (hcd->speed < HCD_USB3)) { | ||
| 1528 | if (usb_amd_pt_check_port(hcd->self.controller, | ||
| 1529 | port_index)) | ||
| 1530 | t2 &= ~PORT_WAKE_BITS; | ||
| 1531 | } | ||
| 1525 | } else | 1532 | } else |
| 1526 | t2 &= ~PORT_WAKE_BITS; | 1533 | t2 &= ~PORT_WAKE_BITS; |
| 1527 | 1534 | ||
diff --git a/drivers/usb/host/xhci-pci.c b/drivers/usb/host/xhci-pci.c index 6c79037876db..5262fa571a5d 100644 --- a/drivers/usb/host/xhci-pci.c +++ b/drivers/usb/host/xhci-pci.c | |||
| @@ -42,6 +42,10 @@ | |||
| 42 | #define PCI_DEVICE_ID_INTEL_APL_XHCI 0x5aa8 | 42 | #define PCI_DEVICE_ID_INTEL_APL_XHCI 0x5aa8 |
| 43 | #define PCI_DEVICE_ID_INTEL_DNV_XHCI 0x19d0 | 43 | #define PCI_DEVICE_ID_INTEL_DNV_XHCI 0x19d0 |
| 44 | 44 | ||
| 45 | #define PCI_DEVICE_ID_AMD_PROMONTORYA_4 0x43b9 | ||
| 46 | #define PCI_DEVICE_ID_AMD_PROMONTORYA_3 0x43ba | ||
| 47 | #define PCI_DEVICE_ID_AMD_PROMONTORYA_2 0x43bb | ||
| 48 | #define PCI_DEVICE_ID_AMD_PROMONTORYA_1 0x43bc | ||
| 45 | #define PCI_DEVICE_ID_ASMEDIA_1042A_XHCI 0x1142 | 49 | #define PCI_DEVICE_ID_ASMEDIA_1042A_XHCI 0x1142 |
| 46 | 50 | ||
| 47 | static const char hcd_name[] = "xhci_hcd"; | 51 | static const char hcd_name[] = "xhci_hcd"; |
| @@ -125,6 +129,13 @@ static void xhci_pci_quirks(struct device *dev, struct xhci_hcd *xhci) | |||
| 125 | if (pdev->vendor == PCI_VENDOR_ID_AMD) | 129 | if (pdev->vendor == PCI_VENDOR_ID_AMD) |
| 126 | xhci->quirks |= XHCI_TRUST_TX_LENGTH; | 130 | xhci->quirks |= XHCI_TRUST_TX_LENGTH; |
| 127 | 131 | ||
| 132 | if ((pdev->vendor == PCI_VENDOR_ID_AMD) && | ||
| 133 | ((pdev->device == PCI_DEVICE_ID_AMD_PROMONTORYA_4) || | ||
| 134 | (pdev->device == PCI_DEVICE_ID_AMD_PROMONTORYA_3) || | ||
| 135 | (pdev->device == PCI_DEVICE_ID_AMD_PROMONTORYA_2) || | ||
| 136 | (pdev->device == PCI_DEVICE_ID_AMD_PROMONTORYA_1))) | ||
| 137 | xhci->quirks |= XHCI_U2_DISABLE_WAKE; | ||
| 138 | |||
| 128 | if (pdev->vendor == PCI_VENDOR_ID_INTEL) { | 139 | if (pdev->vendor == PCI_VENDOR_ID_INTEL) { |
| 129 | xhci->quirks |= XHCI_LPM_SUPPORT; | 140 | xhci->quirks |= XHCI_LPM_SUPPORT; |
| 130 | xhci->quirks |= XHCI_INTEL_HOST; | 141 | xhci->quirks |= XHCI_INTEL_HOST; |
diff --git a/drivers/usb/host/xhci.c b/drivers/usb/host/xhci.c index 1eeb3396300f..25d4b748a56f 100644 --- a/drivers/usb/host/xhci.c +++ b/drivers/usb/host/xhci.c | |||
| @@ -646,8 +646,6 @@ static void xhci_stop(struct usb_hcd *hcd) | |||
| 646 | return; | 646 | return; |
| 647 | } | 647 | } |
| 648 | 648 | ||
| 649 | xhci_debugfs_exit(xhci); | ||
| 650 | |||
| 651 | xhci_dbc_exit(xhci); | 649 | xhci_dbc_exit(xhci); |
| 652 | 650 | ||
| 653 | spin_lock_irq(&xhci->lock); | 651 | spin_lock_irq(&xhci->lock); |
| @@ -680,6 +678,7 @@ static void xhci_stop(struct usb_hcd *hcd) | |||
| 680 | 678 | ||
| 681 | xhci_dbg_trace(xhci, trace_xhci_dbg_init, "cleaning up memory"); | 679 | xhci_dbg_trace(xhci, trace_xhci_dbg_init, "cleaning up memory"); |
| 682 | xhci_mem_cleanup(xhci); | 680 | xhci_mem_cleanup(xhci); |
| 681 | xhci_debugfs_exit(xhci); | ||
| 683 | xhci_dbg_trace(xhci, trace_xhci_dbg_init, | 682 | xhci_dbg_trace(xhci, trace_xhci_dbg_init, |
| 684 | "xhci_stop completed - status = %x", | 683 | "xhci_stop completed - status = %x", |
| 685 | readl(&xhci->op_regs->status)); | 684 | readl(&xhci->op_regs->status)); |
| @@ -1014,6 +1013,7 @@ int xhci_resume(struct xhci_hcd *xhci, bool hibernated) | |||
| 1014 | 1013 | ||
| 1015 | xhci_dbg(xhci, "cleaning up memory\n"); | 1014 | xhci_dbg(xhci, "cleaning up memory\n"); |
| 1016 | xhci_mem_cleanup(xhci); | 1015 | xhci_mem_cleanup(xhci); |
| 1016 | xhci_debugfs_exit(xhci); | ||
| 1017 | xhci_dbg(xhci, "xhci_stop completed - status = %x\n", | 1017 | xhci_dbg(xhci, "xhci_stop completed - status = %x\n", |
| 1018 | readl(&xhci->op_regs->status)); | 1018 | readl(&xhci->op_regs->status)); |
| 1019 | 1019 | ||
| @@ -3544,12 +3544,10 @@ static void xhci_free_dev(struct usb_hcd *hcd, struct usb_device *udev) | |||
| 3544 | virt_dev->eps[i].ep_state &= ~EP_STOP_CMD_PENDING; | 3544 | virt_dev->eps[i].ep_state &= ~EP_STOP_CMD_PENDING; |
| 3545 | del_timer_sync(&virt_dev->eps[i].stop_cmd_timer); | 3545 | del_timer_sync(&virt_dev->eps[i].stop_cmd_timer); |
| 3546 | } | 3546 | } |
| 3547 | 3547 | xhci_debugfs_remove_slot(xhci, udev->slot_id); | |
| 3548 | ret = xhci_disable_slot(xhci, udev->slot_id); | 3548 | ret = xhci_disable_slot(xhci, udev->slot_id); |
| 3549 | if (ret) { | 3549 | if (ret) |
| 3550 | xhci_debugfs_remove_slot(xhci, udev->slot_id); | ||
| 3551 | xhci_free_virt_device(xhci, udev->slot_id); | 3550 | xhci_free_virt_device(xhci, udev->slot_id); |
| 3552 | } | ||
| 3553 | } | 3551 | } |
| 3554 | 3552 | ||
| 3555 | int xhci_disable_slot(struct xhci_hcd *xhci, u32 slot_id) | 3553 | int xhci_disable_slot(struct xhci_hcd *xhci, u32 slot_id) |
diff --git a/drivers/usb/host/xhci.h b/drivers/usb/host/xhci.h index 96099a245c69..e4d7d3d06a75 100644 --- a/drivers/usb/host/xhci.h +++ b/drivers/usb/host/xhci.h | |||
| @@ -1822,7 +1822,7 @@ struct xhci_hcd { | |||
| 1822 | /* For controller with a broken Port Disable implementation */ | 1822 | /* For controller with a broken Port Disable implementation */ |
| 1823 | #define XHCI_BROKEN_PORT_PED (1 << 25) | 1823 | #define XHCI_BROKEN_PORT_PED (1 << 25) |
| 1824 | #define XHCI_LIMIT_ENDPOINT_INTERVAL_7 (1 << 26) | 1824 | #define XHCI_LIMIT_ENDPOINT_INTERVAL_7 (1 << 26) |
| 1825 | /* Reserved. It was XHCI_U2_DISABLE_WAKE */ | 1825 | #define XHCI_U2_DISABLE_WAKE (1 << 27) |
| 1826 | #define XHCI_ASMEDIA_MODIFY_FLOWCONTROL (1 << 28) | 1826 | #define XHCI_ASMEDIA_MODIFY_FLOWCONTROL (1 << 28) |
| 1827 | #define XHCI_HW_LPM_DISABLE (1 << 29) | 1827 | #define XHCI_HW_LPM_DISABLE (1 << 29) |
| 1828 | 1828 | ||
diff --git a/drivers/usb/misc/ldusb.c b/drivers/usb/misc/ldusb.c index 63b9e85dc0e9..236a60f53099 100644 --- a/drivers/usb/misc/ldusb.c +++ b/drivers/usb/misc/ldusb.c | |||
| @@ -42,6 +42,9 @@ | |||
| 42 | #define USB_DEVICE_ID_LD_MICROCASSYTIME 0x1033 /* USB Product ID of Micro-CASSY Time (reserved) */ | 42 | #define USB_DEVICE_ID_LD_MICROCASSYTIME 0x1033 /* USB Product ID of Micro-CASSY Time (reserved) */ |
| 43 | #define USB_DEVICE_ID_LD_MICROCASSYTEMPERATURE 0x1035 /* USB Product ID of Micro-CASSY Temperature */ | 43 | #define USB_DEVICE_ID_LD_MICROCASSYTEMPERATURE 0x1035 /* USB Product ID of Micro-CASSY Temperature */ |
| 44 | #define USB_DEVICE_ID_LD_MICROCASSYPH 0x1038 /* USB Product ID of Micro-CASSY pH */ | 44 | #define USB_DEVICE_ID_LD_MICROCASSYPH 0x1038 /* USB Product ID of Micro-CASSY pH */ |
| 45 | #define USB_DEVICE_ID_LD_POWERANALYSERCASSY 0x1040 /* USB Product ID of Power Analyser CASSY */ | ||
| 46 | #define USB_DEVICE_ID_LD_CONVERTERCONTROLLERCASSY 0x1042 /* USB Product ID of Converter Controller CASSY */ | ||
| 47 | #define USB_DEVICE_ID_LD_MACHINETESTCASSY 0x1043 /* USB Product ID of Machine Test CASSY */ | ||
| 45 | #define USB_DEVICE_ID_LD_JWM 0x1080 /* USB Product ID of Joule and Wattmeter */ | 48 | #define USB_DEVICE_ID_LD_JWM 0x1080 /* USB Product ID of Joule and Wattmeter */ |
| 46 | #define USB_DEVICE_ID_LD_DMMP 0x1081 /* USB Product ID of Digital Multimeter P (reserved) */ | 49 | #define USB_DEVICE_ID_LD_DMMP 0x1081 /* USB Product ID of Digital Multimeter P (reserved) */ |
| 47 | #define USB_DEVICE_ID_LD_UMIP 0x1090 /* USB Product ID of UMI P */ | 50 | #define USB_DEVICE_ID_LD_UMIP 0x1090 /* USB Product ID of UMI P */ |
| @@ -84,6 +87,9 @@ static const struct usb_device_id ld_usb_table[] = { | |||
| 84 | { USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_MICROCASSYTIME) }, | 87 | { USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_MICROCASSYTIME) }, |
| 85 | { USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_MICROCASSYTEMPERATURE) }, | 88 | { USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_MICROCASSYTEMPERATURE) }, |
| 86 | { USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_MICROCASSYPH) }, | 89 | { USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_MICROCASSYPH) }, |
| 90 | { USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_POWERANALYSERCASSY) }, | ||
| 91 | { USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_CONVERTERCONTROLLERCASSY) }, | ||
| 92 | { USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_MACHINETESTCASSY) }, | ||
| 87 | { USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_JWM) }, | 93 | { USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_JWM) }, |
| 88 | { USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_DMMP) }, | 94 | { USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_DMMP) }, |
| 89 | { USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_UMIP) }, | 95 | { USB_DEVICE(USB_VENDOR_ID_LD, USB_DEVICE_ID_LD_UMIP) }, |
diff --git a/drivers/usb/musb/musb_core.c b/drivers/usb/musb/musb_core.c index 968bf1e8b0fe..eef4ad578b31 100644 --- a/drivers/usb/musb/musb_core.c +++ b/drivers/usb/musb/musb_core.c | |||
| @@ -2708,7 +2708,8 @@ static int musb_resume(struct device *dev) | |||
| 2708 | if ((devctl & mask) != (musb->context.devctl & mask)) | 2708 | if ((devctl & mask) != (musb->context.devctl & mask)) |
| 2709 | musb->port1_status = 0; | 2709 | musb->port1_status = 0; |
| 2710 | 2710 | ||
| 2711 | musb_start(musb); | 2711 | musb_enable_interrupts(musb); |
| 2712 | musb_platform_enable(musb); | ||
| 2712 | 2713 | ||
| 2713 | spin_lock_irqsave(&musb->lock, flags); | 2714 | spin_lock_irqsave(&musb->lock, flags); |
| 2714 | error = musb_run_resume_work(musb); | 2715 | error = musb_run_resume_work(musb); |
diff --git a/drivers/usb/musb/musb_host.c b/drivers/usb/musb/musb_host.c index 394b4ac86161..45ed32c2cba9 100644 --- a/drivers/usb/musb/musb_host.c +++ b/drivers/usb/musb/musb_host.c | |||
| @@ -391,13 +391,7 @@ static void musb_advance_schedule(struct musb *musb, struct urb *urb, | |||
| 391 | } | 391 | } |
| 392 | } | 392 | } |
| 393 | 393 | ||
| 394 | /* | 394 | if (qh != NULL && qh->is_ready) { |
| 395 | * The pipe must be broken if current urb->status is set, so don't | ||
| 396 | * start next urb. | ||
| 397 | * TODO: to minimize the risk of regression, only check urb->status | ||
| 398 | * for RX, until we have a test case to understand the behavior of TX. | ||
| 399 | */ | ||
| 400 | if ((!status || !is_in) && qh && qh->is_ready) { | ||
| 401 | musb_dbg(musb, "... next ep%d %cX urb %p", | 395 | musb_dbg(musb, "... next ep%d %cX urb %p", |
| 402 | hw_ep->epnum, is_in ? 'R' : 'T', next_urb(qh)); | 396 | hw_ep->epnum, is_in ? 'R' : 'T', next_urb(qh)); |
| 403 | musb_start_urb(musb, is_in, qh); | 397 | musb_start_urb(musb, is_in, qh); |
diff --git a/drivers/usb/phy/phy-mxs-usb.c b/drivers/usb/phy/phy-mxs-usb.c index da031c45395a..fbec863350f6 100644 --- a/drivers/usb/phy/phy-mxs-usb.c +++ b/drivers/usb/phy/phy-mxs-usb.c | |||
| @@ -602,6 +602,9 @@ static enum usb_charger_type mxs_phy_charger_detect(struct usb_phy *phy) | |||
| 602 | void __iomem *base = phy->io_priv; | 602 | void __iomem *base = phy->io_priv; |
| 603 | enum usb_charger_type chgr_type = UNKNOWN_TYPE; | 603 | enum usb_charger_type chgr_type = UNKNOWN_TYPE; |
| 604 | 604 | ||
| 605 | if (!regmap) | ||
| 606 | return UNKNOWN_TYPE; | ||
| 607 | |||
| 605 | if (mxs_charger_data_contact_detect(mxs_phy)) | 608 | if (mxs_charger_data_contact_detect(mxs_phy)) |
| 606 | return chgr_type; | 609 | return chgr_type; |
| 607 | 610 | ||
diff --git a/drivers/usb/renesas_usbhs/fifo.c b/drivers/usb/renesas_usbhs/fifo.c index 5925d111bd47..39fa2fc1b8b7 100644 --- a/drivers/usb/renesas_usbhs/fifo.c +++ b/drivers/usb/renesas_usbhs/fifo.c | |||
| @@ -982,6 +982,10 @@ static int usbhsf_dma_prepare_pop_with_usb_dmac(struct usbhs_pkt *pkt, | |||
| 982 | if ((uintptr_t)pkt->buf & (USBHS_USB_DMAC_XFER_SIZE - 1)) | 982 | if ((uintptr_t)pkt->buf & (USBHS_USB_DMAC_XFER_SIZE - 1)) |
| 983 | goto usbhsf_pio_prepare_pop; | 983 | goto usbhsf_pio_prepare_pop; |
| 984 | 984 | ||
| 985 | /* return at this time if the pipe is running */ | ||
| 986 | if (usbhs_pipe_is_running(pipe)) | ||
| 987 | return 0; | ||
| 988 | |||
| 985 | usbhs_pipe_config_change_bfre(pipe, 1); | 989 | usbhs_pipe_config_change_bfre(pipe, 1); |
| 986 | 990 | ||
| 987 | ret = usbhsf_fifo_select(pipe, fifo, 0); | 991 | ret = usbhsf_fifo_select(pipe, fifo, 0); |
| @@ -1172,6 +1176,7 @@ static int usbhsf_dma_pop_done_with_usb_dmac(struct usbhs_pkt *pkt, | |||
| 1172 | usbhsf_fifo_clear(pipe, fifo); | 1176 | usbhsf_fifo_clear(pipe, fifo); |
| 1173 | pkt->actual = usbhs_dma_calc_received_size(pkt, chan, rcv_len); | 1177 | pkt->actual = usbhs_dma_calc_received_size(pkt, chan, rcv_len); |
| 1174 | 1178 | ||
| 1179 | usbhs_pipe_running(pipe, 0); | ||
| 1175 | usbhsf_dma_stop(pipe, fifo); | 1180 | usbhsf_dma_stop(pipe, fifo); |
| 1176 | usbhsf_dma_unmap(pkt); | 1181 | usbhsf_dma_unmap(pkt); |
| 1177 | usbhsf_fifo_unselect(pipe, pipe->fifo); | 1182 | usbhsf_fifo_unselect(pipe, pipe->fifo); |
diff --git a/drivers/usb/serial/option.c b/drivers/usb/serial/option.c index 5db8ed517e0e..2d8d9150da0c 100644 --- a/drivers/usb/serial/option.c +++ b/drivers/usb/serial/option.c | |||
| @@ -241,6 +241,7 @@ static void option_instat_callback(struct urb *urb); | |||
| 241 | #define QUECTEL_PRODUCT_EC21 0x0121 | 241 | #define QUECTEL_PRODUCT_EC21 0x0121 |
| 242 | #define QUECTEL_PRODUCT_EC25 0x0125 | 242 | #define QUECTEL_PRODUCT_EC25 0x0125 |
| 243 | #define QUECTEL_PRODUCT_BG96 0x0296 | 243 | #define QUECTEL_PRODUCT_BG96 0x0296 |
| 244 | #define QUECTEL_PRODUCT_EP06 0x0306 | ||
| 244 | 245 | ||
| 245 | #define CMOTECH_VENDOR_ID 0x16d8 | 246 | #define CMOTECH_VENDOR_ID 0x16d8 |
| 246 | #define CMOTECH_PRODUCT_6001 0x6001 | 247 | #define CMOTECH_PRODUCT_6001 0x6001 |
| @@ -689,6 +690,10 @@ static const struct option_blacklist_info yuga_clm920_nc5_blacklist = { | |||
| 689 | .reserved = BIT(1) | BIT(4), | 690 | .reserved = BIT(1) | BIT(4), |
| 690 | }; | 691 | }; |
| 691 | 692 | ||
| 693 | static const struct option_blacklist_info quectel_ep06_blacklist = { | ||
| 694 | .reserved = BIT(4) | BIT(5), | ||
| 695 | }; | ||
| 696 | |||
| 692 | static const struct usb_device_id option_ids[] = { | 697 | static const struct usb_device_id option_ids[] = { |
| 693 | { USB_DEVICE(OPTION_VENDOR_ID, OPTION_PRODUCT_COLT) }, | 698 | { USB_DEVICE(OPTION_VENDOR_ID, OPTION_PRODUCT_COLT) }, |
| 694 | { USB_DEVICE(OPTION_VENDOR_ID, OPTION_PRODUCT_RICOLA) }, | 699 | { USB_DEVICE(OPTION_VENDOR_ID, OPTION_PRODUCT_RICOLA) }, |
| @@ -1203,6 +1208,8 @@ static const struct usb_device_id option_ids[] = { | |||
| 1203 | .driver_info = (kernel_ulong_t)&net_intf4_blacklist }, | 1208 | .driver_info = (kernel_ulong_t)&net_intf4_blacklist }, |
| 1204 | { USB_DEVICE(QUECTEL_VENDOR_ID, QUECTEL_PRODUCT_BG96), | 1209 | { USB_DEVICE(QUECTEL_VENDOR_ID, QUECTEL_PRODUCT_BG96), |
| 1205 | .driver_info = (kernel_ulong_t)&net_intf4_blacklist }, | 1210 | .driver_info = (kernel_ulong_t)&net_intf4_blacklist }, |
| 1211 | { USB_DEVICE(QUECTEL_VENDOR_ID, QUECTEL_PRODUCT_EP06), | ||
| 1212 | .driver_info = (kernel_ulong_t)&quectel_ep06_blacklist }, | ||
| 1206 | { USB_DEVICE(CMOTECH_VENDOR_ID, CMOTECH_PRODUCT_6001) }, | 1213 | { USB_DEVICE(CMOTECH_VENDOR_ID, CMOTECH_PRODUCT_6001) }, |
| 1207 | { USB_DEVICE(CMOTECH_VENDOR_ID, CMOTECH_PRODUCT_CMU_300) }, | 1214 | { USB_DEVICE(CMOTECH_VENDOR_ID, CMOTECH_PRODUCT_CMU_300) }, |
| 1208 | { USB_DEVICE(CMOTECH_VENDOR_ID, CMOTECH_PRODUCT_6003), | 1215 | { USB_DEVICE(CMOTECH_VENDOR_ID, CMOTECH_PRODUCT_6003), |
diff --git a/drivers/usb/usbip/stub_dev.c b/drivers/usb/usbip/stub_dev.c index 49e552472c3f..dd8ef36ab10e 100644 --- a/drivers/usb/usbip/stub_dev.c +++ b/drivers/usb/usbip/stub_dev.c | |||
| @@ -73,6 +73,7 @@ static ssize_t usbip_sockfd_store(struct device *dev, struct device_attribute *a | |||
| 73 | goto err; | 73 | goto err; |
| 74 | 74 | ||
| 75 | sdev->ud.tcp_socket = socket; | 75 | sdev->ud.tcp_socket = socket; |
| 76 | sdev->ud.sockfd = sockfd; | ||
| 76 | 77 | ||
| 77 | spin_unlock_irq(&sdev->ud.lock); | 78 | spin_unlock_irq(&sdev->ud.lock); |
| 78 | 79 | ||
| @@ -172,6 +173,7 @@ static void stub_shutdown_connection(struct usbip_device *ud) | |||
| 172 | if (ud->tcp_socket) { | 173 | if (ud->tcp_socket) { |
| 173 | sockfd_put(ud->tcp_socket); | 174 | sockfd_put(ud->tcp_socket); |
| 174 | ud->tcp_socket = NULL; | 175 | ud->tcp_socket = NULL; |
| 176 | ud->sockfd = -1; | ||
| 175 | } | 177 | } |
| 176 | 178 | ||
| 177 | /* 3. free used data */ | 179 | /* 3. free used data */ |
| @@ -266,6 +268,7 @@ static struct stub_device *stub_device_alloc(struct usb_device *udev) | |||
| 266 | sdev->ud.status = SDEV_ST_AVAILABLE; | 268 | sdev->ud.status = SDEV_ST_AVAILABLE; |
| 267 | spin_lock_init(&sdev->ud.lock); | 269 | spin_lock_init(&sdev->ud.lock); |
| 268 | sdev->ud.tcp_socket = NULL; | 270 | sdev->ud.tcp_socket = NULL; |
| 271 | sdev->ud.sockfd = -1; | ||
| 269 | 272 | ||
| 270 | INIT_LIST_HEAD(&sdev->priv_init); | 273 | INIT_LIST_HEAD(&sdev->priv_init); |
| 271 | INIT_LIST_HEAD(&sdev->priv_tx); | 274 | INIT_LIST_HEAD(&sdev->priv_tx); |
diff --git a/drivers/usb/usbip/vhci_hcd.c b/drivers/usb/usbip/vhci_hcd.c index c3e1008aa491..20e3d4609583 100644 --- a/drivers/usb/usbip/vhci_hcd.c +++ b/drivers/usb/usbip/vhci_hcd.c | |||
| @@ -984,6 +984,7 @@ static void vhci_shutdown_connection(struct usbip_device *ud) | |||
| 984 | if (vdev->ud.tcp_socket) { | 984 | if (vdev->ud.tcp_socket) { |
| 985 | sockfd_put(vdev->ud.tcp_socket); | 985 | sockfd_put(vdev->ud.tcp_socket); |
| 986 | vdev->ud.tcp_socket = NULL; | 986 | vdev->ud.tcp_socket = NULL; |
| 987 | vdev->ud.sockfd = -1; | ||
| 987 | } | 988 | } |
| 988 | pr_info("release socket\n"); | 989 | pr_info("release socket\n"); |
| 989 | 990 | ||
| @@ -1030,6 +1031,7 @@ static void vhci_device_reset(struct usbip_device *ud) | |||
| 1030 | if (ud->tcp_socket) { | 1031 | if (ud->tcp_socket) { |
| 1031 | sockfd_put(ud->tcp_socket); | 1032 | sockfd_put(ud->tcp_socket); |
| 1032 | ud->tcp_socket = NULL; | 1033 | ud->tcp_socket = NULL; |
| 1034 | ud->sockfd = -1; | ||
| 1033 | } | 1035 | } |
| 1034 | ud->status = VDEV_ST_NULL; | 1036 | ud->status = VDEV_ST_NULL; |
| 1035 | 1037 | ||
diff --git a/drivers/video/fbdev/geode/video_gx.c b/drivers/video/fbdev/geode/video_gx.c index 6082f653c68a..67773e8bbb95 100644 --- a/drivers/video/fbdev/geode/video_gx.c +++ b/drivers/video/fbdev/geode/video_gx.c | |||
| @@ -127,7 +127,7 @@ void gx_set_dclk_frequency(struct fb_info *info) | |||
| 127 | int timeout = 1000; | 127 | int timeout = 1000; |
| 128 | 128 | ||
| 129 | /* Rev. 1 Geode GXs use a 14 MHz reference clock instead of 48 MHz. */ | 129 | /* Rev. 1 Geode GXs use a 14 MHz reference clock instead of 48 MHz. */ |
| 130 | if (cpu_data(0).x86_mask == 1) { | 130 | if (cpu_data(0).x86_stepping == 1) { |
| 131 | pll_table = gx_pll_table_14MHz; | 131 | pll_table = gx_pll_table_14MHz; |
| 132 | pll_table_len = ARRAY_SIZE(gx_pll_table_14MHz); | 132 | pll_table_len = ARRAY_SIZE(gx_pll_table_14MHz); |
| 133 | } else { | 133 | } else { |
diff --git a/drivers/xen/pvcalls-front.c b/drivers/xen/pvcalls-front.c index 753d9cb437d0..aedbee3b2838 100644 --- a/drivers/xen/pvcalls-front.c +++ b/drivers/xen/pvcalls-front.c | |||
| @@ -60,6 +60,7 @@ struct sock_mapping { | |||
| 60 | bool active_socket; | 60 | bool active_socket; |
| 61 | struct list_head list; | 61 | struct list_head list; |
| 62 | struct socket *sock; | 62 | struct socket *sock; |
| 63 | atomic_t refcount; | ||
| 63 | union { | 64 | union { |
| 64 | struct { | 65 | struct { |
| 65 | int irq; | 66 | int irq; |
| @@ -93,6 +94,32 @@ struct sock_mapping { | |||
| 93 | }; | 94 | }; |
| 94 | }; | 95 | }; |
| 95 | 96 | ||
| 97 | static inline struct sock_mapping *pvcalls_enter_sock(struct socket *sock) | ||
| 98 | { | ||
| 99 | struct sock_mapping *map; | ||
| 100 | |||
| 101 | if (!pvcalls_front_dev || | ||
| 102 | dev_get_drvdata(&pvcalls_front_dev->dev) == NULL) | ||
| 103 | return ERR_PTR(-ENOTCONN); | ||
| 104 | |||
| 105 | map = (struct sock_mapping *)sock->sk->sk_send_head; | ||
| 106 | if (map == NULL) | ||
| 107 | return ERR_PTR(-ENOTSOCK); | ||
| 108 | |||
| 109 | pvcalls_enter(); | ||
| 110 | atomic_inc(&map->refcount); | ||
| 111 | return map; | ||
| 112 | } | ||
| 113 | |||
| 114 | static inline void pvcalls_exit_sock(struct socket *sock) | ||
| 115 | { | ||
| 116 | struct sock_mapping *map; | ||
| 117 | |||
| 118 | map = (struct sock_mapping *)sock->sk->sk_send_head; | ||
| 119 | atomic_dec(&map->refcount); | ||
| 120 | pvcalls_exit(); | ||
| 121 | } | ||
| 122 | |||
| 96 | static inline int get_request(struct pvcalls_bedata *bedata, int *req_id) | 123 | static inline int get_request(struct pvcalls_bedata *bedata, int *req_id) |
| 97 | { | 124 | { |
| 98 | *req_id = bedata->ring.req_prod_pvt & (RING_SIZE(&bedata->ring) - 1); | 125 | *req_id = bedata->ring.req_prod_pvt & (RING_SIZE(&bedata->ring) - 1); |
| @@ -369,31 +396,23 @@ int pvcalls_front_connect(struct socket *sock, struct sockaddr *addr, | |||
| 369 | if (addr->sa_family != AF_INET || sock->type != SOCK_STREAM) | 396 | if (addr->sa_family != AF_INET || sock->type != SOCK_STREAM) |
| 370 | return -EOPNOTSUPP; | 397 | return -EOPNOTSUPP; |
| 371 | 398 | ||
| 372 | pvcalls_enter(); | 399 | map = pvcalls_enter_sock(sock); |
| 373 | if (!pvcalls_front_dev) { | 400 | if (IS_ERR(map)) |
| 374 | pvcalls_exit(); | 401 | return PTR_ERR(map); |
| 375 | return -ENOTCONN; | ||
| 376 | } | ||
| 377 | 402 | ||
| 378 | bedata = dev_get_drvdata(&pvcalls_front_dev->dev); | 403 | bedata = dev_get_drvdata(&pvcalls_front_dev->dev); |
| 379 | 404 | ||
| 380 | map = (struct sock_mapping *)sock->sk->sk_send_head; | ||
| 381 | if (!map) { | ||
| 382 | pvcalls_exit(); | ||
| 383 | return -ENOTSOCK; | ||
| 384 | } | ||
| 385 | |||
| 386 | spin_lock(&bedata->socket_lock); | 405 | spin_lock(&bedata->socket_lock); |
| 387 | ret = get_request(bedata, &req_id); | 406 | ret = get_request(bedata, &req_id); |
| 388 | if (ret < 0) { | 407 | if (ret < 0) { |
| 389 | spin_unlock(&bedata->socket_lock); | 408 | spin_unlock(&bedata->socket_lock); |
| 390 | pvcalls_exit(); | 409 | pvcalls_exit_sock(sock); |
| 391 | return ret; | 410 | return ret; |
| 392 | } | 411 | } |
| 393 | ret = create_active(map, &evtchn); | 412 | ret = create_active(map, &evtchn); |
| 394 | if (ret < 0) { | 413 | if (ret < 0) { |
| 395 | spin_unlock(&bedata->socket_lock); | 414 | spin_unlock(&bedata->socket_lock); |
| 396 | pvcalls_exit(); | 415 | pvcalls_exit_sock(sock); |
| 397 | return ret; | 416 | return ret; |
| 398 | } | 417 | } |
| 399 | 418 | ||
| @@ -423,7 +442,7 @@ int pvcalls_front_connect(struct socket *sock, struct sockaddr *addr, | |||
| 423 | smp_rmb(); | 442 | smp_rmb(); |
| 424 | ret = bedata->rsp[req_id].ret; | 443 | ret = bedata->rsp[req_id].ret; |
| 425 | bedata->rsp[req_id].req_id = PVCALLS_INVALID_ID; | 444 | bedata->rsp[req_id].req_id = PVCALLS_INVALID_ID; |
| 426 | pvcalls_exit(); | 445 | pvcalls_exit_sock(sock); |
| 427 | return ret; | 446 | return ret; |
| 428 | } | 447 | } |
| 429 | 448 | ||
| @@ -488,23 +507,15 @@ int pvcalls_front_sendmsg(struct socket *sock, struct msghdr *msg, | |||
| 488 | if (flags & (MSG_CONFIRM|MSG_DONTROUTE|MSG_EOR|MSG_OOB)) | 507 | if (flags & (MSG_CONFIRM|MSG_DONTROUTE|MSG_EOR|MSG_OOB)) |
| 489 | return -EOPNOTSUPP; | 508 | return -EOPNOTSUPP; |
| 490 | 509 | ||
| 491 | pvcalls_enter(); | 510 | map = pvcalls_enter_sock(sock); |
| 492 | if (!pvcalls_front_dev) { | 511 | if (IS_ERR(map)) |
| 493 | pvcalls_exit(); | 512 | return PTR_ERR(map); |
| 494 | return -ENOTCONN; | ||
| 495 | } | ||
| 496 | bedata = dev_get_drvdata(&pvcalls_front_dev->dev); | 513 | bedata = dev_get_drvdata(&pvcalls_front_dev->dev); |
| 497 | 514 | ||
| 498 | map = (struct sock_mapping *) sock->sk->sk_send_head; | ||
| 499 | if (!map) { | ||
| 500 | pvcalls_exit(); | ||
| 501 | return -ENOTSOCK; | ||
| 502 | } | ||
| 503 | |||
| 504 | mutex_lock(&map->active.out_mutex); | 515 | mutex_lock(&map->active.out_mutex); |
| 505 | if ((flags & MSG_DONTWAIT) && !pvcalls_front_write_todo(map)) { | 516 | if ((flags & MSG_DONTWAIT) && !pvcalls_front_write_todo(map)) { |
| 506 | mutex_unlock(&map->active.out_mutex); | 517 | mutex_unlock(&map->active.out_mutex); |
| 507 | pvcalls_exit(); | 518 | pvcalls_exit_sock(sock); |
| 508 | return -EAGAIN; | 519 | return -EAGAIN; |
| 509 | } | 520 | } |
| 510 | if (len > INT_MAX) | 521 | if (len > INT_MAX) |
| @@ -526,7 +537,7 @@ again: | |||
| 526 | tot_sent = sent; | 537 | tot_sent = sent; |
| 527 | 538 | ||
| 528 | mutex_unlock(&map->active.out_mutex); | 539 | mutex_unlock(&map->active.out_mutex); |
| 529 | pvcalls_exit(); | 540 | pvcalls_exit_sock(sock); |
| 530 | return tot_sent; | 541 | return tot_sent; |
| 531 | } | 542 | } |
| 532 | 543 | ||
| @@ -591,19 +602,11 @@ int pvcalls_front_recvmsg(struct socket *sock, struct msghdr *msg, size_t len, | |||
| 591 | if (flags & (MSG_CMSG_CLOEXEC|MSG_ERRQUEUE|MSG_OOB|MSG_TRUNC)) | 602 | if (flags & (MSG_CMSG_CLOEXEC|MSG_ERRQUEUE|MSG_OOB|MSG_TRUNC)) |
| 592 | return -EOPNOTSUPP; | 603 | return -EOPNOTSUPP; |
| 593 | 604 | ||
| 594 | pvcalls_enter(); | 605 | map = pvcalls_enter_sock(sock); |
| 595 | if (!pvcalls_front_dev) { | 606 | if (IS_ERR(map)) |
| 596 | pvcalls_exit(); | 607 | return PTR_ERR(map); |
| 597 | return -ENOTCONN; | ||
| 598 | } | ||
| 599 | bedata = dev_get_drvdata(&pvcalls_front_dev->dev); | 608 | bedata = dev_get_drvdata(&pvcalls_front_dev->dev); |
| 600 | 609 | ||
| 601 | map = (struct sock_mapping *) sock->sk->sk_send_head; | ||
| 602 | if (!map) { | ||
| 603 | pvcalls_exit(); | ||
| 604 | return -ENOTSOCK; | ||
| 605 | } | ||
| 606 | |||
| 607 | mutex_lock(&map->active.in_mutex); | 610 | mutex_lock(&map->active.in_mutex); |
| 608 | if (len > XEN_FLEX_RING_SIZE(PVCALLS_RING_ORDER)) | 611 | if (len > XEN_FLEX_RING_SIZE(PVCALLS_RING_ORDER)) |
| 609 | len = XEN_FLEX_RING_SIZE(PVCALLS_RING_ORDER); | 612 | len = XEN_FLEX_RING_SIZE(PVCALLS_RING_ORDER); |
| @@ -623,7 +626,7 @@ int pvcalls_front_recvmsg(struct socket *sock, struct msghdr *msg, size_t len, | |||
| 623 | ret = 0; | 626 | ret = 0; |
| 624 | 627 | ||
| 625 | mutex_unlock(&map->active.in_mutex); | 628 | mutex_unlock(&map->active.in_mutex); |
| 626 | pvcalls_exit(); | 629 | pvcalls_exit_sock(sock); |
| 627 | return ret; | 630 | return ret; |
| 628 | } | 631 | } |
| 629 | 632 | ||
| @@ -637,24 +640,16 @@ int pvcalls_front_bind(struct socket *sock, struct sockaddr *addr, int addr_len) | |||
| 637 | if (addr->sa_family != AF_INET || sock->type != SOCK_STREAM) | 640 | if (addr->sa_family != AF_INET || sock->type != SOCK_STREAM) |
| 638 | return -EOPNOTSUPP; | 641 | return -EOPNOTSUPP; |
| 639 | 642 | ||
| 640 | pvcalls_enter(); | 643 | map = pvcalls_enter_sock(sock); |
| 641 | if (!pvcalls_front_dev) { | 644 | if (IS_ERR(map)) |
| 642 | pvcalls_exit(); | 645 | return PTR_ERR(map); |
| 643 | return -ENOTCONN; | ||
| 644 | } | ||
| 645 | bedata = dev_get_drvdata(&pvcalls_front_dev->dev); | 646 | bedata = dev_get_drvdata(&pvcalls_front_dev->dev); |
| 646 | 647 | ||
| 647 | map = (struct sock_mapping *) sock->sk->sk_send_head; | ||
| 648 | if (map == NULL) { | ||
| 649 | pvcalls_exit(); | ||
| 650 | return -ENOTSOCK; | ||
| 651 | } | ||
| 652 | |||
| 653 | spin_lock(&bedata->socket_lock); | 648 | spin_lock(&bedata->socket_lock); |
| 654 | ret = get_request(bedata, &req_id); | 649 | ret = get_request(bedata, &req_id); |
| 655 | if (ret < 0) { | 650 | if (ret < 0) { |
| 656 | spin_unlock(&bedata->socket_lock); | 651 | spin_unlock(&bedata->socket_lock); |
| 657 | pvcalls_exit(); | 652 | pvcalls_exit_sock(sock); |
| 658 | return ret; | 653 | return ret; |
| 659 | } | 654 | } |
| 660 | req = RING_GET_REQUEST(&bedata->ring, req_id); | 655 | req = RING_GET_REQUEST(&bedata->ring, req_id); |
| @@ -684,7 +679,7 @@ int pvcalls_front_bind(struct socket *sock, struct sockaddr *addr, int addr_len) | |||
| 684 | bedata->rsp[req_id].req_id = PVCALLS_INVALID_ID; | 679 | bedata->rsp[req_id].req_id = PVCALLS_INVALID_ID; |
| 685 | 680 | ||
| 686 | map->passive.status = PVCALLS_STATUS_BIND; | 681 | map->passive.status = PVCALLS_STATUS_BIND; |
| 687 | pvcalls_exit(); | 682 | pvcalls_exit_sock(sock); |
| 688 | return 0; | 683 | return 0; |
| 689 | } | 684 | } |
| 690 | 685 | ||
| @@ -695,21 +690,13 @@ int pvcalls_front_listen(struct socket *sock, int backlog) | |||
| 695 | struct xen_pvcalls_request *req; | 690 | struct xen_pvcalls_request *req; |
| 696 | int notify, req_id, ret; | 691 | int notify, req_id, ret; |
| 697 | 692 | ||
| 698 | pvcalls_enter(); | 693 | map = pvcalls_enter_sock(sock); |
| 699 | if (!pvcalls_front_dev) { | 694 | if (IS_ERR(map)) |
| 700 | pvcalls_exit(); | 695 | return PTR_ERR(map); |
| 701 | return -ENOTCONN; | ||
| 702 | } | ||
| 703 | bedata = dev_get_drvdata(&pvcalls_front_dev->dev); | 696 | bedata = dev_get_drvdata(&pvcalls_front_dev->dev); |
| 704 | 697 | ||
| 705 | map = (struct sock_mapping *) sock->sk->sk_send_head; | ||
| 706 | if (!map) { | ||
| 707 | pvcalls_exit(); | ||
| 708 | return -ENOTSOCK; | ||
| 709 | } | ||
| 710 | |||
| 711 | if (map->passive.status != PVCALLS_STATUS_BIND) { | 698 | if (map->passive.status != PVCALLS_STATUS_BIND) { |
| 712 | pvcalls_exit(); | 699 | pvcalls_exit_sock(sock); |
| 713 | return -EOPNOTSUPP; | 700 | return -EOPNOTSUPP; |
| 714 | } | 701 | } |
| 715 | 702 | ||
| @@ -717,7 +704,7 @@ int pvcalls_front_listen(struct socket *sock, int backlog) | |||
| 717 | ret = get_request(bedata, &req_id); | 704 | ret = get_request(bedata, &req_id); |
| 718 | if (ret < 0) { | 705 | if (ret < 0) { |
| 719 | spin_unlock(&bedata->socket_lock); | 706 | spin_unlock(&bedata->socket_lock); |
| 720 | pvcalls_exit(); | 707 | pvcalls_exit_sock(sock); |
| 721 | return ret; | 708 | return ret; |
| 722 | } | 709 | } |
| 723 | req = RING_GET_REQUEST(&bedata->ring, req_id); | 710 | req = RING_GET_REQUEST(&bedata->ring, req_id); |
| @@ -741,7 +728,7 @@ int pvcalls_front_listen(struct socket *sock, int backlog) | |||
| 741 | bedata->rsp[req_id].req_id = PVCALLS_INVALID_ID; | 728 | bedata->rsp[req_id].req_id = PVCALLS_INVALID_ID; |
| 742 | 729 | ||
| 743 | map->passive.status = PVCALLS_STATUS_LISTEN; | 730 | map->passive.status = PVCALLS_STATUS_LISTEN; |
| 744 | pvcalls_exit(); | 731 | pvcalls_exit_sock(sock); |
| 745 | return ret; | 732 | return ret; |
| 746 | } | 733 | } |
| 747 | 734 | ||
| @@ -753,21 +740,13 @@ int pvcalls_front_accept(struct socket *sock, struct socket *newsock, int flags) | |||
| 753 | struct xen_pvcalls_request *req; | 740 | struct xen_pvcalls_request *req; |
| 754 | int notify, req_id, ret, evtchn, nonblock; | 741 | int notify, req_id, ret, evtchn, nonblock; |
| 755 | 742 | ||
| 756 | pvcalls_enter(); | 743 | map = pvcalls_enter_sock(sock); |
| 757 | if (!pvcalls_front_dev) { | 744 | if (IS_ERR(map)) |
| 758 | pvcalls_exit(); | 745 | return PTR_ERR(map); |
| 759 | return -ENOTCONN; | ||
| 760 | } | ||
| 761 | bedata = dev_get_drvdata(&pvcalls_front_dev->dev); | 746 | bedata = dev_get_drvdata(&pvcalls_front_dev->dev); |
| 762 | 747 | ||
| 763 | map = (struct sock_mapping *) sock->sk->sk_send_head; | ||
| 764 | if (!map) { | ||
| 765 | pvcalls_exit(); | ||
| 766 | return -ENOTSOCK; | ||
| 767 | } | ||
| 768 | |||
| 769 | if (map->passive.status != PVCALLS_STATUS_LISTEN) { | 748 | if (map->passive.status != PVCALLS_STATUS_LISTEN) { |
| 770 | pvcalls_exit(); | 749 | pvcalls_exit_sock(sock); |
| 771 | return -EINVAL; | 750 | return -EINVAL; |
| 772 | } | 751 | } |
| 773 | 752 | ||
| @@ -785,13 +764,13 @@ int pvcalls_front_accept(struct socket *sock, struct socket *newsock, int flags) | |||
| 785 | goto received; | 764 | goto received; |
| 786 | } | 765 | } |
| 787 | if (nonblock) { | 766 | if (nonblock) { |
| 788 | pvcalls_exit(); | 767 | pvcalls_exit_sock(sock); |
| 789 | return -EAGAIN; | 768 | return -EAGAIN; |
| 790 | } | 769 | } |
| 791 | if (wait_event_interruptible(map->passive.inflight_accept_req, | 770 | if (wait_event_interruptible(map->passive.inflight_accept_req, |
| 792 | !test_and_set_bit(PVCALLS_FLAG_ACCEPT_INFLIGHT, | 771 | !test_and_set_bit(PVCALLS_FLAG_ACCEPT_INFLIGHT, |
| 793 | (void *)&map->passive.flags))) { | 772 | (void *)&map->passive.flags))) { |
| 794 | pvcalls_exit(); | 773 | pvcalls_exit_sock(sock); |
| 795 | return -EINTR; | 774 | return -EINTR; |
| 796 | } | 775 | } |
| 797 | } | 776 | } |
| @@ -802,7 +781,7 @@ int pvcalls_front_accept(struct socket *sock, struct socket *newsock, int flags) | |||
| 802 | clear_bit(PVCALLS_FLAG_ACCEPT_INFLIGHT, | 781 | clear_bit(PVCALLS_FLAG_ACCEPT_INFLIGHT, |
| 803 | (void *)&map->passive.flags); | 782 | (void *)&map->passive.flags); |
| 804 | spin_unlock(&bedata->socket_lock); | 783 | spin_unlock(&bedata->socket_lock); |
| 805 | pvcalls_exit(); | 784 | pvcalls_exit_sock(sock); |
| 806 | return ret; | 785 | return ret; |
| 807 | } | 786 | } |
| 808 | map2 = kzalloc(sizeof(*map2), GFP_ATOMIC); | 787 | map2 = kzalloc(sizeof(*map2), GFP_ATOMIC); |
| @@ -810,7 +789,7 @@ int pvcalls_front_accept(struct socket *sock, struct socket *newsock, int flags) | |||
| 810 | clear_bit(PVCALLS_FLAG_ACCEPT_INFLIGHT, | 789 | clear_bit(PVCALLS_FLAG_ACCEPT_INFLIGHT, |
| 811 | (void *)&map->passive.flags); | 790 | (void *)&map->passive.flags); |
| 812 | spin_unlock(&bedata->socket_lock); | 791 | spin_unlock(&bedata->socket_lock); |
| 813 | pvcalls_exit(); | 792 | pvcalls_exit_sock(sock); |
| 814 | return -ENOMEM; | 793 | return -ENOMEM; |
| 815 | } | 794 | } |
| 816 | ret = create_active(map2, &evtchn); | 795 | ret = create_active(map2, &evtchn); |
| @@ -819,7 +798,7 @@ int pvcalls_front_accept(struct socket *sock, struct socket *newsock, int flags) | |||
| 819 | clear_bit(PVCALLS_FLAG_ACCEPT_INFLIGHT, | 798 | clear_bit(PVCALLS_FLAG_ACCEPT_INFLIGHT, |
| 820 | (void *)&map->passive.flags); | 799 | (void *)&map->passive.flags); |
| 821 | spin_unlock(&bedata->socket_lock); | 800 | spin_unlock(&bedata->socket_lock); |
| 822 | pvcalls_exit(); | 801 | pvcalls_exit_sock(sock); |
| 823 | return ret; | 802 | return ret; |
| 824 | } | 803 | } |
| 825 | list_add_tail(&map2->list, &bedata->socket_mappings); | 804 | list_add_tail(&map2->list, &bedata->socket_mappings); |
| @@ -841,13 +820,13 @@ int pvcalls_front_accept(struct socket *sock, struct socket *newsock, int flags) | |||
| 841 | /* We could check if we have received a response before returning. */ | 820 | /* We could check if we have received a response before returning. */ |
| 842 | if (nonblock) { | 821 | if (nonblock) { |
| 843 | WRITE_ONCE(map->passive.inflight_req_id, req_id); | 822 | WRITE_ONCE(map->passive.inflight_req_id, req_id); |
| 844 | pvcalls_exit(); | 823 | pvcalls_exit_sock(sock); |
| 845 | return -EAGAIN; | 824 | return -EAGAIN; |
| 846 | } | 825 | } |
| 847 | 826 | ||
| 848 | if (wait_event_interruptible(bedata->inflight_req, | 827 | if (wait_event_interruptible(bedata->inflight_req, |
| 849 | READ_ONCE(bedata->rsp[req_id].req_id) == req_id)) { | 828 | READ_ONCE(bedata->rsp[req_id].req_id) == req_id)) { |
| 850 | pvcalls_exit(); | 829 | pvcalls_exit_sock(sock); |
| 851 | return -EINTR; | 830 | return -EINTR; |
| 852 | } | 831 | } |
| 853 | /* read req_id, then the content */ | 832 | /* read req_id, then the content */ |
| @@ -862,7 +841,7 @@ received: | |||
| 862 | clear_bit(PVCALLS_FLAG_ACCEPT_INFLIGHT, | 841 | clear_bit(PVCALLS_FLAG_ACCEPT_INFLIGHT, |
| 863 | (void *)&map->passive.flags); | 842 | (void *)&map->passive.flags); |
| 864 | pvcalls_front_free_map(bedata, map2); | 843 | pvcalls_front_free_map(bedata, map2); |
| 865 | pvcalls_exit(); | 844 | pvcalls_exit_sock(sock); |
| 866 | return -ENOMEM; | 845 | return -ENOMEM; |
| 867 | } | 846 | } |
| 868 | newsock->sk->sk_send_head = (void *)map2; | 847 | newsock->sk->sk_send_head = (void *)map2; |
| @@ -874,7 +853,7 @@ received: | |||
| 874 | clear_bit(PVCALLS_FLAG_ACCEPT_INFLIGHT, (void *)&map->passive.flags); | 853 | clear_bit(PVCALLS_FLAG_ACCEPT_INFLIGHT, (void *)&map->passive.flags); |
| 875 | wake_up(&map->passive.inflight_accept_req); | 854 | wake_up(&map->passive.inflight_accept_req); |
| 876 | 855 | ||
| 877 | pvcalls_exit(); | 856 | pvcalls_exit_sock(sock); |
| 878 | return ret; | 857 | return ret; |
| 879 | } | 858 | } |
| 880 | 859 | ||
| @@ -965,23 +944,16 @@ __poll_t pvcalls_front_poll(struct file *file, struct socket *sock, | |||
| 965 | struct sock_mapping *map; | 944 | struct sock_mapping *map; |
| 966 | __poll_t ret; | 945 | __poll_t ret; |
| 967 | 946 | ||
| 968 | pvcalls_enter(); | 947 | map = pvcalls_enter_sock(sock); |
| 969 | if (!pvcalls_front_dev) { | 948 | if (IS_ERR(map)) |
| 970 | pvcalls_exit(); | ||
| 971 | return EPOLLNVAL; | 949 | return EPOLLNVAL; |
| 972 | } | ||
| 973 | bedata = dev_get_drvdata(&pvcalls_front_dev->dev); | 950 | bedata = dev_get_drvdata(&pvcalls_front_dev->dev); |
| 974 | 951 | ||
| 975 | map = (struct sock_mapping *) sock->sk->sk_send_head; | ||
| 976 | if (!map) { | ||
| 977 | pvcalls_exit(); | ||
| 978 | return EPOLLNVAL; | ||
| 979 | } | ||
| 980 | if (map->active_socket) | 952 | if (map->active_socket) |
| 981 | ret = pvcalls_front_poll_active(file, bedata, map, wait); | 953 | ret = pvcalls_front_poll_active(file, bedata, map, wait); |
| 982 | else | 954 | else |
| 983 | ret = pvcalls_front_poll_passive(file, bedata, map, wait); | 955 | ret = pvcalls_front_poll_passive(file, bedata, map, wait); |
| 984 | pvcalls_exit(); | 956 | pvcalls_exit_sock(sock); |
| 985 | return ret; | 957 | return ret; |
| 986 | } | 958 | } |
| 987 | 959 | ||
| @@ -995,25 +967,20 @@ int pvcalls_front_release(struct socket *sock) | |||
| 995 | if (sock->sk == NULL) | 967 | if (sock->sk == NULL) |
| 996 | return 0; | 968 | return 0; |
| 997 | 969 | ||
| 998 | pvcalls_enter(); | 970 | map = pvcalls_enter_sock(sock); |
| 999 | if (!pvcalls_front_dev) { | 971 | if (IS_ERR(map)) { |
| 1000 | pvcalls_exit(); | 972 | if (PTR_ERR(map) == -ENOTCONN) |
| 1001 | return -EIO; | 973 | return -EIO; |
| 974 | else | ||
| 975 | return 0; | ||
| 1002 | } | 976 | } |
| 1003 | |||
| 1004 | bedata = dev_get_drvdata(&pvcalls_front_dev->dev); | 977 | bedata = dev_get_drvdata(&pvcalls_front_dev->dev); |
| 1005 | 978 | ||
| 1006 | map = (struct sock_mapping *) sock->sk->sk_send_head; | ||
| 1007 | if (map == NULL) { | ||
| 1008 | pvcalls_exit(); | ||
| 1009 | return 0; | ||
| 1010 | } | ||
| 1011 | |||
| 1012 | spin_lock(&bedata->socket_lock); | 979 | spin_lock(&bedata->socket_lock); |
| 1013 | ret = get_request(bedata, &req_id); | 980 | ret = get_request(bedata, &req_id); |
| 1014 | if (ret < 0) { | 981 | if (ret < 0) { |
| 1015 | spin_unlock(&bedata->socket_lock); | 982 | spin_unlock(&bedata->socket_lock); |
| 1016 | pvcalls_exit(); | 983 | pvcalls_exit_sock(sock); |
| 1017 | return ret; | 984 | return ret; |
| 1018 | } | 985 | } |
| 1019 | sock->sk->sk_send_head = NULL; | 986 | sock->sk->sk_send_head = NULL; |
| @@ -1043,14 +1010,20 @@ int pvcalls_front_release(struct socket *sock) | |||
| 1043 | /* | 1010 | /* |
| 1044 | * We need to make sure that sendmsg/recvmsg on this socket have | 1011 | * We need to make sure that sendmsg/recvmsg on this socket have |
| 1045 | * not started before we've cleared sk_send_head here. The | 1012 | * not started before we've cleared sk_send_head here. The |
| 1046 | * easiest (though not optimal) way to guarantee this is to see | 1013 | * easiest way to guarantee this is to see that no pvcalls |
| 1047 | * that no pvcall (other than us) is in progress. | 1014 | * (other than us) is in progress on this socket. |
| 1048 | */ | 1015 | */ |
| 1049 | while (atomic_read(&pvcalls_refcount) > 1) | 1016 | while (atomic_read(&map->refcount) > 1) |
| 1050 | cpu_relax(); | 1017 | cpu_relax(); |
| 1051 | 1018 | ||
| 1052 | pvcalls_front_free_map(bedata, map); | 1019 | pvcalls_front_free_map(bedata, map); |
| 1053 | } else { | 1020 | } else { |
| 1021 | wake_up(&bedata->inflight_req); | ||
| 1022 | wake_up(&map->passive.inflight_accept_req); | ||
| 1023 | |||
| 1024 | while (atomic_read(&map->refcount) > 1) | ||
| 1025 | cpu_relax(); | ||
| 1026 | |||
| 1054 | spin_lock(&bedata->socket_lock); | 1027 | spin_lock(&bedata->socket_lock); |
| 1055 | list_del(&map->list); | 1028 | list_del(&map->list); |
| 1056 | spin_unlock(&bedata->socket_lock); | 1029 | spin_unlock(&bedata->socket_lock); |
diff --git a/drivers/xen/tmem.c b/drivers/xen/tmem.c index bf13d1ec51f3..04e7b3b29bac 100644 --- a/drivers/xen/tmem.c +++ b/drivers/xen/tmem.c | |||
| @@ -284,6 +284,10 @@ static int tmem_frontswap_store(unsigned type, pgoff_t offset, | |||
| 284 | int pool = tmem_frontswap_poolid; | 284 | int pool = tmem_frontswap_poolid; |
| 285 | int ret; | 285 | int ret; |
| 286 | 286 | ||
| 287 | /* THP isn't supported */ | ||
| 288 | if (PageTransHuge(page)) | ||
| 289 | return -1; | ||
| 290 | |||
| 287 | if (pool < 0) | 291 | if (pool < 0) |
| 288 | return -1; | 292 | return -1; |
| 289 | if (ind64 != ind) | 293 | if (ind64 != ind) |
diff --git a/drivers/xen/xenbus/xenbus.h b/drivers/xen/xenbus/xenbus.h index 149c5e7efc89..092981171df1 100644 --- a/drivers/xen/xenbus/xenbus.h +++ b/drivers/xen/xenbus/xenbus.h | |||
| @@ -76,6 +76,7 @@ struct xb_req_data { | |||
| 76 | struct list_head list; | 76 | struct list_head list; |
| 77 | wait_queue_head_t wq; | 77 | wait_queue_head_t wq; |
| 78 | struct xsd_sockmsg msg; | 78 | struct xsd_sockmsg msg; |
| 79 | uint32_t caller_req_id; | ||
| 79 | enum xsd_sockmsg_type type; | 80 | enum xsd_sockmsg_type type; |
| 80 | char *body; | 81 | char *body; |
| 81 | const struct kvec *vec; | 82 | const struct kvec *vec; |
diff --git a/drivers/xen/xenbus/xenbus_comms.c b/drivers/xen/xenbus/xenbus_comms.c index 5b081a01779d..d239fc3c5e3d 100644 --- a/drivers/xen/xenbus/xenbus_comms.c +++ b/drivers/xen/xenbus/xenbus_comms.c | |||
| @@ -309,6 +309,7 @@ static int process_msg(void) | |||
| 309 | goto out; | 309 | goto out; |
| 310 | 310 | ||
| 311 | if (req->state == xb_req_state_wait_reply) { | 311 | if (req->state == xb_req_state_wait_reply) { |
| 312 | req->msg.req_id = req->caller_req_id; | ||
| 312 | req->msg.type = state.msg.type; | 313 | req->msg.type = state.msg.type; |
| 313 | req->msg.len = state.msg.len; | 314 | req->msg.len = state.msg.len; |
| 314 | req->body = state.body; | 315 | req->body = state.body; |
diff --git a/drivers/xen/xenbus/xenbus_xs.c b/drivers/xen/xenbus/xenbus_xs.c index 3e59590c7254..3f3b29398ab8 100644 --- a/drivers/xen/xenbus/xenbus_xs.c +++ b/drivers/xen/xenbus/xenbus_xs.c | |||
| @@ -227,6 +227,8 @@ static void xs_send(struct xb_req_data *req, struct xsd_sockmsg *msg) | |||
| 227 | req->state = xb_req_state_queued; | 227 | req->state = xb_req_state_queued; |
| 228 | init_waitqueue_head(&req->wq); | 228 | init_waitqueue_head(&req->wq); |
| 229 | 229 | ||
| 230 | /* Save the caller req_id and restore it later in the reply */ | ||
| 231 | req->caller_req_id = req->msg.req_id; | ||
| 230 | req->msg.req_id = xs_request_enter(req); | 232 | req->msg.req_id = xs_request_enter(req); |
| 231 | 233 | ||
| 232 | mutex_lock(&xb_write_mutex); | 234 | mutex_lock(&xb_write_mutex); |
| @@ -310,6 +312,7 @@ static void *xs_talkv(struct xenbus_transaction t, | |||
| 310 | req->num_vecs = num_vecs; | 312 | req->num_vecs = num_vecs; |
| 311 | req->cb = xs_wake_up; | 313 | req->cb = xs_wake_up; |
| 312 | 314 | ||
| 315 | msg.req_id = 0; | ||
| 313 | msg.tx_id = t.id; | 316 | msg.tx_id = t.id; |
| 314 | msg.type = type; | 317 | msg.type = type; |
| 315 | msg.len = 0; | 318 | msg.len = 0; |
