5.4.75-rc1 review
Subsystems (2)
Greg Kroah-Hartman
maintainerPATCH 141/214 usb: cdc-acm: fix cooldown mechanism
In reply to Greg Kroah-HartmanFrom: Jerome Brunet <[email protected]>
commit 38203b8385bf6283537162bde7d499f830964711 upstream.
Commit a4e7279cd1d1 ("cdc-acm: introduce a cool down") is causing regression if there is some USB error, such as -EPROTO.
This has been reported on some samples of the Odroid-N2 using the Combee II Zibgee USB dongle.
Quoted 1 line
struct acm *acm =
container_of(work, struct acm, work)
is incorrect in case of a delayed work and causes warnings, usually from the workqueue:
Quoted 1 line
WARNING: CPU: 0 PID: 0 at kernel/workqueue.c:1474 __queue_work+0x480/0x528.
When this happens, USB eventually stops working completely after a while. Also the ACM_ERROR_DELAY bit is never set, so the cooldown mechanism previously introduced cannot be triggered and acm_submit_read_urb() is never called.
This changes makes the cdc-acm driver use a single delayed work, fixing the pointer arithmetic in acm_softint() and set the ACM_ERROR_DELAY when the cooldown mechanism appear to be needed.
--- drivers/usb/class/cdc-acm.c | 12 +++++------- drivers/usb/class/cdc-acm.h | 3 +-- 2 files changed, 6 insertions(+), 9 deletions(-)
drivers/usb/class/cdc-acm.c +5 -7
@@ -507,6 +507,7 @@ static void acm_read_bulk_callback(struc "%s - cooling babbling device\n", __func__);usb_mark_last_busy (acm->dev);set_bit (rb->index, &acm->urbs_in_error_delay); +set_bit (ACM_ERROR_DELAY , &acm->flags); cooldown = true;break ;default :
@@ -532,7 +533,7 @@ static void acm_read_bulk_callback(strucif (stopped || stalled || cooldown) {if (stalled) -schedule_work (&acm->work); +schedule_delayed_work (&acm->dwork,0 );else if (cooldown)schedule_delayed_work (&acm->dwork,HZ /2 );return ;
@@ -562,13 +563,13 @@ static void acm_write_bulk(struct urb *uacm_write_done (acm, wb);spin_unlock_irqrestore (&acm->write_lock, flags);set_bit (EVENT_TTY_WAKEUP , &acm->flags); -schedule_work (&acm->work); +schedule_delayed_work (&acm->dwork,0 ); }static void acm_softint (struct work_struct *work) {int i; - struct acm *acm = container_of(work, struct acm, work); + struct acm *acm = container_of(work, struct acm, dwork.work);if (test_bit (EVENT_RX_STALL , &acm->flags)) {smp_mb ();/* against acm_suspend() */
@@ -584,7 +585,7 @@ static void acm_softint(struct work_struif (test_and_clear_bit (ACM_ERROR_DELAY , &acm->flags)) {for (i =0 ; i < acm->rx_buflimit; i++)if (test_and_clear_bit (i, &acm->urbs_in_error_delay)) -acm_submit_read_urb (acm, i,GFP_NOIO ); +acm_submit_read_urb (acm, i,GFP_KERNEL ); }if (test_and_clear_bit (EVENT_TTY_WAKEUP , &acm->flags))
@@ -1364,7 +1365,6 @@ made_compressed_probe: acm->ctrlsize = ctrlsize; acm->readsize = readsize; acm->rx_buflimit = num_rx_buf; -INIT_WORK (&acm->work, acm_softint);INIT_DELAYED_WORK (&acm->dwork, acm_softint);init_waitqueue_head (&acm->wioctl);spin_lock_init (&acm->write_lock);
@@ -1574,7 +1574,6 @@ static void acm_disconnect(struct usb_in }acm_kill_urbs (acm); -cancel_work_sync (&acm->work);cancel_delayed_work_sync (&acm->dwork);tty_unregister_device (acm_tty_driver, acm->minor);
@@ -1617,7 +1616,6 @@ static int acm_suspend(struct usb_interfreturn 0 ;acm_kill_urbs (acm); -cancel_work_sync (&acm->work);cancel_delayed_work_sync (&acm->dwork); acm->urbs_in_error_delay =0 ;
drivers/usb/class/cdc-acm.h +1 -2
@@ -112,8 +112,7 @@ struct acm {# define ACM_ERROR_DELAY 3unsigned long urbs_in_error_delay;/* these need to be restarted after a delay */ struct usb_cdc_line_coding line;/* bits, stop, parity */ -struct work_struct work;/* work queue entry for various purposes*/ -struct delayed_work dwork;/* for cool downs needed in error recovery */ +struct delayed_work dwork;/* work queue entry for various purposes */ unsigned int ctrlin;/* input control lines (DCD, DSR, RI, break, overruns) */ unsigned int ctrlout;/* output control lines (DTR, RTS) */ struct async_icount iocount;/* counters for control line changes */
Greg Kroah-Hartman
maintainerPATCH 142/214 usb: typec: tcpm: reset hard_reset_count for any disconnect
In reply to Greg Kroah-HartmanFrom: Li Jun <[email protected]>
commit 2d9c6442a9c81f4f8dee678d0b3c183173ab1e2d upstream.
Current tcpm_detach() only reset hard_reset_count if port->attached is true, this may cause this counter clear is missed if the CC disconnect event is generated after tcpm_port_reset() is done by other events, e.g. VBUS off comes first before CC disconect for a power sink, in that case the first tcpm_detach() will only clear port->attached flag but leave hard_reset_count there because tcpm_port_is_disconnected() is still false, then later tcpm_detach() by CC disconnect will directly return due to port->attached is cleared, finally this will result tcpm will not try hard reset or error recovery for later attach.
ChiYuan reported this issue on his platform with below tcpm trace:
After power sink session setup after hard reset 2 times, detach from the power source and then attach:
[ 4848.046358] VBUS off [ 4848.046384] state change SNK_READY -> SNK_UNATTACHED [ 4848.050908] Setting voltage/current limit 0 mV 0 mA [ 4848.050936] polarity 0 [ 4848.052593] Requesting mux state 0, usb-role 0, orientation 0 [ 4848.053222] Start toggling [ 4848.086500] state change SNK_UNATTACHED -> TOGGLING [ 4848.089983] CC1: 0 -> 0, CC2: 3 -> 3 [state TOGGLING, polarity 0, connected] [ 4848.089993] state change TOGGLING -> SNK_ATTACH_WAIT [ 4848.090031] pending state change SNK_ATTACH_WAIT -> SNK_DEBOUNCED @200 ms [ 4848.141162] CC1: 0 -> 0, CC2: 3 -> 0 [state SNK_ATTACH_WAIT, polarity 0, disconnected] [ 4848.141170] state change SNK_ATTACH_WAIT -> SNK_ATTACH_WAIT [ 4848.141184] pending state change SNK_ATTACH_WAIT -> SNK_UNATTACHED @20 ms [ 4848.163156] state change SNK_ATTACH_WAIT -> SNK_UNATTACHED [delayed 20 ms] [ 4848.163162] Start toggling [ 4848.216918] CC1: 0 -> 0, CC2: 0 -> 3 [state TOGGLING, polarity 0, connected] [ 4848.216954] state change TOGGLING -> SNK_ATTACH_WAIT [ 4848.217080] pending state change SNK_ATTACH_WAIT -> SNK_DEBOUNCED @200 ms [ 4848.231771] CC1: 0 -> 0, CC2: 3 -> 0 [state SNK_ATTACH_WAIT, polarity 0, disconnected] [ 4848.231800] state change SNK_ATTACH_WAIT -> SNK_ATTACH_WAIT [ 4848.231857] pending state change SNK_ATTACH_WAIT -> SNK_UNATTACHED @20 ms [ 4848.256022] state change SNK_ATTACH_WAIT -> SNK_UNATTACHED [delayed20 ms] [ 4848.256049] Start toggling [ 4848.871148] VBUS on [ 4848.885324] CC1: 0 -> 0, CC2: 0 -> 3 [state TOGGLING, polarity 0, connected] [ 4848.885372] state change TOGGLING -> SNK_ATTACH_WAIT [ 4848.885548] pending state change SNK_ATTACH_WAIT -> SNK_DEBOUNCED @200 ms [ 4849.088240] state change SNK_ATTACH_WAIT -> SNK_DEBOUNCED [delayed200 ms] [ 4849.088284] state change SNK_DEBOUNCED -> SNK_ATTACHED [ 4849.088291] polarity 1 [ 4849.088769] Requesting mux state 1, usb-role 2, orientation 2 [ 4849.088895] state change SNK_ATTACHED -> SNK_STARTUP [ 4849.088907] state change SNK_STARTUP -> SNK_DISCOVERY [ 4849.088915] Setting voltage/current limit 5000 mV 0 mA [ 4849.088927] vbus=0 charge:=1 [ 4849.090505] state change SNK_DISCOVERY -> SNK_WAIT_CAPABILITIES [ 4849.090828] pending state change SNK_WAIT_CAPABILITIES -> SNK_READY @240 ms [ 4849.335878] state change SNK_WAIT_CAPABILITIES -> SNK_READY [delayed240 ms]
this patch fix this issue by clear hard_reset_count at any cases of cc disconnect, í.e. don't check port->attached flag.
--- drivers/usb/typec/tcpm/tcpm.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-)
drivers/usb/typec/tcpm/tcpm.c +3 -3
@@ -2723,12 +2723,12 @@ static void tcpm_reset_port(struct tcpm_static void tcpm_detach (struct tcpm_port *port) { -if (!port->attached) -return ; -if (tcpm_port_is_disconnected (port)) port->hard_reset_count =0 ; +if (!port->attached) +return ; +tcpm_reset_port (port); }
Greg Kroah-Hartman
maintainerPATCH 143/214 usb: host: fsl-mph-dr-of: check return of dma_set_mask()
In reply to Greg Kroah-HartmanFrom: Ran Wang <[email protected]>
commit 3cd54a618834430a26a648d880dd83d740f2ae30 upstream.
fsl_usb2_device_register() should stop init if dma_set_mask() return error.
--- drivers/usb/host/fsl-mph-dr-of.c | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-)
drivers/usb/host/fsl-mph-dr-of.c +6 -3
@@ -94,10 +94,13 @@ static struct platform_device *fsl_usb2_ pdev->dev.coherent_dma_mask = ofdev->dev.coherent_dma_mask; -if (!pdev->dev.dma_mask) +if (!pdev->dev.dma_mask) { pdev->dev.dma_mask = &ofdev->dev.coherent_dma_mask; -else -dma_set_mask (&pdev->dev,DMA_BIT_MASK (32 )); + }else { + retval =dma_set_mask (&pdev->dev,DMA_BIT_MASK (32 )); +if (retval) + goto error; + } retval =platform_device_add_data (pdev, pdata,sizeof (*pdata));if (retval)
Greg Kroah-Hartman
maintainerPATCH 144/214 drm/i915: Force VTd workarounds when running as a guest OS
In reply to Greg Kroah-HartmanFrom: Chris Wilson <[email protected]>
commit 8195400f7ea95399f721ad21f4d663a62c65036f upstream.
If i915.ko is being used as a passthrough device, it does not know if the host is using intel_iommu. Mixing the iommu and gfx causes a few issues (such as scanout overfetch) which we need to workaround inside the driver, so if we detect we are running under a hypervisor, also assume the device access is being virtualised.
--- drivers/gpu/drm/i915/i915_drv.h | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-)
drivers/gpu/drm/i915/i915_drv.h +5 -1
@@ -33,6 +33,8 @@#include <uapi/drm/i915_drm.h> #include <uapi/drm/drm_fourcc.h> +#include <asm/hypervisor.h> +#include <linux/io-mapping.h> #include <linux/i2c.h> #include <linux/i2c-algo-bit.h>
@@ -2197,7 +2199,9 @@ static inline bool intel_vtd_active(voidif (intel_iommu_gfx_mapped)return true;#endif -return false; + +/* Running as a guest, we assume the host is enforcing VT'd */ +return !hypervisor_is_type (X86_HYPER_NATIVE ); }static inline bool intel_scanout_needs_vtd_wa (struct drm_i915_private *dev_priv)
Greg Kroah-Hartman
maintainerPATCH 145/214 vt: keyboard, simplify vt_kdgkbsent
In reply to Greg Kroah-HartmanFrom: Jiri Slaby <[email protected]>
commit 6ca03f90527e499dd5e32d6522909e2ad390896b upstream.
Use 'strlen' of the string, add one for NUL terminator and simply do 'copy_to_user' instead of the explicit 'for' loop. This makes the KDGKBSENT case more compact.
The only thing we need to take care about is NULL 'func_table[i]'. Use an empty string in that case.
The original check for overflow could never trigger as the func_buf strings are always shorter or equal to 'struct kbsentry's.
--- drivers/tty/vt/keyboard.c | 28 +++++++++------------------- 1 file changed, 9 insertions(+), 19 deletions(-)
drivers/tty/vt/keyboard.c +9 -19
@@ -1994,9 +1994,7 @@ out:int vt_do_kdgkb_ioctl (int cmd,struct kbsentry __user *user_kdgkb,int perm) {struct kbsentry *kbs; -char *p;u_char *q; -u_char __user *up;int sz, fnw_sz;int delta;char *first_free, *fj, *fnw;
@@ -2022,23 +2020,15 @@ int vt_do_kdgkb_ioctl(int cmd, struct kb i = kbs->kb_func;switch (cmd) { -case KDGKBSENT : - sz =sizeof (kbs->kb_string) -1 ;/* sz should have been -a struct member */ - up = user_kdgkb->kb_string; - p = func_table[i]; -if (p) -for ( ; *p && sz; p++, sz--) -if (put_user (*p, up++)) { - ret = -EFAULT ; - goto reterr; - } -if (put_user ('\0' , up)) { - ret = -EFAULT ; - goto reterr; - } -kfree (kbs); -return ((p && *p) ? -EOVERFLOW :0 ); +case KDGKBSENT : { +/* size should have been a struct member */ +unsigned char *from = func_table[i] ? :"" ; + + ret =copy_to_user (user_kdgkb->kb_string, from, +strlen (from) +1 ) ? -EFAULT :0 ; + + goto reterr; + }case KDSKBSENT :if (!perm) { ret = -EPERM ;
Greg Kroah-Hartman
maintainerPATCH 146/214 vt: keyboard, extend func_buf_lock to readers
In reply to Greg Kroah-HartmanFrom: Jiri Slaby <[email protected]>
commit 82e61c3909db51d91b9d3e2071557b6435018b80 upstream.
Both read-side users of func_table/func_buf need locking. Without that, one can easily confuse the code by repeatedly setting altering strings like:
while (1)
for (a = 0; a < 2; a++) {
struct kbsentry kbs = {};
strcpy((char *)kbs.kb_string, a ? ".\n" : "88888\n");
ioctl(fd, KDSKBSENT, &kbs);
}When that program runs, one can get unexpected output by holding F1 (note the unxpected period on the last line):
.
88888
.8888
So protect all accesses to 'func_table' (and func_buf) by preexisting 'func_buf_lock'.
It is easy in 'k_fn' handler as 'puts_queue' is expected not to sleep. On the other hand, KDGKBSENT needs a local (atomic) copy of the string because copy_to_user can sleep. Use already allocated, but unused 'kbs->kb_string' for that purpose.
Note that the program above needs at least CAP_SYS_TTY_CONFIG.
This depends on the previous patch and on the func_buf_lock lock added in commit 46ca3f735f34 (tty/vt: fix write/write race in ioctl(KDSKBSENT) handler) in 5.2.
Likely fixes CVE-2020-25656.
--- drivers/tty/vt/keyboard.c | 17 +++++++++++++---- 1 file changed, 13 insertions(+), 4 deletions(-)
drivers/tty/vt/keyboard.c +13 -4
@@ -742,8 +742,13 @@ static void k_fn(struct vc_data *vc, unsreturn ;if ((unsigned )value <ARRAY_SIZE (func_table)) { +unsigned long flags; + +spin_lock_irqsave (&func_buf_lock, flags);if (func_table[value])puts_queue (vc, func_table[value]); +spin_unlock_irqrestore (&func_buf_lock, flags); + }else pr_err ("k_fn called with value=%d\n" , value); }
@@ -1990,7 +1995,7 @@ out:#undef s#undef v -/* FIXME: This one needs untangling and locking */ +/* FIXME: This one needs untangling */ int vt_do_kdgkb_ioctl (int cmd,struct kbsentry __user *user_kdgkb,int perm) {struct kbsentry *kbs;
@@ -2022,10 +2027,14 @@ int vt_do_kdgkb_ioctl(int cmd, struct kbswitch (cmd) {case KDGKBSENT : {/* size should have been a struct member */ -unsigned char *from = func_table[i] ? :"" ; +ssize_t len =sizeof (user_kdgkb->kb_string); + +spin_lock_irqsave (&func_buf_lock, flags); + len =strlcpy (kbs->kb_string, func_table[i] ? :"" , len); +spin_unlock_irqrestore (&func_buf_lock, flags); - ret =copy_to_user (user_kdgkb->kb_string, from, -strlen (from) +1 ) ? -EFAULT :0 ; + ret =copy_to_user (user_kdgkb->kb_string, kbs->kb_string, + len +1 ) ? -EFAULT :0 ; goto reterr; }
Greg Kroah-Hartman
maintainerPATCH 147/214 HID: wacom: Avoid entering wacom_wac_pen_report for pad / battery
In reply to Greg Kroah-HartmanFrom: Jason Gerecke <[email protected]>
commit d9216d753b2b1406b801243b12aaf00a5ce5b861 upstream.
It has recently been reported that the "heartbeat" report from devices like the 2nd-gen Intuos Pro (PTH-460, PTH-660, PTH-860) or the 2nd-gen Bluetooth-enabled Intuos tablets (CTL-4100WL, CTL-6100WL) can cause the driver to send a spurious BTN_TOUCH=0 once per second in the middle of drawing. This can result in broken lines while drawing on Chrome OS.
The source of the issue has been traced back to a change which modified the driver to only call wacom_wac_pad_report() once per report instead of once per collection. As part of this change, pad-handling code was removed from wacom_wac_collection() under the assumption that the WACOM_PEN_FIELD and WACOM_TOUCH_FIELD checks would not be satisfied when a pad or battery collection was being processed.
To be clear, the macros WACOM_PAD_FIELD and WACOM_PEN_FIELD do not currently check exclusive conditions. In fact, most "pad" fields will also appear to be "pen" fields simply due to their presence inside of a Digitizer application collection. Because of this, the removal of the check from wacom_wac_collection() just causes pad / battery collections to instead trigger a call to wacom_wac_pen_report() instead. The pen report function in turn resets the tip switch state just prior to exiting, resulting in the observed BTN_TOUCH=0 symptom.
To correct this, we restore a version of the WACOM_PAD_FIELD check in wacom_wac_collection() and return early. This effectively prevents pad / battery collections from being reported until the very end of the report as originally intended.
--- drivers/hid/wacom_wac.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
drivers/hid/wacom_wac.c +3 -1
@@ -2773,7 +2773,9 @@ static int wacom_wac_collection(struct hif (report->type !=HID_INPUT_REPORT )return -1 ; -if (WACOM_PEN_FIELD (field) && wacom->wacom_wac.pen_input) +if (WACOM_PAD_FIELD (field)) +return 0 ; +else if (WACOM_PEN_FIELD (field) && wacom->wacom_wac.pen_input)wacom_wac_pen_report (hdev, report);else if (WACOM_FINGER_FIELD (field) && wacom->wacom_wac.touch_input)wacom_wac_finger_report (hdev, report);
Greg Kroah-Hartman
maintainerPATCH 148/214 udf: Fix memory leak when mounting
In reply to Greg Kroah-HartmanFrom: Jan Kara <[email protected]>
commit a7be300de800e755714c71103ae4a0d205e41e99 upstream.
udf_process_sequence() allocates temporary array for processing partition descriptors on volume which it fails to free. Free the array when it is not needed anymore.
--- fs/udf/super.c | 21 +++++++++++++-------- 1 file changed, 13 insertions(+), 8 deletions(-)
fs/udf/super.c +13 -8
@@ -1703,7 +1703,8 @@ static noinline int udf_process_sequence"Pointers (max %u supported)\n" , UDF_MAX_TD_NESTING);brelse (bh); -return -EIO ; + ret = -EIO ; + goto out; } vdp = (struct volDescPtr *)bh->b_data;
@@ -1723,7 +1724,8 @@ static noinline int udf_process_sequence curr =get_volume_descriptor_record (ident, bh, &data);if (IS_ERR (curr)) {brelse (bh); -return PTR_ERR (curr); + ret =PTR_ERR (curr); + goto out; }/* Descriptor we don't care about? */ if (!curr)
@@ -1745,28 +1747,31 @@ static noinline int udf_process_sequence*/ if (!data.vds[VDS_POS_PRIMARY_VOL_DESC ].block) {udf_err (sb,"Primary Volume Descriptor not found!\n" ); -return -EAGAIN ; + ret = -EAGAIN ; + goto out; } ret =udf_load_pvoldesc (sb, data.vds[VDS_POS_PRIMARY_VOL_DESC ].block);if (ret <0 ) -return ret; + goto out;if (data.vds[VDS_POS_LOGICAL_VOL_DESC ].block) { ret =udf_load_logicalvol (sb, data.vds[VDS_POS_LOGICAL_VOL_DESC ].block, fileset);if (ret <0 ) -return ret; + goto out; }/* Now handle prevailing Partition Descriptors */ for (i =0 ; i < data.num_part_descs; i++) { ret =udf_load_partdesc (sb, data.part_descs_loc[i].rec.block);if (ret <0 ) -return ret; + goto out; } - -return 0 ; + ret =0 ; +out: +kfree (data.part_descs_loc); +return ret; }/*
Greg Kroah-Hartman
maintainerPATCH 149/214 dmaengine: dma-jz4780: Fix race in jz4780_dma_tx_status
In reply to Greg Kroah-HartmanFrom: Paul Cercueil <[email protected]>
commit baf6fd97b16ea8f981b8a8b04039596f32fc2972 upstream.
The jz4780_dma_tx_status() function would check if a channel's cookie state was set to 'completed', and if not, it would enter the critical section. However, in that time frame, the jz4780_dma_chan_irq() function was able to set the cookie to 'completed', and clear the jzchan->vchan pointer, which was deferenced in the critical section of the first function.
Fix this race by checking the channel's cookie state after entering the critical function and not before.
--- drivers/dma/dma-jz4780.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-)
drivers/dma/dma-jz4780.c +4 -3
@@ -639,11 +639,11 @@ static enum dma_status jz4780_dma_tx_staunsigned long flags;unsigned long residue =0 ; +spin_lock_irqsave (&jzchan->vchan.lock, flags); + status =dma_cookie_status (chan, cookie, txstate);if ((status ==DMA_COMPLETE ) || (txstate ==NULL )) -return status; - -spin_lock_irqsave (&jzchan->vchan.lock, flags); + goto out_unlock_irqrestore; vdesc =vchan_find_desc (&jzchan->vchan, cookie);if (vdesc) {
@@ -660,6 +660,7 @@ static enum dma_status jz4780_dma_tx_sta && jzchan->desc->status & (JZ_DMA_DCS_AR | JZ_DMA_DCS_HLT)) status =DMA_ERROR ; +out_unlock_irqrestore:spin_unlock_irqrestore (&jzchan->vchan.lock, flags);return status; }
Greg Kroah-Hartman
maintainerPATCH 150/214 iio:light:si1145: Fix timestamp alignment and prevent data leak.
In reply to Greg Kroah-HartmanFrom: Jonathan Cameron <[email protected]>
commit 0456ecf34d466261970e0ff92b2b9c78a4908637 upstream.
One of a class of bugs pointed out by Lars in a recent review. iio_push_to_buffers_with_timestamp assumes the buffer used is aligned to the size of the timestamp (8 bytes). This is not guaranteed in this driver which uses a 24 byte array of smaller elements on the stack. As Lars also noted this anti pattern can involve a leak of data to userspace and that indeed can happen here. We close both issues by moving to a suitable array in the iio_priv() data with alignment explicitly requested. This data is allocated with kzalloc so no data can leak appart from previous readings.
Depending on the enabled channels, the location of the timestamp can be at various aligned offsets through the buffer. As such we any use of a structure to enforce this alignment would incorrectly suggest a single location for the timestamp. Comments adjusted to express this clearly in the code.
--- drivers/iio/light/si1145.c | 19 +++++++++++-------- 1 file changed, 11 insertions(+), 8 deletions(-)
drivers/iio/light/si1145.c +11 -8
@@ -169,6 +169,7 @@ struct si1145_part_info {* @part_info: Part information * @trig: Pointer to iio trigger * @meas_rate: Value of MEAS_RATE register. Only set in HW in auto mode +* @buffer: Used to pack data read from sensor. */ struct si1145_data {struct i2c_client *client;
@@ -180,6 +181,14 @@ struct si1145_data {bool autonomous;struct iio_trigger *trig;int meas_rate; +/* +* Ensure timestamp will be naturally aligned if present. +* Maximum buffer size (may be only partly used if not all +* channels are enabled): +* 6*2 bytes channels data + 4 bytes alignment + +* 8 bytes timestamp +*/ +u8 buffer[24 ]__aligned(8) ; };/**
@@ -441,12 +450,6 @@ static irqreturn_t si1145_trigger_handlestruct iio_poll_func *pf = private;struct iio_dev *indio_dev = pf->indio_dev;struct si1145_data *data =iio_priv (indio_dev); -/* -* Maximum buffer size: -* 6*2 bytes channels data + 4 bytes alignment + -* 8 bytes timestamp -*/ -u8 buffer[24 ];int i, j =0 ;int ret;u8 irq_status =0 ;
@@ -479,7 +482,7 @@ static irqreturn_t si1145_trigger_handle ret =i2c_smbus_read_i2c_block_data_or_emulated ( data->client, indio_dev->channels[i].address, -sizeof (u16) * run, &buffer[j]); +sizeof (u16) * run, &data->buffer[j]);if (ret <0 ) goto done; j += run *sizeof (u16);
@@ -494,7 +497,7 @@ static irqreturn_t si1145_trigger_handle goto done; } -iio_push_to_buffers_with_timestamp (indio_dev, buffer, +iio_push_to_buffers_with_timestamp (indio_dev, data->buffer,iio_get_time_ns (indio_dev)); done:
Greg Kroah-Hartman
maintainerPATCH 151/214 iio: adc: gyroadc: fix leak of device node iterator
In reply to Greg Kroah-HartmanFrom: Tobias Jordan <[email protected]>
commit da4410d4078ba4ead9d6f1027d6db77c5a74ecee upstream.
Add missing of_node_put calls when exiting the for_each_child_of_node loop in rcar_gyroadc_parse_subdevs early.
Also add goto-exception handling for the error paths in that loop.
--- drivers/iio/adc/rcar-gyroadc.c | 21 +++++++++++++++------ 1 file changed, 15 insertions(+), 6 deletions(-)
drivers/iio/adc/rcar-gyroadc.c +15 -6
@@ -357,7 +357,7 @@ static int rcar_gyroadc_parse_subdevs(st num_channels =ARRAY_SIZE (rcar_gyroadc_iio_channels_3);break ;default : -return -EINVAL ; + goto err_e_inval; }/*
@@ -374,7 +374,7 @@ static int rcar_gyroadc_parse_subdevs(stdev_err (dev,"Failed to get child reg property of ADC \"%pOFn\".\n" , child); -return ret; + goto err_of_node_put; }/* Channel number is too high. */
@@ -382,7 +382,7 @@ static int rcar_gyroadc_parse_subdevs(stdev_err (dev,"Only %i channels supported with %pOFn, but reg = <%i>.\n" , num_channels, child, reg); -return -EINVAL ; + goto err_e_inval; } }
@@ -391,7 +391,7 @@ static int rcar_gyroadc_parse_subdevs(stdev_err (dev,"Channel %i uses different ADC mode than the rest.\n" , reg); -return -EINVAL ; + goto err_e_inval; }/* Channel is valid, grab the regulator. */
@@ -401,7 +401,8 @@ static int rcar_gyroadc_parse_subdevs(stif (IS_ERR (vref)) {dev_dbg (dev,"Channel %i 'vref' supply not connected.\n" , reg); -return PTR_ERR (vref); + ret =PTR_ERR (vref); + goto err_of_node_put; } priv->vref[reg] = vref;
@@ -425,8 +426,10 @@ static int rcar_gyroadc_parse_subdevs(st* attached to the GyroADC at a time, so if we found it, * we can stop parsing here. */ -if (childmode ==RCAR_GYROADC_MODE_SELECT_1_MB88101A ) +if (childmode ==RCAR_GYROADC_MODE_SELECT_1_MB88101A ) { +of_node_put (child);break ; + } }if (first) {
@@ -435,6 +438,12 @@ static int rcar_gyroadc_parse_subdevs(st }return 0 ; + +err_e_inval: + ret = -EINVAL ; +err_of_node_put: +of_node_put (child); +return ret; }static void rcar_gyroadc_deinit_supplies (struct iio_dev *indio_dev)
Greg Kroah-Hartman
maintainerPATCH 152/214 iio:adc:ti-adc0832 Fix alignment issue with timestamp
In reply to Greg Kroah-HartmanFrom: Jonathan Cameron <[email protected]>
commit 39e91f3be4cba51c1560bcda3a343ed1f64dc916 upstream.
One of a class of bugs pointed out by Lars in a recent review. iio_push_to_buffers_with_timestamp assumes the buffer used is aligned to the size of the timestamp (8 bytes). This is not guaranteed in this driver which uses an array of smaller elements on the stack.
We fix this issues by moving to a suitable structure in the iio_priv() data with alignment explicitly requested. This data is allocated with kzalloc so no data can leak apart from previous readings. Note that previously no data could leak 'including' previous readings but I don't think it is an issue to potentially leak them like this now does.
In this case the postioning of the timestamp is depends on what other channels are enabled. As such we cannot use a structure to make the alignment explicit as it would be missleading by suggesting only one possible location for the timestamp.
--- drivers/iio/adc/ti-adc0832.c | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-)
drivers/iio/adc/ti-adc0832.c +8 -3
@@ -28,6 +28,12 @@ struct adc0832 {struct regulator *reg;struct mutex lock;u8 mux_bits; +/* +* Max size needed: 16x 1 byte ADC data + 8 bytes timestamp +* May be shorter if not all channels are enabled subject +* to the timestamp remaining 8 byte aligned. +*/ +u8 data[24 ]__aligned(8) ;u8 tx_buf[2 ]____cacheline_aligned ;u8 rx_buf[2 ];
@@ -199,7 +205,6 @@ static irqreturn_t adc0832_trigger_handlstruct iio_poll_func *pf = p;struct iio_dev *indio_dev = pf->indio_dev;struct adc0832 *adc =iio_priv (indio_dev); -u8 data[24 ] = { };/* 16x 1 byte ADC data + 8 bytes timestamp */ int scan_index;int i =0 ;
@@ -217,10 +222,10 @@ static irqreturn_t adc0832_trigger_handl goto out; } - data[i] = ret; + adc->data[i] = ret; i++; } -iio_push_to_buffers_with_timestamp (indio_dev, data, +iio_push_to_buffers_with_timestamp (indio_dev, adc->data,iio_get_time_ns (indio_dev)); out:mutex_unlock (&adc->lock);
Greg Kroah-Hartman
maintainerPATCH 153/214 iio:adc:ti-adc12138 Fix alignment issue with timestamp
In reply to Greg Kroah-HartmanFrom: Jonathan Cameron <[email protected]>
commit 293e809b2e8e608b65a949101aaf7c0bd1224247 upstream.
One of a class of bugs pointed out by Lars in a recent review. iio_push_to_buffers_with_timestamp assumes the buffer used is aligned to the size of the timestamp (8 bytes). This is not guaranteed in this driver which uses an array of smaller elements on the stack.
We move to a suitable structure in the iio_priv() data with alignment explicitly requested. This data is allocated with kzalloc so no data can leak apart from previous readings. Note that previously no leak at all could occur, but previous readings should never be a problem.
In this case the timestamp location depends on what other channels are enabled. As such we can't use a structure without misleading by suggesting only one possible timestamp location.
--- drivers/iio/adc/ti-adc12138.c | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-)
drivers/iio/adc/ti-adc12138.c +9 -4
@@ -47,6 +47,12 @@ struct adc12138 {struct completion complete;/* The number of cclk periods for the S/H's acquisition time */ unsigned int acquisition_time; +/* +* Maximum size needed: 16x 2 bytes ADC data + 8 bytes timestamp. +* Less may be need if not all channels are enabled, as long as +* the 8 byte alignment of the timestamp is maintained. +*/ +__be16 data[20 ]__aligned(8) ;u8 tx_buf[2 ]____cacheline_aligned ;u8 rx_buf[2 ];
@@ -329,7 +335,6 @@ static irqreturn_t adc12138_trigger_handstruct iio_poll_func *pf = p;struct iio_dev *indio_dev = pf->indio_dev;struct adc12138 *adc =iio_priv (indio_dev); -__be16 data[20 ] = { };/* 16x 2 bytes ADC data + 8 bytes timestamp */ __be16 trash;int ret;int scan_index;
@@ -345,7 +350,7 @@ static irqreturn_t adc12138_trigger_handreinit_completion (&adc->complete); ret =adc12138_start_and_read_conv (adc, scan_chan, - i ? &data[i -1 ] : &trash); + i ? &adc->data[i -1 ] : &trash);if (ret) {dev_warn (&adc->spi->dev,"failed to start conversion\n" );
@@ -362,7 +367,7 @@ static irqreturn_t adc12138_trigger_hand }if (i) { - ret =adc12138_read_conv_data (adc, &data[i -1 ]); + ret =adc12138_read_conv_data (adc, &adc->data[i -1 ]);if (ret) {dev_warn (&adc->spi->dev,"failed to get conversion data\n" );
@@ -370,7 +375,7 @@ static irqreturn_t adc12138_trigger_hand } } -iio_push_to_buffers_with_timestamp (indio_dev, data, +iio_push_to_buffers_with_timestamp (indio_dev, adc->data,iio_get_time_ns (indio_dev)); out:mutex_unlock (&adc->lock);
Greg Kroah-Hartman
maintainerPATCH 154/214 iio:gyro:itg3200: Fix timestamp alignment and prevent data leak.
In reply to Greg Kroah-HartmanFrom: Jonathan Cameron <[email protected]>
commit 10ab7cfd5522f0041028556dac864a003e158556 upstream.
One of a class of bugs pointed out by Lars in a recent review. iio_push_to_buffers_with_timestamp assumes the buffer used is aligned to the size of the timestamp (8 bytes). This is not guaranteed in this driver which uses a 16 byte array of smaller elements on the stack. This is fixed by using an explicit c structure. As there are no holes in the structure, there is no possiblity of data leakage in this case.
The explicit alignment of ts is not strictly necessary but potentially makes the code slightly less fragile. It also removes the possibility of this being cut and paste into another driver where the alignment isn't already true.
--- drivers/iio/gyro/itg3200_buffer.c | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-)
drivers/iio/gyro/itg3200_buffer.c +10 -3
@@ -46,13 +46,20 @@ static irqreturn_t itg3200_trigger_handlstruct iio_poll_func *pf = p;struct iio_dev *indio_dev = pf->indio_dev;struct itg3200 *st =iio_priv (indio_dev); -__be16 buf[ITG3200_SCAN_ELEMENTS +sizeof (s64)/sizeof (u16)]; +/* +* Ensure correct alignment and padding including for the +* timestamp that may be inserted. +*/ +struct { +__be16 buf[ITG3200_SCAN_ELEMENTS ]; +s64 ts__aligned(8) ; + } scan; -int ret =itg3200_read_all_channels (st->i2c, buf); +int ret =itg3200_read_all_channels (st->i2c, scan.buf);if (ret <0 ) goto error_ret; -iio_push_to_buffers_with_timestamp (indio_dev, buf, pf->timestamp); +iio_push_to_buffers_with_timestamp (indio_dev, &scan, pf->timestamp);iio_trigger_notify_done (indio_dev->trig);
Greg Kroah-Hartman
maintainerPATCH 155/214 powerpc/drmem: Make lmb_size 64 bit
In reply to Greg Kroah-HartmanFrom: Aneesh Kumar K.V <[email protected]>
commit ec72024e35dddb88a81e40071c87ceb18b5ee835 upstream.
Similar to commit 89c140bbaeee ("pseries: Fix 64 bit logical memory block panic") make sure different variables tracking lmb_size are updated to be 64 bit.
This was found by code audit.
--- arch/powerpc/include/asm/drmem.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
arch/powerpc/include/asm/drmem.h +2 -2
@@ -20,7 +20,7 @@ struct drmem_lmb {struct drmem_lmb_info {struct drmem_lmb *lmbs;int n_lmbs; -u32 lmb_size; +u64 lmb_size; };extern struct drmem_lmb_info *drmem_info;
@@ -79,7 +79,7 @@ struct of_drconf_cell_v2 {#define DRCONF_MEM_AI_INVALID 0x00000040#define DRCONF_MEM_RESERVED 0x00000080 -static inline u32 drmem_lmb_size (void ) +static inline u64 drmem_lmb_size (void ) {return drmem_info->lmb_size; }
Greg Kroah-Hartman
maintainerPATCH 156/214 MIPS: DEC: Restore bootmem reservation for firmware working memory area
In reply to Greg Kroah-HartmanFrom: Maciej W. Rozycki <[email protected]>
commit cf3af0a4d3b62ab48e0b90180ea161d0f5d4953f upstream.
Fix a crash on DEC platforms starting with:
VFS: Mounted root (nfs filesystem) on device 0:11. Freeing unused PROM memory: 124k freed
BUG: Bad page state in process swapper pfn:00001
page:(ptrval) refcount:0 mapcount:-128 mapping:00000000 index:0x1 pfn:0x1
flags: 0x0()
raw: 00000000 00000100 00000122 00000000 00000001 00000000 ffffff7f 00000000
page dumped because: nonzero mapcount
Modules linked in:
CPU: 0 PID: 1 Comm: swapper Not tainted 5.9.0-00858-g865c50e1d279 #1
Stack : 8065dc48 0000000b 8065d2b8 9bc27dcc 80645bfc 9bc259a4 806a1b97 80703124
80710000 8064a900 00000001 80099574 806b116c 1000ec00 9bc27d88 806a6f30
00000000 00000000 80645bfc 00000000 31232039 80706ba4 2e392e35 8039f348
2d383538 00000070 0000000a 35363867 00000000 806c2830 80710000 806b0000
80710000 8064a900 00000001 81000000 00000000 00000000 8035af2c 80700000
...
Call Trace:
[<8004bc5c>] show_stack+0x34/0x104
[<8015675c>] bad_page+0xfc/0x128
[<80157714>] free_pcppages_bulk+0x1f4/0x5dc
[<801591cc>] free_unref_page+0xc0/0x130
[<8015cb04>] free_reserved_area+0x144/0x1d8
[<805abd78>] kernel_init+0x20/0x100
[<80046070>] ret_from_kernel_thread+0x14/0x1cDisabling lock debugging due to kernel taint
caused by an attempt to free bootmem space that as from
commit b93ddc4f9156 ("mips: Reserve memory for the kernel image resources") has not been anymore reserved due to the removal of generic MIPS arch code that used to reserve all the memory from the beginning of RAM up to the kernel load address.
This memory does need to be reserved on DEC platforms however as it is used by REX firmware as working area, as per the TURBOchannel firmware specification[1]:
Table 2-2 REX Memory Regions
-------------------------------------------------------------------------
Starting Ending
Region Address Address Use
-------------------------------------------------------------------------
0 0xa0000000 0xa000ffff Restart block, exception vectors,
REX stack and bss
1 0xa0010000 0xa0017fff Keyboard or tty drivers
2 0xa0018000 0xa001f3ff 1) CRT driver
3 0xa0020000 0xa002ffff boot, cnfg, init and t objects
4 0xa0020000 0xa002ffff 64KB scratch space
-------------------------------------------------------------------------
1) Note that the last 3 Kbytes of region 2 are reserved for backward compatibility with previous system software.
-------------------------------------------------------------------------
(this table uses KSEG2 unmapped virtual addresses, which in the MIPS architecture are offset from physical addresses by a fixed value of 0xa0000000 and therefore the regions referred do correspond to the beginning of the physical address space) and we call into the firmware on several occasions throughout the bootstrap process. It is believed that pre-REX firmware used with non-TURBOchannel DEC platforms has the same requirements, as hinted by note #1 cited.
Recreate the discarded reservation then, in DEC platform code, removing the crash.
[1] "TURBOchannel Firmware Specification", On-line version, EK-TCAAD-FS-004, Digital Equipment Corporation, January 1993, Chapter 2 "System Module Firmware", p. 2-5
--- arch/mips/dec/setup.c | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-)
arch/mips/dec/setup.c +8 -1
@@ -6,7 +6,7 @@* for more details. * * Copyright (C) 1998 Harald Koerfgen -* Copyright (C) 2000, 2001, 2002, 2003, 2005 Maciej W. Rozycki +* Copyright (C) 2000, 2001, 2002, 2003, 2005, 2020 Maciej W. Rozycki */ #include <linux/console.h> #include <linux/export.h>
@@ -15,6 +15,7 @@#include <linux/ioport.h> #include <linux/irq.h> #include <linux/irqnr.h> +#include <linux/memblock.h> #include <linux/param.h> #include <linux/percpu-defs.h> #include <linux/sched.h>
@@ -22,6 +23,7 @@#include <linux/types.h> #include <linux/pm.h> +#include <asm/addrspace.h> #include <asm/bootinfo.h> #include <asm/cpu.h> #include <asm/cpu-features.h>
@@ -29,7 +31,9 @@#include <asm/irq.h> #include <asm/irq_cpu.h> #include <asm/mipsregs.h> +#include <asm/page.h> #include <asm/reboot.h> +#include <asm/sections.h> #include <asm/time.h> #include <asm/traps.h> #include <asm/wbflush.h>
@@ -166,6 +170,9 @@ void __init plat_mem_setup(void) ioport_resource.start = ~0UL ; ioport_resource.end =0UL ; + +/* Stay away from the firmware working memory area for now. */ +memblock_reserve (PHYS_OFFSET ,__pa_symbol (&_text) -PHYS_OFFSET ); }/*
Greg Kroah-Hartman
maintainerPATCH 157/214 s390/stp: add locking to sysfs functions
In reply to Greg Kroah-HartmanFrom: Sven Schnelle <[email protected]>
commit b3bd02495cb339124f13135d51940cf48d83e5cb upstream.
The sysfs function might race with stp_work_fn. To prevent that, add the required locking. Another issue is that the sysfs functions are checking the stp_online flag, but this flag just holds the user setting whether STP is enabled. Add a flag to clock_sync_flag whether stp_info holds valid data and use that instead.
--- arch/s390/kernel/time.c | 118 ++++++++++++++++++++++++++++++++++-------------- 1 file changed, 85 insertions(+), 33 deletions(-)
arch/s390/kernel/time.c +85 -33
@@ -354,8 +354,9 @@ static DEFINE_PER_CPU(atomic_t, clock_systatic DEFINE_MUTEX (clock_sync_mutex);static unsigned long clock_sync_flags; -#define CLOCK_SYNC_HAS_STP 0 -#define CLOCK_SYNC_STP 1 +#define CLOCK_SYNC_HAS_STP 0 +#define CLOCK_SYNC_STP 1 +#define CLOCK_SYNC_STPINFO_VALID 2/* * The get_clock function for the physical clock. It will get the current
@@ -592,6 +593,22 @@ void stp_queue_work(void)queue_work (time_sync_wq, &stp_work); } +static int __store_stpinfo (void ) +{ +int rc =chsc_sstpi (stp_page, &stp_info,sizeof (struct stp_sstpi )); + +if (rc) +clear_bit (CLOCK_SYNC_STPINFO_VALID , &clock_sync_flags); +else +set_bit (CLOCK_SYNC_STPINFO_VALID , &clock_sync_flags); +return rc; +} + +static int stpinfo_valid (void ) +{ +return stp_online &&test_bit (CLOCK_SYNC_STPINFO_VALID , &clock_sync_flags); +} +static int stp_sync_clock (void *data) {struct clock_sync_data *sync = data;
@@ -613,8 +630,7 @@ static int stp_sync_clock(void *data)if (rc ==0 ) { sync->clock_delta = clock_delta;clock_sync_global (clock_delta); - rc =chsc_sstpi (stp_page, &stp_info, -sizeof (struct stp_sstpi )); + rc =__store_stpinfo ();if (rc ==0 && stp_info.tmd !=2 ) rc = -EAGAIN ; }
@@ -659,7 +675,7 @@ static void stp_work_fn(struct work_struif (rc) goto out_unlock; - rc =chsc_sstpi (stp_page, &stp_info,sizeof (struct stp_sstpi )); + rc =__store_stpinfo ();if (rc || stp_info.c ==0 ) goto out_unlock;
@@ -696,10 +712,14 @@ static ssize_t stp_ctn_id_show(struct destruct device_attribute *attr, char *buf) { -if (!stp_online) -return -ENODATA ; -return sprintf (buf,"%016llx\n" , - *(unsigned long long *) stp_info.ctnid); + ssize_t ret = -ENODATA; + +mutex_lock (&stp_work_mutex); +if (stpinfo_valid ()) + ret =sprintf (buf,"%016llx\n" , + *(unsigned long long *) stp_info.ctnid); +mutex_unlock (&stp_work_mutex); +return ret; } static DEVICE_ATTR(ctn_id, 0400, stp_ctn_id_show, NULL);
@@ -708,9 +728,13 @@ static ssize_t stp_ctn_type_show(structstruct device_attribute *attr, char *buf) { -if (!stp_online) -return -ENODATA ; -return sprintf (buf,"%i\n" , stp_info.ctn); + ssize_t ret = -ENODATA; + +mutex_lock (&stp_work_mutex); +if (stpinfo_valid ()) + ret =sprintf (buf,"%i\n" , stp_info.ctn); +mutex_unlock (&stp_work_mutex); +return ret; } static DEVICE_ATTR(ctn_type, 0400, stp_ctn_type_show, NULL);
@@ -719,9 +743,13 @@ static ssize_t stp_dst_offset_show(strucstruct device_attribute *attr, char *buf) { -if (!stp_online || !(stp_info.vbits &0x2000 )) -return -ENODATA ; -return sprintf (buf,"%i\n" , (int )(s16 ) stp_info.dsto); + ssize_t ret = -ENODATA; + +mutex_lock (&stp_work_mutex); +if (stpinfo_valid () && (stp_info.vbits &0x2000 )) + ret =sprintf (buf,"%i\n" , (int )(s16 ) stp_info.dsto); +mutex_unlock (&stp_work_mutex); +return ret; } static DEVICE_ATTR(dst_offset, 0400, stp_dst_offset_show, NULL);
@@ -730,9 +758,13 @@ static ssize_t stp_leap_seconds_show(strstruct device_attribute *attr, char *buf) { -if (!stp_online || !(stp_info.vbits &0x8000 )) -return -ENODATA ; -return sprintf (buf,"%i\n" , (int )(s16 ) stp_info.leaps); + ssize_t ret = -ENODATA; + +mutex_lock (&stp_work_mutex); +if (stpinfo_valid () && (stp_info.vbits &0x8000 )) + ret =sprintf (buf,"%i\n" , (int )(s16 ) stp_info.leaps); +mutex_unlock (&stp_work_mutex); +return ret; } static DEVICE_ATTR(leap_seconds, 0400, stp_leap_seconds_show, NULL);
@@ -741,9 +773,13 @@ static ssize_t stp_stratum_show(struct dstruct device_attribute *attr, char *buf) { -if (!stp_online) -return -ENODATA ; -return sprintf (buf,"%i\n" , (int )(s16 ) stp_info.stratum); + ssize_t ret = -ENODATA; + +mutex_lock (&stp_work_mutex); +if (stpinfo_valid ()) + ret =sprintf (buf,"%i\n" , (int )(s16 ) stp_info.stratum); +mutex_unlock (&stp_work_mutex); +return ret; } static DEVICE_ATTR(stratum, 0400, stp_stratum_show, NULL);
@@ -752,9 +788,13 @@ static ssize_t stp_time_offset_show(strustruct device_attribute *attr, char *buf) { -if (!stp_online || !(stp_info.vbits &0x0800 )) -return -ENODATA ; -return sprintf (buf,"%i\n" , (int ) stp_info.tto); + ssize_t ret = -ENODATA; + +mutex_lock (&stp_work_mutex); +if (stpinfo_valid () && (stp_info.vbits &0x0800 )) + ret =sprintf (buf,"%i\n" , (int ) stp_info.tto); +mutex_unlock (&stp_work_mutex); +return ret; } static DEVICE_ATTR(time_offset, 0400, stp_time_offset_show, NULL);
@@ -763,9 +803,13 @@ static ssize_t stp_time_zone_offset_showstruct device_attribute *attr, char *buf) { -if (!stp_online || !(stp_info.vbits &0x4000 )) -return -ENODATA ; -return sprintf (buf,"%i\n" , (int )(s16 ) stp_info.tzo); + ssize_t ret = -ENODATA; + +mutex_lock (&stp_work_mutex); +if (stpinfo_valid () && (stp_info.vbits &0x4000 )) + ret =sprintf (buf,"%i\n" , (int )(s16 ) stp_info.tzo); +mutex_unlock (&stp_work_mutex); +return ret; } static DEVICE_ATTR(time_zone_offset, 0400,
@@ -775,9 +819,13 @@ static ssize_t stp_timing_mode_show(strustruct device_attribute *attr, char *buf) { -if (!stp_online) -return -ENODATA ; -return sprintf (buf,"%i\n" , stp_info.tmd); + ssize_t ret = -ENODATA; + +mutex_lock (&stp_work_mutex); +if (stpinfo_valid ()) + ret =sprintf (buf,"%i\n" , stp_info.tmd); +mutex_unlock (&stp_work_mutex); +return ret; } static DEVICE_ATTR(timing_mode, 0400, stp_timing_mode_show, NULL);
@@ -786,9 +834,13 @@ static ssize_t stp_timing_state_show(strstruct device_attribute *attr, char *buf) { -if (!stp_online) -return -ENODATA ; -return sprintf (buf,"%i\n" , stp_info.tst); + ssize_t ret = -ENODATA; + +mutex_lock (&stp_work_mutex); +if (stpinfo_valid ()) + ret =sprintf (buf,"%i\n" , stp_info.tst); +mutex_unlock (&stp_work_mutex); +return ret; } static DEVICE_ATTR(timing_state, 0400, stp_timing_state_show, NULL);
Greg Kroah-Hartman
maintainerPATCH 158/214 powerpc/rtas: Restrict RTAS requests from userspace
In reply to Greg Kroah-HartmanFrom: Andrew Donnellan <[email protected]>
commit bd59380c5ba4147dcbaad3e582b55ccfd120b764 upstream.
A number of userspace utilities depend on making calls to RTAS to retrieve information and update various things.
The existing API through which we expose RTAS to userspace exposes more RTAS functionality than we actually need, through the sys_rtas syscall, which allows root (or anyone with CAP_SYS_ADMIN) to make any RTAS call they want with arbitrary arguments.
Many RTAS calls take the address of a buffer as an argument, and it's up to the caller to specify the physical address of the buffer as an argument. We allocate a buffer (the "RMO buffer") in the Real Memory Area that RTAS can access, and then expose the physical address and size of this buffer in /proc/powerpc/rtas/rmo_buffer. Userspace is expected to read this address, poke at the buffer using /dev/mem, and pass an address in the RMO buffer to the RTAS call.
However, there's nothing stopping the caller from specifying whatever address they want in the RTAS call, and it's easy to construct a series of RTAS calls that can overwrite arbitrary bytes (even without /dev/mem access).
Additionally, there are some RTAS calls that do potentially dangerous things and for which there are no legitimate userspace use cases.
In the past, this would not have been a particularly big deal as it was assumed that root could modify all system state freely, but with Secure Boot and lockdown we need to care about this.
We can't fundamentally change the ABI at this point, however we can address this by implementing a filter that checks RTAS calls against a list of permitted calls and forces the caller to use addresses within the RMO buffer.
The list is based off the list of calls that are used by the librtas userspace library, and has been tested with a number of existing userspace RTAS utilities. For compatibility with any applications we are not aware of that require other calls, the filter can be turned off at build time.
--- arch/powerpc/Kconfig | 13 +++ arch/powerpc/kernel/rtas.c | 153 +++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 166 insertions(+)
arch/powerpc/Kconfig +13 -0
@@ -1024,6 +1024,19 @@ config FSL_RIO Include support for RapidIO controller on Freescale embedded processors (MPC8548, MPC8641, etc). +config PPC_RTAS_FILTER + bool "Enable filtering of RTAS syscalls" + default y + depends on PPC_RTAS + help + The RTAS syscall API has security issues that could be used to + compromise system integrity. This option enforces restrictions on the + RTAS calls and arguments passed by userspace programs to mitigate + these issues. + + Say Y unless you know what you are doing and the filter is causing + problems for you. + endmenu config NONSTATIC_KERNEL
arch/powerpc/kernel/rtas.c +153 -0
177 lines not on this page · raw message
Greg Kroah-Hartman
maintainerPATCH 159/214 powerpc: Warn about use of smt_snooze_delay
In reply to Greg Kroah-HartmanFrom: Joel Stanley <[email protected]>
commit a02f6d42357acf6e5de6ffc728e6e77faf3ad217 upstream.
It's not done anything for a long time. Save the percpu variable, and emit a warning to remind users to not expect it to do anything.
This uses pr_warn_once instead of pr_warn_ratelimit as testing 'ppc64_cpu --smt=off' on a 24 core / 4 SMT system showed the warning to be noisy, as the online/offline loop is slow.
--- arch/powerpc/kernel/sysfs.c | 42 +++++++++++++++++------------------------- 1 file changed, 17 insertions(+), 25 deletions(-)
arch/powerpc/kernel/sysfs.c +17 -25
@@ -31,29 +31,27 @@ static DEFINE_PER_CPU(struct cpu, cpu_devices); -/* -* SMT snooze delay stuff, 64-bit only for now -*/ -#ifdef CONFIG_PPC64 -/* Time in microseconds we delay before sleeping in the idle loop */ -static DEFINE_PER_CPU(long, smt_snooze_delay) = { 100 }; +/* +* Snooze delay has not been hooked up since 3fa8cad82b94 ("powerpc/pseries/cpuidle: +* smt-snooze-delay cleanup.") and has been broken even longer. As was foretold in +* 2014: +* +* "ppc64_util currently utilises it. Once we fix ppc64_util, propose to clean +* up the kernel code." +* +* powerpc-utils stopped using it as of 1.3.8. At some point in the future this +* code should be removed. +*/ static ssize_t store_smt_snooze_delay (struct device *dev,struct device_attribute *attr,const char *buf,size_t count) { - struct cpu *cpu = container_of(dev, struct cpu, dev); -ssize_t ret; -long snooze; - - ret =sscanf (buf,"%ld" , &snooze); -if (ret !=1 ) -return -EINVAL ; - -per_cpu (smt_snooze_delay, cpu->dev.id) = snooze; +pr_warn_once ("%s (%d) stored to unsupported smt_snooze_delay, which has no effect.\n" , + current->comm, current->pid);return count; }
@@ -61,9 +59,9 @@ static ssize_t show_smt_snooze_delay(str struct device_attribute *attr, char *buf) { - struct cpu *cpu = container_of(dev, struct cpu, dev); - -return sprintf (buf,"%ld\n" ,per_cpu (smt_snooze_delay, cpu->dev.id)); + pr_warn_once("%s (%d) read from unsupported smt_snooze_delay\n", + current->comm, current->pid); +return sprintf (buf,"100\n" ); } static DEVICE_ATTR(smt_snooze_delay, 0644, show_smt_snooze_delay,
@@ -71,16 +69,10 @@ static DEVICE_ATTR(smt_snooze_delay, 064static int __init setup_smt_snooze_delay (char *str) { -unsigned int cpu; -long snooze; -if (!cpu_has_feature (CPU_FTR_SMT ))return 1 ; - snooze =simple_strtol (str,NULL ,10 ); -for_each_possible_cpu (cpu) -per_cpu (smt_snooze_delay, cpu) = snooze; - +pr_warn ("smt-snooze-delay command line option has no effect\n" );return 1 ; }__setup ("smt-snooze-delay=" , setup_smt_snooze_delay);
Greg Kroah-Hartman
maintainerPATCH 160/214 powerpc/memhotplug: Make lmb size 64bit
In reply to Greg Kroah-HartmanFrom: Aneesh Kumar K.V <[email protected]>
commit 301d2ea6572386245c5d2d2dc85c3b5a737b85ac upstream.
Similar to commit 89c140bbaeee ("pseries: Fix 64 bit logical memory block panic") make sure different variables tracking lmb_size are updated to be 64 bit.
This was found by code audit.
--- arch/powerpc/platforms/pseries/hotplug-memory.c | 43 ++++++++++++++++-------- 1 file changed, 29 insertions(+), 14 deletions(-)
arch/powerpc/platforms/pseries/hotplug-memory.c +29 -14
@@ -279,7 +279,7 @@ static int dlpar_offline_lmb(struct drmereturn dlpar_change_lmb_state (lmb, false); } -static int pseries_remove_memblock (unsigned long base,unsigned int memblock_size) +static int pseries_remove_memblock (unsigned long base,unsigned long memblock_size) {unsigned long block_sz, start_pfn;int sections_per_block;
@@ -310,10 +310,11 @@ out:static int pseries_remove_mem_node (struct device_node *np) { -const __be32 *regs; +const __be32 *prop;unsigned long base; -unsigned int lmb_size; +unsigned long lmb_size;int ret = -EINVAL ; +int addr_cells, size_cells;/* * Check to see if we are actually removing memory
@@ -324,12 +325,19 @@ static int pseries_remove_mem_node(struc/* * Find the base address and size of the memblock */ - regs =of_get_property (np,"reg" ,NULL ); -if (!regs) + prop =of_get_property (np,"reg" ,NULL ); +if (!prop)return ret; - base =be64_to_cpu (*(unsigned long *)regs); - lmb_size =be32_to_cpu (regs[3 ]); + addr_cells =of_n_addr_cells (np); + size_cells =of_n_size_cells (np); + +/* +* "reg" property represents (addr,size) tuple. +*/ + base =of_read_number (prop, addr_cells); + prop += addr_cells; + lmb_size =of_read_number (prop, size_cells);pseries_remove_memblock (base, lmb_size);return 0 ;
@@ -620,7 +628,7 @@ static int dlpar_memory_remove_by_ic(u32#else static inline int pseries_remove_memblock (unsigned long base, -unsigned int memblock_size) +unsigned long memblock_size) {return -EOPNOTSUPP ; }
@@ -953,10 +961,11 @@ int dlpar_memory(struct pseries_hp_errorstatic int pseries_add_mem_node (struct device_node *np) { -const __be32 *regs; +const __be32 *prop;unsigned long base; -unsigned int lmb_size; +unsigned long lmb_size;int ret = -EINVAL ; +int addr_cells, size_cells;/* * Check to see if we are actually adding memory
@@ -967,12 +976,18 @@ static int pseries_add_mem_node(struct d/* * Find the base and size of the memblock */ - regs =of_get_property (np,"reg" ,NULL ); -if (!regs) + prop =of_get_property (np,"reg" ,NULL ); +if (!prop)return ret; - base =be64_to_cpu (*(unsigned long *)regs); - lmb_size =be32_to_cpu (regs[3 ]); + addr_cells =of_n_addr_cells (np); + size_cells =of_n_size_cells (np); +/* +* "reg" property represents (addr,size) tuple. +*/ + base =of_read_number (prop, addr_cells); + prop += addr_cells; + lmb_size =of_read_number (prop, size_cells);/* * Update memory region to represent the memory add
Greg Kroah-Hartman
maintainerPATCH 161/214 powerpc/powernv/elog: Fix race while processing OPAL error log event.
In reply to Greg Kroah-HartmanFrom: Mahesh Salgaonkar <[email protected]>
commit aea948bb80b478ddc2448f7359d574387521a52d upstream.
Every error log reported by OPAL is exported to userspace through a sysfs interface and notified using kobject_uevent(). The userspace daemon (opal_errd) then reads the error log and acknowledges the error log is saved safely to disk. Once acknowledged the kernel removes the respective sysfs file entry causing respective resources to be released including kobject.
However it's possible the userspace daemon may already be scanning elog entries when a new sysfs elog entry is created by the kernel. User daemon may read this new entry and ack it even before kernel can notify userspace about it through kobject_uevent() call. If that happens then we have a potential race between elog_ack_store->kobject_put() and kobject_uevent which can lead to use-after-free of a kernfs object resulting in a kernel crash. eg:
BUG: Unable to handle kernel data access on read at 0x6b6b6b6b6b6b6bfb
Faulting instruction address: 0xc0000000008ff2a0
Oops: Kernel access of bad area, sig: 11 [#1]
LE PAGE_SIZE=64K MMU=Hash SMP NR_CPUS=2048 NUMA PowerNV
CPU: 27 PID: 805 Comm: irq/29-opal-elo Not tainted 5.9.0-rc2-gcc-8.2.0-00214-g6f56a67bcbb5-dirty #363
...
NIP kobject_uevent_env+0xa0/0x910
LR elog_event+0x1f4/0x2d0
Call Trace:
0x5deadbeef0000122 (unreliable)
elog_event+0x1f4/0x2d0
irq_thread_fn+0x4c/0xc0
irq_thread+0x1c0/0x2b0
kthread+0x1c4/0x1d0
ret_from_kernel_thread+0x5c/0x6cThis patch fixes this race by protecting the sysfs file creation/notification by holding a reference count on kobject until we safely send kobject_uevent().
The function create_elog_obj() returns the elog object which if used by caller function will end up in use-after-free problem again. However, the return value of create_elog_obj() function isn't being used today and there is no need as well. Hence change it to return void to make this fix complete.
--- arch/powerpc/platforms/powernv/opal-elog.c | 33 ++++++++++++++++++++++------- 1 file changed, 26 insertions(+), 7 deletions(-)
arch/powerpc/platforms/powernv/opal-elog.c +26 -7
@@ -179,14 +179,14 @@ static ssize_t raw_attr_read(struct filereturn count; } -static struct elog_obj *create_elog_obj (uint64_t id,size_t size,uint64_t type) +static void create_elog_obj (uint64_t id,size_t size,uint64_t type) {struct elog_obj *elog;int rc; elog =kzalloc (sizeof (*elog),GFP_KERNEL );if (!elog) -return NULL ; +return ; elog->kobj.kset = elog_kset;
@@ -219,18 +219,37 @@ static struct elog_obj *create_elog_obj( rc =kobject_add (&elog->kobj,NULL ,"0x%llx" , id);if (rc) {kobject_put (&elog->kobj); -return NULL ; +return ; } +/* +* As soon as the sysfs file for this elog is created/activated there is +* a chance the opal_errd daemon (or any userspace) might read and +* acknowledge the elog before kobject_uevent() is called. If that +* happens then there is a potential race between +* elog_ack_store->kobject_put() and kobject_uevent() which leads to a +* use-after-free of a kernfs object resulting in a kernel crash. +* +* To avoid that, we need to take a reference on behalf of the bin file, +* so that our reference remains valid while we call kobject_uevent(). +* We then drop our reference before exiting the function, leaving the +* bin file to drop the last reference (if it hasn't already). +*/ + +/* Take a reference for the bin file */ +kobject_get (&elog->kobj); rc =sysfs_create_bin_file (&elog->kobj, &elog->raw_attr); -if (rc) { +if (rc ==0 ) { +kobject_uevent (&elog->kobj,KOBJ_ADD ); + }else { +/* Drop the reference taken for the bin file */ kobject_put (&elog->kobj); -return NULL ; } -kobject_uevent (&elog->kobj,KOBJ_ADD ); +/* Drop our reference */ +kobject_put (&elog->kobj); -return elog; +return ; }static irqreturn_t elog_event (int irq,void *data)
Greg Kroah-Hartman
maintainerPATCH 162/214 powerpc/powermac: Fix low_sleep_handler with KUAP and KUEP
In reply to Greg Kroah-HartmanFrom: Christophe Leroy <[email protected]>
commit 2c637d2df4ee4830e9d3eb2bd5412250522ce96e upstream.
low_sleep_handler() has an hardcoded restore of segment registers that doesn't take KUAP and KUEP into account.
Use head_32's load_segment_registers() routine instead.
--- arch/powerpc/kernel/head_32.S | 2 +- arch/powerpc/platforms/powermac/sleep.S | 9 +-------- 2 files changed, 2 insertions(+), 9 deletions(-)
arch/powerpc/kernel/head_32.S +1 -1
@@ -843,7 +843,7 @@ BEGIN_MMU_FTR_SECTION END_MMU_FTR_SECTION_IFSET(MMU_FTR_USE_HIGH_BATS) blr -load_segment_registers: +_GLOBAL(load_segment_registers) li r0, NUM_USER_SEGMENTS /* load up user segment register values */ mtctr r0 /* for context 0 */ li r3, 0 /* Kp = 0, Ks = 0, VSID = 0 */
arch/powerpc/platforms/powermac/sleep.S +1 -8
@@ -293,14 +293,7 @@ grackle_wake_up: * we do any r1 memory access as we are not sure they * are in a sane state above the first 256Mb region */ - li r0,16 /* load up segment register values */ - mtctr r0 /* for context 0 */ - lis r3,0x2000 /* Ku = 1, VSID = 0 */ - li r4,0 -3: mtsrin r3,r4 - addi r3,r3,0x111 /* increment VSID */ - addis r4,r4,0x1000 /* address of next segment */ - bdnz 3b + bl load_segment_registers sync isync
Greg Kroah-Hartman
maintainerPATCH 163/214 powerpc: Fix undetected data corruption with P9N DD2.1 VSX CI load emulation
In reply to Greg Kroah-HartmanFrom: Michael Neuling <[email protected]>
commit 1da4a0272c5469169f78cd76cf175ff984f52f06 upstream.
__get_user_atomic_128_aligned() stores to kaddr using stvx which is a VMX store instruction, hence kaddr must be 16 byte aligned otherwise the store won't occur as expected.
Unfortunately when we call __get_user_atomic_128_aligned() in p9_hmi_special_emu(), the buffer we pass as kaddr (ie. vbuf) isn't guaranteed to be 16B aligned. This means that the write to vbuf in __get_user_atomic_128_aligned() has the bottom bits of the address truncated. This results in other local variables being overwritten. Also vbuf will not contain the correct data which results in the userspace emulation being wrong and hence undetected user data corruption.
In the past we've been mostly lucky as vbuf has ended up aligned but this is fragile and isn't always true. CONFIG_STACKPROTECTOR in particular can change the stack arrangement enough that our luck runs out.
This issue only occurs on POWER9 Nimbus <= DD2.1 bare metal.
The fix is to align vbuf to a 16 byte boundary.
--- arch/powerpc/kernel/traps.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
arch/powerpc/kernel/traps.c +1 -1
@@ -877,7 +877,7 @@ static void p9_hmi_special_emu(struct pt {unsigned int ra, rb, t, i, sel, instr, rc;const void __user *addr; -u8 vbuf[16 ], *vdst; +u8 vbuf[16 ]__aligned(16) , *vdst;unsigned long ea, msr, msr_mask;bool swap;
Greg Kroah-Hartman
maintainerPATCH 164/214 NFSv4: Wait for stateid updates after CLOSE/OPEN_DOWNGRADE
In reply to Greg Kroah-HartmanFrom: Benjamin Coddington <[email protected]>
commit b4868b44c5628995fdd8ef2e24dda73cef963a75 upstream.
Since commit 0e0cb35b417f ("NFSv4: Handle NFS4ERR_OLD_STATEID in CLOSE/OPEN_DOWNGRADE") the following livelock may occur if a CLOSE races with the update of the nfs_state:
Process 1 Process 2 Server
========= ========= ========
OPEN file
OPEN file
Reply OPEN (1)
Reply OPEN (2)
Update state (1)
CLOSE file (1)
Reply OLD_STATEID (1)
CLOSE file (2)
Reply CLOSE (-1)
Update state (2)
wait for state change
OPEN file
wake
CLOSE file
OPEN file
wake
CLOSE file
...
...We can avoid this situation by not issuing an immediate retry with a bumped seqid when CLOSE/OPEN_DOWNGRADE receives NFS4ERR_OLD_STATEID. Instead, take the same approach used by OPEN and wait at least 5 seconds for outstanding stateid updates to complete if we can detect that we're out of sequence.
Note that after this change it is still possible (though unlikely) that CLOSE waits a full 5 seconds, bumps the seqid, and retries -- and that attempt races with another OPEN at the same time. In order to avoid this race (which would result in the livelock), update nfs_need_update_open_stateid() to handle the case where:
- the state is NFS_OPEN_STATE, and
- the stateid doesn't match the current open stateid
Finally, nfs_need_update_open_stateid() is modified to be idempotent and renamed to better suit the purpose of signaling that the stateid passed is the next stateid in sequence.
--- fs/nfs/nfs4_fs.h | 8 +++++ fs/nfs/nfs4proc.c | 81 ++++++++++++++++++++++++++++++----------------------- fs/nfs/nfs4trace.h | 1 3 files changed, 56 insertions(+), 34 deletions(-)
fs/nfs/nfs4_fs.h +8 -0
@@ -570,6 +570,14 @@ static inline bool nfs4_stateid_is_newerreturn (s32)(be32_to_cpu (s1->seqid) -be32_to_cpu (s2->seqid)) >0 ; } +static inline bool nfs4_stateid_is_next (const nfs4_stateid *s1,const nfs4_stateid *s2) +{ +u32 seq1 =be32_to_cpu (s1->seqid); +u32 seq2 =be32_to_cpu (s2->seqid); + +return seq2 == seq1 +1U || (seq2 ==1U && seq1 ==0xffffffffU ); +} +static inline void nfs4_stateid_seqid_inc (nfs4_stateid *s1) {u32 seqid =be32_to_cpu (s1->seqid);
fs/nfs/nfs4proc.c +47 -34
131 lines not on this page · raw message
fs/nfs/nfs4trace.h +1 -0
@@ -1291,6 +1291,7 @@ DEFINE_NFS4_INODE_STATEID_EVENT(nfs4_setDEFINE_NFS4_INODE_STATEID_EVENT (nfs4_delegreturn);DEFINE_NFS4_INODE_STATEID_EVENT (nfs4_open_stateid_update);DEFINE_NFS4_INODE_STATEID_EVENT (nfs4_open_stateid_update_wait); +DEFINE_NFS4_INODE_STATEID_EVENT (nfs4_close_stateid_update_wait); DECLARE_EVENT_CLASS(nfs4_getattr_event, TP_PROTO(
Greg Kroah-Hartman
maintainerPATCH 165/214 NFSv4.2: support EXCHGID4_FLAG_SUPP_FENCE_OPS 4.2 EXCHANGE_ID flag
In reply to Greg Kroah-HartmanFrom: Olga Kornievskaia <[email protected]>
commit 8c39076c276be0b31982e44654e2c2357473258a upstream.
RFC 7862 introduced a new flag that either client or server is allowed to set: EXCHGID4_FLAG_SUPP_FENCE_OPS.
Client needs to update its bitmask to allow for this flag value.
v2: changed minor version argument to unsigned int
--- fs/nfs/nfs4proc.c | 9 ++++++--- include/uapi/linux/nfs4.h | 3 +++ 2 files changed, 9 insertions(+), 3 deletions(-)
fs/nfs/nfs4proc.c +6 -3
@@ -7859,9 +7859,11 @@ int nfs4_proc_secinfo(struct inode *dir,* both PNFS and NON_PNFS flags set, and not having one of NON_PNFS, PNFS, or * DS flags set. */ -static int nfs4_check_cl_exchange_flags (u32 flags) +static int nfs4_check_cl_exchange_flags (u32 flags,u32 version) { -if (flags & ~EXCHGID4_FLAG_MASK_R ) +if (version >=2 && (flags & ~EXCHGID4_2_FLAG_MASK_R )) + goto out_inval; +else if (version <2 && (flags & ~EXCHGID4_FLAG_MASK_R )) goto out_inval;if ((flags &EXCHGID4_FLAG_USE_PNFS_MDS ) && (flags &EXCHGID4_FLAG_USE_NON_PNFS ))
@@ -8274,7 +8276,8 @@ static int _nfs4_proc_exchange_id(structif (status !=0 ) goto out; - status =nfs4_check_cl_exchange_flags (resp->flags); + status =nfs4_check_cl_exchange_flags (resp->flags, + clp->cl_mvops->minor_version);if (status !=0 ) goto out;
include/uapi/linux/nfs4.h +3 -0
@@ -136,6 +136,8 @@#define EXCHGID4_FLAG_UPD_CONFIRMED_REC_A 0x40000000#define EXCHGID4_FLAG_CONFIRMED_R 0x80000000 + +#define EXCHGID4_FLAG_SUPP_FENCE_OPS 0x00000004/* * Since the validity of these bits depends on whether * they're set in the argument or response, have separate
@@ -143,6 +145,7 @@*/ #define EXCHGID4_FLAG_MASK_A 0x40070103#define EXCHGID4_FLAG_MASK_R 0x80070103 +#define EXCHGID4_2_FLAG_MASK_R 0x80070107#define SEQ4_STATUS_CB_PATH_DOWN 0x00000001#define SEQ4_STATUS_CB_GSS_CONTEXTS_EXPIRING 0x00000002
Greg Kroah-Hartman
maintainerPATCH 166/214 NFSD: Add missing NFSv2 .pc_func methods
In reply to Greg Kroah-HartmanFrom: Chuck Lever <[email protected]>
commit 6b3dccd48de8a4c650b01499a0b09d1e2279649e upstream.
There's no protection in nfsd_dispatch() against a NULL .pc_func helpers. A malicious NFS client can trigger a crash by invoking the unused/unsupported NFSv2 ROOT or WRITECACHE procedures.
The current NFSD dispatcher does not support returning a void reply to a non-NULL procedure, so the reply to both of these is wrong, for the moment.
--- fs/nfsd/nfsproc.c | 16 ++++++++++++++++ 1 file changed, 16 insertions(+)
fs/nfsd/nfsproc.c +16 -0
@@ -118,6 +118,13 @@ done:return nfsd_return_attrs (nfserr, resp); } +/* Obsolete, replaced by MNTPROC_MNT. */ +static __be32 +nfsd_proc_root (struct svc_rqst *rqstp) +{ +return nfs_ok; +} +/* * Look up a path name component * Note: the dentry in the resp->fh may be negative if the file
@@ -203,6 +210,13 @@ nfsd_proc_read(struct svc_rqst *rqstp)return fh_getattr (&resp->fh, &resp->stat); } +/* Reserved */ +static __be32 +nfsd_proc_writecache (struct svc_rqst *rqstp) +{ +return nfs_ok; +} +/* * Write data to a file * N.B. After this call resp->fh needs an fh_put
@@ -617,6 +631,7 @@ static const struct svc_procedure nfsd_p .pc_xdrressize = ST+AT, }, [NFSPROC_ROOT] = { + .pc_func = nfsd_proc_root, .pc_decode = nfssvc_decode_void, .pc_encode = nfssvc_encode_void, .pc_argsize = sizeof(struct nfsd_void),
@@ -654,6 +669,7 @@ static const struct svc_procedure nfsd_p .pc_xdrressize = ST+AT+1+NFSSVC_MAXBLKSIZE_V2/4, }, [NFSPROC_WRITECACHE] = { + .pc_func = nfsd_proc_writecache, .pc_decode = nfssvc_decode_void, .pc_encode = nfssvc_encode_void, .pc_argsize = sizeof(struct nfsd_void),
Greg Kroah-Hartman
maintainerPATCH 167/214 ubifs: dent: Fix some potential memory leaks while iterating entries
In reply to Greg Kroah-HartmanFrom: Zhihao Cheng <[email protected]>
commit 58f6e78a65f1fcbf732f60a7478ccc99873ff3ba upstream.
Fix some potential memory leaks in error handling branches while iterating dent entries. For example, function dbg_check_dir() forgets to free pdent if it exists.
--- fs/ubifs/debug.c | 1 + 1 file changed, 1 insertion(+)
fs/ubifs/debug.c +1 -0
@@ -1123,6 +1123,7 @@ int dbg_check_dir(struct ubifs_info *c, err =PTR_ERR (dent);if (err == -ENOENT )break ; +kfree (pdent);return err; }
Greg Kroah-Hartman
maintainerPATCH 168/214 ubifs: xattr: Fix some potential memory leaks while iterating entries
In reply to Greg Kroah-HartmanFrom: Zhihao Cheng <[email protected]>
commit f2aae745b82c842221f4f233051f9ac641790959 upstream.
Fix some potential memory leaks in error handling branches while iterating xattr entries. For example, function ubifs_tnc_remove_ino() forgets to free pxent if it exists. Similar problems also exist in ubifs_purge_xattrs(), ubifs_add_orphan() and ubifs_jnl_write_inode().
--- fs/ubifs/journal.c | 2 ++ fs/ubifs/orphan.c | 2 ++ fs/ubifs/tnc.c | 3 +++ fs/ubifs/xattr.c | 2 ++ 4 files changed, 9 insertions(+)
fs/ubifs/journal.c +2 -0
@@ -894,6 +894,7 @@ int ubifs_jnl_write_inode(struct ubifs_iif (err == -ENOENT )break ; +kfree (pxent); goto out_release; }
@@ -906,6 +907,7 @@ int ubifs_jnl_write_inode(struct ubifs_iubifs_err (c,"dead directory entry '%s', error %d" , xent->name, err);ubifs_ro_mode (c, err); +kfree (pxent);kfree (xent); goto out_release; }
fs/ubifs/orphan.c +2 -0
@@ -173,6 +173,7 @@ int ubifs_add_orphan(struct ubifs_info * err =PTR_ERR (xent);if (err == -ENOENT )break ; +kfree (pxent);return err; }
@@ -182,6 +183,7 @@ int ubifs_add_orphan(struct ubifs_info * xattr_orphan =orphan_add (c, xattr_inum, orphan);if (IS_ERR (xattr_orphan)) { +kfree (pxent);kfree (xent);return PTR_ERR (xattr_orphan); }
fs/ubifs/tnc.c +3 -0
@@ -2885,6 +2885,7 @@ int ubifs_tnc_remove_ino(struct ubifs_in err =PTR_ERR (xent);if (err == -ENOENT )break ; +kfree (pxent);return err; }
@@ -2898,6 +2899,7 @@ int ubifs_tnc_remove_ino(struct ubifs_infname_len (&nm) =le16_to_cpu (xent->nlen); err =ubifs_tnc_remove_nm (c, &key1, &nm);if (err) { +kfree (pxent);kfree (xent);return err; }
@@ -2906,6 +2908,7 @@ int ubifs_tnc_remove_ino(struct ubifs_inhighest_ino_key (c, &key2, xattr_inum); err =ubifs_tnc_remove_range (c, &key1, &key2);if (err) { +kfree (pxent);kfree (xent);return err; }
fs/ubifs/xattr.c +2 -0
@@ -522,6 +522,7 @@ int ubifs_purge_xattrs(struct inode *hos xent->name, err);ubifs_ro_mode (c, err);kfree (pxent); +kfree (xent);return err; }
@@ -531,6 +532,7 @@ int ubifs_purge_xattrs(struct inode *hos err =remove_xattr (c, host, xino, &nm);if (err) {kfree (pxent); +kfree (xent);iput (xino);ubifs_err (c,"cannot remove xattr, error %d" , err);return err;
Greg Kroah-Hartman
maintainerPATCH 169/214 ubifs: journal: Make sure to not dirty twice for auth nodes
In reply to Greg Kroah-HartmanFrom: Richard Weinberger <[email protected]>
commit 78c7d49f55d8631b67c09f9bfbe8155211a9ea06 upstream.
When removing the last reference of an inode the size of an auth node is already part of write_len. So we must not call ubifs_add_auth_dirt(). Call it only when needed.
--- fs/ubifs/journal.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
fs/ubifs/journal.c +2 -2
@@ -938,8 +938,6 @@ int ubifs_jnl_write_inode(struct ubifs_i inode->i_ino);release_head (c,BASEHD ); -ubifs_add_auth_dirt (c, lnum); -if (last_reference) { err =ubifs_tnc_remove_ino (c, inode->i_ino);if (err)
@@ -949,6 +947,8 @@ int ubifs_jnl_write_inode(struct ubifs_i }else {union ubifs_key key; +ubifs_add_auth_dirt (c, lnum); +ino_key_init (c, &key, inode->i_ino); err =ubifs_tnc_add (c, &key, lnum, offs, ilen, hash); }
Greg Kroah-Hartman
maintainerPATCH 170/214 ubifs: Fix a memleak after dumping authentication mount options
In reply to Greg Kroah-HartmanFrom: Zhihao Cheng <[email protected]>
commit 47f6d9ce45b03a40c34b668a9884754c58122b39 upstream.
Fix a memory leak after dumping authentication mount options in error handling branch.
--- fs/ubifs/super.c | 16 ++++++++++++++-- 1 file changed, 14 insertions(+), 2 deletions(-)
fs/ubifs/super.c +14 -2
@@ -1123,6 +1123,18 @@ static int ubifs_parse_options(struct ubreturn 0 ; } +/* +* ubifs_release_options - release mount parameters which have been dumped. +* @c: UBIFS file-system description object +*/ +static void ubifs_release_options (struct ubifs_info *c) +{ +kfree (c->auth_key_name); + c->auth_key_name =NULL ; +kfree (c->auth_hash_name); + c->auth_hash_name =NULL ; +} +/** * destroy_journal - destroy journal data structures. * @c: UBIFS file-system description object
@@ -1632,8 +1644,7 @@ static void ubifs_umount(struct ubifs_inubifs_lpt_free (c,0 );ubifs_exit_authentication (c); -kfree (c->auth_key_name); -kfree (c->auth_hash_name); +ubifs_release_options (c);kfree (c->cbuf);kfree (c->rcvrd_mst_node);kfree (c->mst_node);
@@ -2201,6 +2212,7 @@ out_umount: out_unlock:mutex_unlock (&c->umount_mutex); out_close: +ubifs_release_options (c);ubi_close_volume (c->ubi); out:return err;
Greg Kroah-Hartman
maintainerPATCH 171/214 ubifs: Dont parse authentication mount options in remount process
In reply to Greg Kroah-HartmanFrom: Zhihao Cheng <[email protected]>
commit bb674a4d4de1032837fcbf860a63939e66f0b7ad upstream.
There is no need to dump authentication options while remounting, because authentication initialization can only be doing once in the first mount process. Dumping authentication mount options in remount process may cause memory leak if UBIFS has already been mounted with old authentication mount options.
--- fs/ubifs/super.c | 18 ++++++++++++------ 1 file changed, 12 insertions(+), 6 deletions(-)
fs/ubifs/super.c +12 -6
@@ -1092,14 +1092,20 @@ static int ubifs_parse_options(struct ubbreak ; }case Opt_auth_key: - c->auth_key_name =kstrdup (args[0 ].from,GFP_KERNEL ); -if (!c->auth_key_name) -return -ENOMEM ; +if (!is_remount) { + c->auth_key_name =kstrdup (args[0 ].from, +GFP_KERNEL ); +if (!c->auth_key_name) +return -ENOMEM ; + }break ;case Opt_auth_hash_name: - c->auth_hash_name =kstrdup (args[0 ].from,GFP_KERNEL ); -if (!c->auth_hash_name) -return -ENOMEM ; +if (!is_remount) { + c->auth_hash_name =kstrdup (args[0 ].from, +GFP_KERNEL ); +if (!c->auth_hash_name) +return -ENOMEM ; + }break ;case Opt_ignore:break ;
Greg Kroah-Hartman
maintainerPATCH 172/214 ubifs: mount_ubifs: Release authentication resource in error handling path
In reply to Greg Kroah-HartmanFrom: Zhihao Cheng <[email protected]>
commit e2a05cc7f8229e150243cdae40f2af9021d67a4a upstream.
Release the authentication related resource in some error handling branches in mount_ubifs().
--- fs/ubifs/super.c | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-)
fs/ubifs/super.c +6 -4
@@ -1313,7 +1313,7 @@ static int mount_ubifs(struct ubifs_info err =ubifs_read_superblock (c);if (err) - goto out_free; + goto out_auth; c->probing =0 ;
@@ -1325,18 +1325,18 @@ static int mount_ubifs(struct ubifs_infoubifs_err (c,"'compressor \"%s\" is not compiled in" ,ubifs_compr_name (c, c->default_compr)); err = -ENOTSUPP ; - goto out_free; + goto out_auth; } err =init_constants_sb (c);if (err) - goto out_free; + goto out_auth; sz =ALIGN (c->max_idx_node_sz, c->min_io_size) *2 ; c->cbuf =kmalloc (sz,GFP_NOFS );if (!c->cbuf) { err = -ENOMEM ; - goto out_free; + goto out_auth; } err =alloc_wbufs (c);
@@ -1611,6 +1611,8 @@ out_wbufs:free_wbufs (c); out_cbuf:kfree (c->cbuf); +out_auth: +ubifs_exit_authentication (c); out_free:kfree (c->write_reserve_buf);kfree (c->bu.buf);
Greg Kroah-Hartman
maintainerPATCH 173/214 perf python scripting: Fix printable strings in python3 scripts
In reply to Greg Kroah-HartmanFrom: Jiri Olsa <[email protected]>
commit 6fcd5ddc3b1467b3586972ef785d0d926ae4cdf4 upstream.
Hagen reported broken strings in python3 tracepoint scripts:
make PYTHON=python3 perf record -e sched:sched_switch -a -- sleep 5 perf script --gen-script py perf script -s ./perf-script.py
[..]
sched__sched_switch 7 563231.759525792 0 swapper prev_comm=bytearray(b'swapper/7\x00\x00\x00\x00\x00\x00\x00'), prev_pid=0, prev_prio=120, prev_state=, next_comm=bytearray(b'mutex-thread-co\x00'),
The problem is in the is_printable_array function that does not take the zero byte into account and claim such string as not printable, so the code will create byte array instead of string.
Committer testing:
After this fix:
sched__sched_switch 3 484522.497072626 1158680 kworker/3:0-eve prev_comm=kworker/3:0, prev_pid=1158680, prev_prio=120, prev_state=I, next_comm=swapper/3, next_pid=0, next_prio=120
Sample: {addr=0, cpu=3, datasrc=84410401, datasrc_decode=N/A|SNP N/A|TLB N/A|LCK N/A, ip=18446744071841817196, period=1, phys_addr=0, pid=1158680, tid=1158680, time=484522497072626, transaction=0, values=[(0, 0)], weight=0}
sched__sched_switch 4 484522.497085610 1225814 perf prev_comm=perf, prev_pid=1225814, prev_prio=120, prev_state=, next_comm=migration/4, next_pid=30, next_prio=0
Sample: {addr=0, cpu=4, datasrc=84410401, datasrc_decode=N/A|SNP N/A|TLB N/A|LCK N/A, ip=18446744071841817196, period=1, phys_addr=0, pid=1225814, tid=1225814, time=484522497085610, transaction=0, values=[(0, 0)], weight=0}
--- tools/perf/util/print_binary.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
tools/perf/util/print_binary.c +1 -1
@@ -50,7 +50,7 @@ int is_printable_array(char *p, unsigned len--; -for (i =0 ; i < len; i++) { +for (i =0 ; i < len && p[i]; i++) {if (!isprint (p[i]) && !isspace (p[i]))return 0 ; }
Greg Kroah-Hartman
maintainerPATCH 174/214 ARC: perf: redo the pct irq missing in device-tree handling
In reply to Greg Kroah-HartmanFrom: Vineet Gupta <[email protected]>
commit 8c42a5c02bec6c7eccf08957be3c6c8fccf9790b upstream.
commit feb92d7d3813456c11dce21 "(ARC: perf: don't bail setup if pct irq missing in device-tree)" introduced a silly brown-paper bag bug:
The assignment and comparison in an if statement were not bracketed correctly leaving the order of evaluation undefined.
|
| if (has_interrupts && (irq = platform_get_irq(pdev, 0) >= 0)) {
| ^^^ ^^^^And given such a chance, the compiler will bite you hard, fully entitled to generating this piece of beauty:
|
| # if (has_interrupts && (irq = platform_get_irq(pdev, 0) >= 0)) {
|
| bl.d @platform_get_irq <-- irq returned in r0
|
| setge r2, r0, 0 <-- r2 is bool 1 or 0 if irq >= 0 true/false
| brlt.d r0, 0, @.L114
|
| st_s r2,[sp] <-- irq saved is bool 1 or 0, not actual return val
| st 1,[r3,160] # arc_pmu.18_29->irq <-- drops bool and assumes 1
|
| # return __request_percpu_irq(irq, handler, 0,
|
| bl.d @__request_percpu_irq;
| mov_s r0,1 <-- drops even bool and assumes 1 which failsWith the snafu fixed, everything is as expected.
| bl.d @platform_get_irq <-- returns irq in r0 | | mov_s r2,r0 | brlt.d r2, 0, @.L112 | | st_s r0,[sp] <-- irq isaved is actual return value above | st r0,[r13,160] #arc_pmu.18_27->irq | | bl.d @__request_percpu_irq <-- r0 unchanged so actual irq returned | add r4,r4,r12 #, tmp363, __ptr
--- arch/arc/kernel/perf_event.c | 29 +++++++++++++++++++---------- 1 file changed, 19 insertions(+), 10 deletions(-)
arch/arc/kernel/perf_event.c +19 -10
@@ -562,7 +562,7 @@ static int arc_pmu_device_probe(struct p {struct arc_reg_pct_build pct_bcr;struct arc_reg_cc_build cc_bcr; -int i, has_interrupts, irq; +int i, has_interrupts, irq =-1 ;int counter_size;/* in bits */ union cc_name {
@@ -637,18 +637,27 @@ static int arc_pmu_device_probe(struct p .attr_groups = arc_pmu->attr_groups, }; -if (has_interrupts && (irq =platform_get_irq (pdev,0 ) >=0 )) { +if (has_interrupts) { + irq =platform_get_irq (pdev,0 ); +if (irq >=0 ) { +int ret; + + arc_pmu->irq = irq; + +/* intc map function ensures irq_set_percpu_devid() called */ + ret =request_percpu_irq (irq, arc_pmu_intr,"ARC perf counters" , +this_cpu_ptr (&arc_pmu_cpu)); + +if (!ret) +on_each_cpu (arc_cpu_pmu_irq_init, &irq,1 ); +else + irq =-1 ; + } - arc_pmu->irq = irq; - -/* intc map function ensures irq_set_percpu_devid() called */ -request_percpu_irq (irq, arc_pmu_intr,"ARC perf counters" , -this_cpu_ptr (&arc_pmu_cpu)); + } -on_each_cpu (arc_cpu_pmu_irq_init, &irq,1 ); - }else { +if (irq ==-1 ) arc_pmu->pmu.capabilities |=PERF_PMU_CAP_NO_INTERRUPT ; - }/* * perf parser doesn't really like '-' symbol in events name, so let's
Greg Kroah-Hartman
maintainerPATCH 175/214 ubi: check kthread_should_stop() after the setting of task state
In reply to Greg Kroah-HartmanFrom: Zhihao Cheng <[email protected]>
commit d005f8c6588efcfbe88099b6edafc6f58c84a9c1 upstream.
A detach hung is possible when a race occurs between the detach process and the ubi background thread. The following sequences outline the race:
ubi thread: if (list_empty(&ubi->works)...
ubi detach: set_bit(KTHREAD_SHOULD_STOP, &kthread->flags)
=> by kthread_stop()
wake_up_process()
=> ubi thread is still running, so 0 is returned
ubi thread: set_current_state(TASK_INTERRUPTIBLE)
schedule()
=> ubi thread will never be scheduled again
ubi detach: wait_for_completion()
=> hung task!
To fix that, we need to check kthread_should_stop() after we set the task state, so the ubi thread will either see the stop bit and exit or the task state is reset to runnable such that it isn't scheduled out indefinitely.
--- drivers/mtd/ubi/wl.c | 13 +++++++++++++ 1 file changed, 13 insertions(+)
drivers/mtd/ubi/wl.c +13 -0
@@ -1629,6 +1629,19 @@ int ubi_thread(void *u) !ubi->thread_enabled || ubi_dbg_is_bgt_disabled(ubi)) {set_current_state (TASK_INTERRUPTIBLE );spin_unlock (&ubi->wl_lock); + +/* +* Check kthread_should_stop() after we set the task +* state to guarantee that we either see the stop bit +* and exit or the task state is reset to runnable such +* that it's not scheduled out indefinitely and detects +* the stop bit at kthread_should_stop(). +*/ +if (kthread_should_stop ()) { +set_current_state (TASK_RUNNING ); +break ; + } +schedule ();continue ; }
Greg Kroah-Hartman
maintainerPATCH 176/214 ia64: fix build error with !COREDUMP
In reply to Greg Kroah-HartmanFrom: Krzysztof Kozlowski <[email protected]>
commit 7404840d87557c4092bf0272bce5e0354c774bf9 upstream.
Fix linkage error when CONFIG_BINFMT_ELF is selected but CONFIG_COREDUMP is not:
ia64-linux-ld: arch/ia64/kernel/elfcore.o: in function `elf_core_write_extra_phdrs':
elfcore.c:(.text+0x172): undefined reference to `dump_emit'
ia64-linux-ld: arch/ia64/kernel/elfcore.o: in function `elf_core_write_extra_data':
elfcore.c:(.text+0x2b2): undefined reference to `dump_emit'
--- arch/ia64/kernel/Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
arch/ia64/kernel/Makefile +1 -1
@@ -41,7 +41,7 @@ obj-y += esi_stub.o # must be in kern endif obj-$(CONFIG_INTEL_IOMMU) += pci-dma.o -obj-$(CONFIG_BINFMT_ELF) += elfcore.o +obj-$(CONFIG_ELF_CORE) += elfcore.o # fp_emulate() expects f2-f5,f16-f31 to contain the user-level state. CFLAGS_traps.o += -mfixed-range=f2-f5,f16-f31
Greg Kroah-Hartman
maintainerPATCH 177/214 rtc: rx8010: dont modify the global rtc ops
In reply to Greg Kroah-HartmanFrom: Bartosz Golaszewski <[email protected]>
commit d3b14296da69adb7825022f3224ac6137eb30abf upstream.
The way the driver is implemented is buggy for the (admittedly unlikely) use case where there are two RTCs with one having an interrupt configured and the second not. This is caused by the fact that we use a global rtc_class_ops struct which we modify depending on whether the irq number is present or not.
Fix it by using two const ops structs with and without alarm operations. While at it: not being able to request a configured interrupt is an error so don't ignore it and bail out of probe().
--- drivers/rtc/rtc-rx8010.c | 24 +++++++++++++++++------- 1 file changed, 17 insertions(+), 7 deletions(-)
drivers/rtc/rtc-rx8010.c +17 -7
@@ -424,16 +424,26 @@ static int rx8010_ioctl(struct device *d } } -static struct rtc_class_ops rx8010_rtc_ops = { +static const struct rtc_class_ops rx8010_rtc_ops_default = { .read_time = rx8010_get_time, .set_time = rx8010_set_time, .ioctl = rx8010_ioctl, }; +static const struct rtc_class_ops rx8010_rtc_ops_alarm = { + .read_time = rx8010_get_time, + .set_time = rx8010_set_time, + .ioctl = rx8010_ioctl, + .read_alarm = rx8010_read_alarm, + .set_alarm = rx8010_set_alarm, + .alarm_irq_enable = rx8010_alarm_irq_enable, +}; +static int rx8010_probe (struct i2c_client *client,const struct i2c_device_id *id) {struct i2c_adapter *adapter = client->adapter; +const struct rtc_class_ops *rtc_ops;struct rx8010_data *rx8010;int err =0 ;
@@ -464,16 +474,16 @@ static int rx8010_probe(struct i2c_clienif (err) {dev_err (&client->dev,"unable to request IRQ\n" ); - client->irq =0 ; - }else { - rx8010_rtc_ops.read_alarm = rx8010_read_alarm; - rx8010_rtc_ops.set_alarm = rx8010_set_alarm; - rx8010_rtc_ops.alarm_irq_enable = rx8010_alarm_irq_enable; +return err; } + + rtc_ops = &rx8010_rtc_ops_alarm; + }else { + rtc_ops = &rx8010_rtc_ops_default; } rx8010->rtc =devm_rtc_device_register (&client->dev, client->name, - &rx8010_rtc_ops,THIS_MODULE ); + rtc_ops,THIS_MODULE );if (IS_ERR (rx8010->rtc)) {dev_err (&client->dev,"unable to register the class device\n" );
Greg Kroah-Hartman
maintainerPATCH 178/214 i2c: imx: Fix external abort on interrupt in exit paths
In reply to Greg Kroah-HartmanFrom: Krzysztof Kozlowski <[email protected]>
commit e50e4f0b85be308a01b830c5fbdffc657e1a6dd0 upstream.
If interrupt comes late, during probe error path or device remove (could be triggered with CONFIG_DEBUG_SHIRQ), the interrupt handler i2c_imx_isr() will access registers with the clock being disabled. This leads to external abort on non-linefetch on Toradex Colibri VF50 module (with Vybrid VF5xx):
Unhandled fault: external abort on non-linefetch (0x1008) at 0x8882d003
Internal error: : 1008 [#1] ARM
Modules linked in:
CPU: 0 PID: 1 Comm: swapper Not tainted 5.7.0 #607
Hardware name: Freescale Vybrid VF5xx/VF6xx (Device Tree)
(i2c_imx_isr) from [<8017009c>] (free_irq+0x25c/0x3b0)
(free_irq) from [<805844ec>] (release_nodes+0x178/0x284)
(release_nodes) from [<80580030>] (really_probe+0x10c/0x348)
(really_probe) from [<80580380>] (driver_probe_device+0x60/0x170)
(driver_probe_device) from [<80580630>] (device_driver_attach+0x58/0x60)
(device_driver_attach) from [<805806bc>] (__driver_attach+0x84/0xc0)
(__driver_attach) from [<8057e228>] (bus_for_each_dev+0x68/0xb4)
(bus_for_each_dev) from [<8057f3ec>] (bus_add_driver+0x144/0x1ec)
(bus_add_driver) from [<80581320>] (driver_register+0x78/0x110)
(driver_register) from [<8010213c>] (do_one_initcall+0xa8/0x2f4)
(do_one_initcall) from [<80c0100c>] (kernel_init_freeable+0x178/0x1dc)
(kernel_init_freeable) from [<80807048>] (kernel_init+0x8/0x110)
(kernel_init) from [<80100114>] (ret_from_fork+0x14/0x20)Additionally, the i2c_imx_isr() could wake up the wait queue (imx_i2c_struct->queue) before its initialization happens.
The resource-managed framework should not be used for interrupt handling, because the resource will be released too late - after disabling clocks. The interrupt handler is not prepared for such case.
--- drivers/i2c/busses/i2c-imx.c | 24 +++++++++++++----------- 1 file changed, 13 insertions(+), 11 deletions(-)
drivers/i2c/busses/i2c-imx.c +13 -11
@@ -1112,14 +1112,6 @@ static int i2c_imx_probe(struct platformreturn ret; } -/* Request IRQ */ - ret =devm_request_irq (&pdev->dev, irq, i2c_imx_isr,IRQF_SHARED , - pdev->name, i2c_imx); -if (ret) { -dev_err (&pdev->dev,"can't claim irq %d\n" , irq); - goto clk_disable; - } -/* Init queue */ init_waitqueue_head (&i2c_imx->queue);
@@ -1138,6 +1130,14 @@ static int i2c_imx_probe(struct platformif (ret <0 ) goto rpm_disable; +/* Request IRQ */ + ret =request_threaded_irq (irq, i2c_imx_isr,NULL ,IRQF_SHARED , + pdev->name, i2c_imx); +if (ret) { +dev_err (&pdev->dev,"can't claim irq %d\n" , irq); + goto rpm_disable; + } +/* Set up clock divider */ i2c_imx->bitrate =IMX_I2C_BIT_RATE ; ret = of_property_read_u32(pdev->dev.of_node,
@@ -1180,13 +1180,12 @@ static int i2c_imx_probe(struct platform clk_notifier_unregister:clk_notifier_unregister (i2c_imx->clk, &i2c_imx->clk_change_nb); +free_irq (irq, i2c_imx); rpm_disable:pm_runtime_put_noidle (&pdev->dev);pm_runtime_disable (&pdev->dev);pm_runtime_set_suspended (&pdev->dev);pm_runtime_dont_use_autosuspend (&pdev->dev); - -clk_disable:clk_disable_unprepare (i2c_imx->clk);return ret; }
@@ -1194,7 +1193,7 @@ clk_disable:static int i2c_imx_remove (struct platform_device *pdev) {struct imx_i2c_struct *i2c_imx =platform_get_drvdata (pdev); -int ret; +int irq, ret; ret =pm_runtime_get_sync (&pdev->dev);if (ret <0 )
@@ -1214,6 +1213,9 @@ static int i2c_imx_remove(struct platforimx_i2c_write_reg (0 , i2c_imx,IMX_I2C_I2SR );clk_notifier_unregister (i2c_imx->clk, &i2c_imx->clk_change_nb); + irq =platform_get_irq (pdev,0 ); +if (irq >=0 ) +free_irq (irq, i2c_imx);clk_disable_unprepare (i2c_imx->clk);pm_runtime_put_noidle (&pdev->dev);
Greg Kroah-Hartman
maintainerPATCH 179/214 drm/amdgpu: dont map BO in reserved region
In reply to Greg Kroah-HartmanFrom: Madhav Chauhan <[email protected]>
commit c4aa8dff6091cc9536aeb255e544b0b4ba29faf4 upstream.
2MB area is reserved at top inside VM.
--- drivers/gpu/drm/amd/amdgpu/amdgpu_gem.c | 10 ++++++++++ 1 file changed, 10 insertions(+)
drivers/gpu/drm/amd/amdgpu/amdgpu_gem.c +10 -0
@@ -561,6 +561,7 @@ int amdgpu_gem_va_ioctl(struct drm_devicstruct ww_acquire_ctx ticket;struct list_head list, duplicates;uint64_t va_flags; +uint64_t vm_size;int r =0 ;if (args->va_address <AMDGPU_VA_RESERVED_SIZE ) {
@@ -581,6 +582,15 @@ int amdgpu_gem_va_ioctl(struct drm_devic args->va_address &=AMDGPU_GMC_HOLE_MASK ; + vm_size = adev->vm_manager.max_pfn *AMDGPU_GPU_PAGE_SIZE ; + vm_size -=AMDGPU_VA_RESERVED_SIZE ; +if (args->va_address + args->map_size > vm_size) { +dev_dbg (&dev->pdev->dev, +"va_address 0x%llx is in top reserved area 0x%llx\n" , + args->va_address + args->map_size, vm_size); +return -EINVAL ; + } +if ((args->flags & ~valid_flags) && (args->flags & ~prt_flags)) {dev_dbg (&dev->pdev->dev,"invalid flags combination 0x%08X\n" , args->flags);
Greg Kroah-Hartman
maintainerPATCH 180/214 drm/amd/display: Increase timeout for DP Disable
In reply to Greg Kroah-HartmanFrom: Wesley Chalmers <[email protected]>
commit 37b7cb10f07c1174522faafc1d51c6591b1501d4 upstream.
[WHY]
When disabling DP video, the current REG_WAIT timeout of 50ms is too low for certain cases with very high VSYNC intervals.
[HOW]
Increase the timeout to 102ms, so that refresh rates as low as 10Hz can be handled properly.
--- drivers/gpu/drm/amd/display/dc/dcn10/dcn10_stream_encoder.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/gpu/drm/amd/display/dc/dcn10/dcn10_stream_encoder.c +2 -2
@@ -898,10 +898,10 @@ void enc1_stream_encoder_dp_blank(*/ REG_UPDATE (DP_VID_STREAM_CNTL ,DP_VID_STREAM_DIS_DEFER ,2 );/* Larger delay to wait until VBLANK - use max retry of -* 10us*5000=50ms. This covers 41.7ms of minimum 24 Hz mode + +* 10us*10200=102ms. This covers 100.0ms of minimum 10 Hz mode + * a little more because we may not trust delay accuracy. */ - max_retries =DP_BLANK_MAX_RETRY *250 ; + max_retries =DP_BLANK_MAX_RETRY *501 ;/* disable DP stream */ REG_UPDATE (DP_VID_STREAM_CNTL ,DP_VID_STREAM_ENABLE ,0 );
Greg Kroah-Hartman
maintainerPATCH 181/214 drm/amdgpu: correct the gpu reset handling for job != NULL case
In reply to Greg Kroah-HartmanFrom: Evan Quan <[email protected]>
commit 207ac684792560acdb9e06f9d707ebf63c84b0e0 upstream.
Current code wrongly treat all cases as job == NULL.
--- drivers/gpu/drm/amd/amdgpu/amdgpu_device.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/gpu/drm/amd/amdgpu/amdgpu_device.c +1 -1
@@ -3890,7 +3890,7 @@ retry: /* Rest of adevs pre asic reset famdgpu_device_lock_adev (tmp_adev, false); r =amdgpu_device_pre_asic_reset (tmp_adev, -NULL , + (tmp_adev == adev) ? job :NULL , &need_full_reset);/*TODO Should we stop ?*/ if (r) {
Greg Kroah-Hartman
maintainerPATCH 182/214 drm/amdkfd: Use same SQ prefetch setting as amdgpu
In reply to Greg Kroah-HartmanFrom: Jay Cornwall <[email protected]>
commit d56b1980d7efe9ef08469e856fc0703d0cef65e4 upstream.
0 causes instruction fetch stall at cache line boundary under some conditions on Navi10. A non-zero prefetch is the preferred default in any case.
Fixes soft hang in Luxmark.
--- drivers/gpu/drm/amd/amdkfd/kfd_device_queue_manager_v10.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-)
drivers/gpu/drm/amd/amdkfd/kfd_device_queue_manager_v10.c +3 -2
@@ -58,8 +58,9 @@ static int update_qpd_v10(struct device_/* check if sh_mem_config register already configured */ if (qpd->sh_mem_config ==0 ) { qpd->sh_mem_config = -SH_MEM_ALIGNMENT_MODE_UNALIGNED << -SH_MEM_CONFIG__ALIGNMENT_MODE__SHIFT ; + (SH_MEM_ALIGNMENT_MODE_UNALIGNED << +SH_MEM_CONFIG__ALIGNMENT_MODE__SHIFT ) | + (3 <<SH_MEM_CONFIG__INITIAL_INST_PREFETCH__SHIFT );#if 0 /* TODO: * This shouldn't be an issue with Navi10. Verify.
Greg Kroah-Hartman
maintainerPATCH 183/214 drm/amd/display: Avoid MST manager resource leak.
In reply to Greg Kroah-HartmanFrom: Andrey Grodzovsky <[email protected]>
commit 5dff80bdce9e385af5716ed083f9e33e814484ab upstream.
On connector destruction call drm_dp_mst_topology_mgr_destroy to release resources allocated in drm_dp_mst_topology_mgr_init. Do it only if MST manager was initilized before otherwsie a crash is seen on driver unload/device unplug.
--- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 7 +++++++ 1 file changed, 7 insertions(+)
drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +7 -0
@@ -3956,6 +3956,13 @@ static void amdgpu_dm_connector_destroy(struct amdgpu_device *adev = connector->dev->dev_private;struct amdgpu_display_manager *dm = &adev->dm; +/* +* Call only if mst_mgr was iniitalized before since it's not done +* for all connector types. +*/ +if (aconnector->mst_mgr.dev) +drm_dp_mst_topology_mgr_destroy (&aconnector->mst_mgr); +#if defined(CONFIG_BACKLIGHT_CLASS_DEVICE ) ||\ defined(CONFIG_BACKLIGHT_CLASS_DEVICE_MODULE )
Greg Kroah-Hartman
maintainerPATCH 184/214 drm/amdgpu: increase the reserved VM size to 2MB
In reply to Greg Kroah-HartmanFrom: Christian König <[email protected]>
commit 55bb919be4e4973cd037a04f527ecc6686800437 upstream.
Ideally this should be a multiple of the VM block size. 2MB should at least fit for Vega/Navi.
--- drivers/gpu/drm/amd/amdgpu/amdgpu_vm.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/gpu/drm/amd/amdgpu/amdgpu_vm.h +2 -2
@@ -105,8 +105,8 @@ struct amdgpu_bo_list_entry;#define AMDGPU_MMHUB_0 1#define AMDGPU_MMHUB_1 2 -/* hardcode that limit for now */ -#define AMDGPU_VA_RESERVED_SIZE (1ULL << 20) +/* Reserve 2MB at top/bottom of address space for kernel use */ +#define AMDGPU_VA_RESERVED_SIZE (2ULL << 20)/* max vmids dedicated for process */ #define AMDGPU_VM_MAX_RESERVED_VMID 1
Greg Kroah-Hartman
maintainerPATCH 185/214 drm/amd/display: Dont invoke kgdb_breakpoint() unconditionally
In reply to Greg Kroah-HartmanFrom: Takashi Iwai <[email protected]>
commit 8b7dc1fe1a5c1093551f6cd7dfbb941bd9081c2e upstream.
ASSERT_CRITICAL() invokes kgdb_breakpoint() whenever either CONFIG_KGDB or CONFIG_HAVE_KGDB is set. This, however, may lead to a kernel panic when no kdb stuff is attached, since the kgdb_breakpoint() call issues INT3. It's nothing but a surprise for normal end-users.
For avoiding the pitfall, make the kgdb_breakpoint() call only when CONFIG_DEBUG_KERNEL_DC is set.
https://bugzilla.opensuse.org/show_bug.cgi?id=1177973
--- drivers/gpu/drm/amd/display/dc/os_types.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/gpu/drm/amd/display/dc/os_types.h +1 -1
@@ -57,7 +57,7 @@* general debug capabilities * */ -#if defined(CONFIG_HAVE_KGDB ) || defined(CONFIG_KGDB ) +#if defined(CONFIG_DEBUG_KERNEL_DC ) && (defined(CONFIG_HAVE_KGDB ) || defined(CONFIG_KGDB ))#define ASSERT_CRITICAL (expr) do { \ if (WARN_ON(!(expr))) { \ kgdb_breakpoint(); \
Greg Kroah-Hartman
maintainerPATCH 186/214 drm/amd/display: Fix kernel panic by dal_gpio_open() error
In reply to Greg Kroah-HartmanFrom: Takashi Iwai <[email protected]>
commit 920bb38c518408fa2600eaefa0af9e82cf48f166 upstream.
Currently both error code paths handled in dal_gpio_open_ex() issues ASSERT_CRITICAL(), and this leads to a kernel panic unnecessarily if CONFIG_KGDB is enabled. Since basically both are non-critical errors and can be recovered, drop those assert calls and use a safer one, BREAK_TO_DEBUGGER(), for allowing the debugging, instead.
--- drivers/gpu/drm/amd/display/dc/gpio/gpio_base.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/gpu/drm/amd/display/dc/gpio/gpio_base.c +2 -2
@@ -63,13 +63,13 @@ enum gpio_result dal_gpio_open_ex( enum gpio_mode mode) {if (gpio->pin) { -ASSERT_CRITICAL (false); +BREAK_TO_DEBUGGER ();return GPIO_RESULT_ALREADY_OPENED ; }// No action if allocation failed during gpio construct if (!gpio->hw_container.ddc) { -ASSERT_CRITICAL (false); +BREAK_TO_DEBUGGER ();return GPIO_RESULT_NON_SPECIFIC_ERROR ; } gpio->mode = mode;
Greg Kroah-Hartman
maintainerPATCH 187/214 ceph: promote to unsigned long long before shifting
In reply to Greg Kroah-HartmanFrom: Matthew Wilcox (Oracle) <[email protected]>
commit c403c3a2fbe24d4ed33e10cabad048583ebd4edf upstream.
On 32-bit systems, this shift will overflow for files larger than 4GB.
--- fs/ceph/addr.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
fs/ceph/addr.c +1 -1
@@ -1427,7 +1427,7 @@ static vm_fault_t ceph_filemap_fault(strstruct ceph_inode_info *ci =ceph_inode (inode);struct ceph_file_info *fi = vma->vm_file->private_data;struct page *pinned_page =NULL ; -loff_t off = vmf->pgoff <<PAGE_SHIFT ; +loff_t off = (loff_t )vmf->pgoff <<PAGE_SHIFT ;int want, got, err;sigset_t oldset;vm_fault_t ret =VM_FAULT_SIGBUS ;
Greg Kroah-Hartman
maintainerPATCH 188/214 libceph: clear con->out_msg on Policy::stateful_server faults
In reply to Greg Kroah-HartmanFrom: Ilya Dryomov <[email protected]>
commit 28e1581c3b4ea5f98530064a103c6217bedeea73 upstream.
con->out_msg must be cleared on Policy::stateful_server (!CEPH_MSG_CONNECT_LOSSY) faults. Not doing so botches the reconnection attempt, because after writing the banner the messenger moves on to writing the data section of that message (either from where it got interrupted by the connection reset or from the beginning) instead of writing struct ceph_msg_connect. This results in a bizarre error message because the server sends CEPH_MSGR_TAG_BADPROTOVER but we think we wrote struct ceph_msg_connect:
libceph: mds0 (1)172.21.15.45:6828 socket error on write
ceph: mds0 reconnect start
libceph: mds0 (1)172.21.15.45:6829 socket closed (con state OPEN)
libceph: mds0 (1)172.21.15.45:6829 protocol version mismatch, my 32 != server's 32
libceph: mds0 (1)172.21.15.45:6829 protocol version mismatch
AFAICT this bug goes back to the dawn of the kernel client. The reason it survived for so long is that only MDS sessions are stateful and only two MDS messages have a data section:CEPH_MSG_CLIENT_RECONNECT (always, but reconnecting is rare) and CEPH_MSG_CLIENT_REQUEST (only when xattrs are involved). The connection has to get reset precisely when such message is being sent -- in this case it was the former.
--- net/ceph/messenger.c | 5 +++++ 1 file changed, 5 insertions(+)
net/ceph/messenger.c +5 -0
@@ -3007,6 +3007,11 @@ static void con_fault(struct ceph_connecceph_msg_put (con->in_msg); con->in_msg =NULL ; } +if (con->out_msg) { +BUG_ON (con->out_msg->con != con); +ceph_msg_put (con->out_msg); + con->out_msg =NULL ; + }/* Requeue anything that hasn't been acked */ list_splice_init (&con->out_sent, &con->out_queue);
Greg Kroah-Hartman
maintainerPATCH 189/214 9P: Cast to loff_t before multiplying
In reply to Greg Kroah-HartmanFrom: Matthew Wilcox (Oracle) <[email protected]>
commit f5f7ab168b9a60e12a4b8f2bb6fcc91321dc23c1 upstream.
On 32-bit systems, this multiplication will overflow for files larger than 4GB.
--- fs/9p/vfs_file.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
fs/9p/vfs_file.c +2 -2
@@ -609,9 +609,9 @@ static void v9fs_mmap_vm_close(struct vmstruct writeback_control wbc = { .nr_to_write =LONG_MAX , .sync_mode =WB_SYNC_ALL , - .range_start = vma->vm_pgoff *PAGE_SIZE , + .range_start = (loff_t )vma->vm_pgoff *PAGE_SIZE ,/* absolute end, byte at end included */ - .range_end = vma->vm_pgoff *PAGE_SIZE + + .range_end = (loff_t )vma->vm_pgoff *PAGE_SIZE + (vma->vm_end - vma->vm_start -1 ), };
Greg Kroah-Hartman
maintainerPATCH 190/214 ring-buffer: Return 0 on success from ring_buffer_resize()
In reply to Greg Kroah-HartmanFrom: Qiujun Huang <[email protected]>
commit 0a1754b2a97efa644aa6e84d1db5b17c42251483 upstream.
We don't need to check the new buffer size, and the return value had confused resize_buffer_duplicate_size().
...
ret = ring_buffer_resize(trace_buf->buffer, per_cpu_ptr(size_buf->data,cpu_id)->entries, cpu_id); if (ret == 0) per_cpu_ptr(trace_buf->data, cpu_id)->entries = per_cpu_ptr(size_buf->data, cpu_id)->entries;
...
--- kernel/trace/ring_buffer.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-)
kernel/trace/ring_buffer.c +4 -4
@@ -1717,18 +1717,18 @@ int ring_buffer_resize(struct ring_buffe {struct ring_buffer_per_cpu *cpu_buffer;unsigned long nr_pages; -int cpu, err =0 ; +int cpu, err;/* * Always succeed at resizing a non-existent buffer: */ if (!buffer) -return size; +return 0 ;/* Make sure the requested buffer exists */ if (cpu_id !=RING_BUFFER_ALL_CPUS && !cpumask_test_cpu (cpu_id, buffer->cpumask)) -return size; +return 0 ; nr_pages =DIV_ROUND_UP (size,BUF_PAGE_SIZE );
@@ -1868,7 +1868,7 @@ int ring_buffer_resize(struct ring_buffe }mutex_unlock (&buffer->mutex); -return size; +return 0 ; out_err:for_each_buffer_cpu (buffer, cpu) {
Greg Kroah-Hartman
maintainerPATCH 191/214 vringh: fix __vringh_iov() when riov and wiov are different
In reply to Greg Kroah-HartmanFrom: Stefano Garzarella <[email protected]>
commit 5745bcfbbf89b158416075374254d3c013488f21 upstream.
If riov and wiov are both defined and they point to different objects, only riov is initialized. If the wiov is not initialized by the caller, the function fails returning -EINVAL and printing "Readable desc 0x... after writable" error message.
This issue happens when descriptors have both readable and writable buffers (eg. virtio-blk devices has virtio_blk_outhdr in the readable buffer and status as last byte of writable buffer) and we call __vringh_iov() to get both type of buffers in two different iovecs.
Let's replace the 'else if' clause with 'if' to initialize both riov and wiov if they are not NULL.
As checkpatch pointed out, we also avoid crashing the kernel when riov and wiov are both NULL, replacing BUG() with WARN_ON() and returning -EINVAL.
--- drivers/vhost/vringh.c | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-)
drivers/vhost/vringh.c +5 -4
@@ -274,13 +274,14 @@ __vringh_iov(struct vringh *vrh, u16 i, desc_max = vrh->vring.num; up_next =-1 ; +/* You must want something! */ +if (WARN_ON (!riov && !wiov)) +return -EINVAL ; +if (riov) riov->i = riov->used =0 ; -else if (wiov) +if (wiov) wiov->i = wiov->used =0 ; -else -/* You must want something! */ -BUG ();for (;;) {void *addr;
Greg Kroah-Hartman
maintainerPATCH 192/214 ext4: fix leaking sysfs kobject after failed mount
In reply to Greg Kroah-HartmanFrom: Eric Biggers <[email protected]>
commit cb8d53d2c97369029cc638c9274ac7be0a316c75 upstream.
ext4_unregister_sysfs() only deletes the kobject. The reference to it needs to be put separately, like ext4_put_super() does.
This addresses the syzbot report
"memory leak in kobject_set_name_vargs (3)"
(https://syzkaller.appspot.com/bug?extid=9f864abad79fae7c17e1).
--- fs/ext4/super.c | 1 + 1 file changed, 1 insertion(+)
fs/ext4/super.c +1 -0
@@ -4684,6 +4684,7 @@ cantfind_ext4: failed_mount8:ext4_unregister_sysfs (sb); +kobject_put (&sbi->s_kobj); failed_mount7:ext4_unregister_li_request (sb); failed_mount6:
Greg Kroah-Hartman
maintainerPATCH 193/214 ext4: fix error handling code in add_new_gdb
In reply to Greg Kroah-HartmanFrom: Dinghao Liu <[email protected]>
commit c9e87161cc621cbdcfc472fa0b2d81c63780c8f5 upstream.
When ext4_journal_get_write_access() fails, we should terminate the execution flow and release n_group_desc, iloc.bh, dind and gdb_bh.
--- fs/ext4/resize.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
fs/ext4/resize.c +3 -1
@@ -861,8 +861,10 @@ static int add_new_gdb(handle_t *handle,BUFFER_TRACE (dind,"get_write_access" ); err =ext4_journal_get_write_access (handle, dind); -if (unlikely (err)) +if (unlikely (err)) {ext4_std_error (sb, err); + goto errout; + }/* ext4_reserve_inode_write() gets a reference on the iloc */ err =ext4_reserve_inode_write (handle, inode, &iloc);
Greg Kroah-Hartman
maintainerPATCH 194/214 ext4: fix invalid inode checksum
In reply to Greg Kroah-HartmanFrom: Luo Meng <[email protected]>
commit 1322181170bb01bce3c228b82ae3d5c6b793164f upstream.
During the stability test, there are some errors:
ext4_lookup:1590: inode #6967: comm fsstress: iget: checksum invalid.
If the inode->i_iblocks too big and doesn't set huge file flag, checksum will not be recalculated when update the inode information to it's buffer. If other inode marks the buffer dirty, then the inconsistent inode will be flushed to disk.
Fix this problem by checking i_blocks in advance.
--- fs/ext4/inode.c | 11 ++++++----- 1 file changed, 6 insertions(+), 5 deletions(-)
fs/ext4/inode.c +6 -5
@@ -5271,6 +5271,12 @@ static int ext4_do_update_inode(handle_tif (ext4_test_inode_state (inode,EXT4_STATE_NEW ))memset (raw_inode,0 ,EXT4_SB (inode->i_sb)->s_inode_size); + err =ext4_inode_blocks_set (handle, raw_inode, ei); +if (err) { +spin_unlock (&ei->i_raw_lock); + goto out_brelse; + } + raw_inode->i_mode =cpu_to_le16 (inode->i_mode); i_uid =i_uid_read (inode); i_gid =i_gid_read (inode);
@@ -5304,11 +5310,6 @@ static int ext4_do_update_inode(handle_tEXT4_INODE_SET_XTIME (i_atime, inode, raw_inode);EXT4_EINODE_SET_XTIME (i_crtime, ei, raw_inode); - err =ext4_inode_blocks_set (handle, raw_inode, ei); -if (err) { -spin_unlock (&ei->i_raw_lock); - goto out_brelse; - } raw_inode->i_dtime =cpu_to_le32 (ei->i_dtime); raw_inode->i_flags =cpu_to_le32 (ei->i_flags &0xFFFFFFFF );if (likely (!test_opt2 (inode->i_sb,HURD_COMPAT )))
Greg Kroah-Hartman
maintainerPATCH 195/214 ext4: fix superblock checksum calculation race
In reply to Greg Kroah-HartmanFrom: Constantine Sapuntzakis <[email protected]>
commit acaa532687cdc3a03757defafece9c27aa667546 upstream.
The race condition could cause the persisted superblock checksum to not match the contents of the superblock, causing the superblock to be considered corrupt.
An example of the race follows. A first thread is interrupted in the middle of a checksum calculation. Then, another thread changes the superblock, calculates a new checksum, and sets it. Then, the first thread resumes and sets the checksum based on the older superblock.
To fix, serialize the superblock checksum calculation using the buffer header lock. While a spinlock is sufficient, the buffer header is already there and there is precedent for locking it (e.g. in ext4_commit_super).
Tested the patch by booting up a kernel with the patch, creating a filesystem and some files (including some orphans), and then unmounting and remounting the file system.
--- fs/ext4/super.c | 11 +++++++++++ 1 file changed, 11 insertions(+)
fs/ext4/super.c +11 -0
@@ -201,7 +201,18 @@ void ext4_superblock_csum_set(struct supif (!ext4_has_metadata_csum (sb))return ; +/* +* Locking the superblock prevents the scenario +* where: +* 1) a first thread pauses during checksum calculation. +* 2) a second thread updates the superblock, recalculates +* the checksum, and updates s_checksum +* 3) the first thread resumes and finishes its checksum calculation +* and updates s_checksum with a potentially stale or torn value. +*/ +lock_buffer (EXT4_SB (sb)->s_sbh); es->s_checksum =ext4_superblock_csum (sb, es); +unlock_buffer (EXT4_SB (sb)->s_sbh); }void *ext4_kvmalloc (size_t size,gfp_t flags)
Greg Kroah-Hartman
maintainerPATCH 196/214 drm/ttm: fix eviction valuable range check.
In reply to Greg Kroah-HartmanFrom: Dave Airlie <[email protected]>
commit fea456d82c19d201c21313864105876deabe148b upstream.
This was adding size to start, but pfn and start are in pages, so it should be using num_pages.
Not sure this fixes anything in the real world, just noticed it during refactoring.
--- drivers/gpu/drm/ttm/ttm_bo.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/gpu/drm/ttm/ttm_bo.c +1 -1
@@ -761,7 +761,7 @@ bool ttm_bo_eviction_valuable(struct ttm/* Don't evict this BO if it's outside of the * requested placement range */ -if (place->fpfn >= (bo->mem.start + bo->mem.size) || +if (place->fpfn >= (bo->mem.start + bo->mem.num_pages) || (place->lpfn && place->lpfn <= bo->mem.start))return false;
Greg Kroah-Hartman
maintainerPATCH 197/214 mmc: sdhci-of-esdhc: set timeout to max before tuning
In reply to Greg Kroah-HartmanFrom: Michael Walle <[email protected]>
commit 0add6e9b88d0632a25323aaf4987dbacb0e4ae64 upstream.
On rare occations there is the following error:
mmc0: Tuning timeout, falling back to fixed sampling clock
There are SD cards which takes a significant longer time to reply to the first CMD19 command. The eSDHC takes the data timeout value into account during the tuning period. The SDHCI core doesn't explicitly set this timeout for the tuning procedure. Thus on the slow cards, there might be a spurious "Buffer Read Ready" interrupt, which in turn triggers a wrong sequence of events. In the end this will lead to an unsuccessful tuning procedure and to the above error.
To workaround this, set the timeout to the maximum value (which is the best we can do) and the SDHCI core will take care of the proper timeout handling.
--- drivers/mmc/host/sdhci-of-esdhc.c | 11 +++++++++++ 1 file changed, 11 insertions(+)
drivers/mmc/host/sdhci-of-esdhc.c +11 -0
@@ -1004,6 +1004,17 @@ static int esdhc_execute_tuning(struct mesdhc_tuning_block_enable (host, true); +/* +* The eSDHC controller takes the data timeout value into account +* during tuning. If the SD card is too slow sending the response, the +* timer will expire and a "Buffer Read Ready" interrupt without data +* is triggered. This leads to tuning errors. +* +* Just set the timeout to the maximum value because the core will +* already take care of it in sdhci_send_tuning(). +*/ +sdhci_writeb (host,0xe ,SDHCI_TIMEOUT_CONTROL ); + hs400_tuning = host->flags &SDHCI_HS400_TUNING ; do {
Greg Kroah-Hartman
maintainerPATCH 198/214 mmc: sdhci: Use Auto CMD Auto Select only when v4_mode is true
In reply to Greg Kroah-HartmanFrom: Jisheng Zhang <[email protected]>
commit b3e1ea16fb39fb6e1a1cf1dbdd6738531de3dc7d upstream.
sdhci-of-dwcmshc meets an eMMC read performance regression with below command after commit 427b6514d095 ("mmc: sdhci: Add Auto CMD Auto Select support"):
dd if=/dev/mmcblk0 of=/dev/null bs=8192 count=100000
Before the commit, the above command gives 120MB/s After the commit, the above command gives 51.3 MB/s
So it looks like sdhci-of-dwcmshc expects Version 4 Mode for Auto CMD Auto Select. Fix the performance degradation by ensuring v4_mode is true to use Auto CMD Auto Select.
--- drivers/mmc/host/sdhci.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-)
drivers/mmc/host/sdhci.c +4 -2
@@ -1162,9 +1162,11 @@ static inline void sdhci_auto_cmd_select/* * In case of Version 4.10 or later, use of 'Auto CMD Auto * Select' is recommended rather than use of 'Auto CMD12 -* Enable' or 'Auto CMD23 Enable'. +* Enable' or 'Auto CMD23 Enable'. We require Version 4 Mode +* here because some controllers (e.g sdhci-of-dwmshc) expect it. */ -if (host->version >=SDHCI_SPEC_410 && (use_cmd12 || use_cmd23)) { +if (host->version >=SDHCI_SPEC_410 && host->v4_mode && + (use_cmd12 || use_cmd23)) { *mode |=SDHCI_TRNS_AUTO_SEL ; ctrl2 =sdhci_readw (host,SDHCI_HOST_CONTROL2 );
Greg Kroah-Hartman
maintainerPATCH 199/214 drm/amd/pm: increase mclk switch threshold to 200 us
In reply to Greg Kroah-HartmanFrom: Evan Quan <[email protected]>
commit 83da6eea3af669ee0b1f1bc05ffd6150af984994 upstream.
To avoid underflow seen on Polaris10 with some 3440x1440 144Hz displays. As the threshold of 190 us cuts too close to minVBlankTime of 192 us.
--- drivers/gpu/drm/amd/powerplay/hwmgr/smu7_hwmgr.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/gpu/drm/amd/powerplay/hwmgr/smu7_hwmgr.c +1 -1
@@ -2864,7 +2864,7 @@ static int smu7_vblank_too_short(structif (hwmgr->is_kicker) switch_limit_us = data->is_memory_gddr5 ?450 :150 ;else - switch_limit_us = data->is_memory_gddr5 ?190 :150 ; + switch_limit_us = data->is_memory_gddr5 ?200 :150 ;break ;case CHIP_VEGAM : switch_limit_us =30 ;
Greg Kroah-Hartman
maintainerPATCH 200/214 tty: make FONTX ioctl use the tty pointer they were actually passed
In reply to Greg Kroah-HartmanFrom: Linus Torvalds <[email protected]>
commit 90bfdeef83f1d6c696039b6a917190dcbbad3220 upstream.
Some of the font tty ioctl's always used the current foreground VC for their operations. Don't do that then.
This fixes a data race on fg_console.
Side note: both Michael Ellerman and Jiri Slaby point out that all these ioctls are deprecated, and should probably have been removed long ago, and everything seems to be using the KDFONTOP ioctl instead.
In fact, Michael points out that it looks like busybox's loadfont program seems to have switched over to using KDFONTOP exactly _because_ of this bug (ahem.. 12 years ago ;-).
--- drivers/tty/vt/vt_ioctl.c | 32 +++++++++++++++++--------------- 1 file changed, 17 insertions(+), 15 deletions(-)
drivers/tty/vt/vt_ioctl.c +17 -15
@@ -244,7 +244,7 @@ int vt_waitactive(int n)static inline int -do_fontx_ioctl (int cmd,struct consolefontdesc __user *user_cfd,int perm,struct console_font_op *op) +do_fontx_ioctl (struct vc_data *vc,int cmd,struct consolefontdesc __user *user_cfd,int perm,struct console_font_op *op) {struct consolefontdesc cfdarg;int i;
@@ -262,15 +262,16 @@ do_fontx_ioctl(int cmd, struct consolefo op->height = cfdarg.charheight; op->charcount = cfdarg.charcount; op->data = cfdarg.chardata; -return con_font_op (vc_cons[fg_console].d, op); -case GIO_FONTX : { +return con_font_op (vc, op); + +case GIO_FONTX : op->op =KD_FONT_OP_GET ; op->flags =KD_FONT_FLAG_OLD ; op->width =8 ; op->height = cfdarg.charheight; op->charcount = cfdarg.charcount; op->data = cfdarg.chardata; - i =con_font_op (vc_cons[fg_console].d, op); + i =con_font_op (vc, op);if (i)return i; cfdarg.charheight = op->height;
@@ -278,7 +279,6 @@ do_fontx_ioctl(int cmd, struct consolefoif (copy_to_user (user_cfd, &cfdarg,sizeof (struct consolefontdesc )))return -EFAULT ;return 0 ; - } }return -EINVAL ; }
@@ -924,7 +924,7 @@ int vt_ioctl(struct tty_struct *tty, op.height =0 ; op.charcount =256 ; op.data = up; - ret =con_font_op (vc_cons[fg_console].d, &op); + ret =con_font_op (vc, &op);break ; }
@@ -935,7 +935,7 @@ int vt_ioctl(struct tty_struct *tty, op.height =32 ; op.charcount =256 ; op.data = up; - ret =con_font_op (vc_cons[fg_console].d, &op); + ret =con_font_op (vc, &op);break ; }
@@ -952,7 +952,7 @@ int vt_ioctl(struct tty_struct *tty,case PIO_FONTX :case GIO_FONTX : - ret =do_fontx_ioctl (cmd, up, perm, &op); + ret =do_fontx_ioctl (vc, cmd, up, perm, &op);break ;case PIO_FONTRESET :
@@ -969,11 +969,11 @@ int vt_ioctl(struct tty_struct *tty, { op.op =KD_FONT_OP_SET_DEFAULT ; op.data =NULL ; - ret =con_font_op (vc_cons[fg_console].d, &op); + ret =con_font_op (vc, &op);if (ret)break ;console_lock (); -con_set_default_unimap (vc_cons[fg_console].d); +con_set_default_unimap (vc);console_unlock ();break ; }
@@ -1100,8 +1100,9 @@ struct compat_consolefontdesc { };static inline int -compat_fontx_ioctl (int cmd,struct compat_consolefontdesc __user *user_cfd, -int perm,struct console_font_op *op) +compat_fontx_ioctl (struct vc_data *vc,int cmd, +struct compat_consolefontdesc __user *user_cfd, +int perm,struct console_font_op *op) {struct compat_consolefontdesc cfdarg;int i;
@@ -1119,7 +1120,8 @@ compat_fontx_ioctl(int cmd, struct compa op->height = cfdarg.charheight; op->charcount = cfdarg.charcount; op->data =compat_ptr (cfdarg.chardata); -return con_font_op (vc_cons[fg_console].d, op); +return con_font_op (vc, op); +case GIO_FONTX : op->op =KD_FONT_OP_GET ; op->flags =KD_FONT_FLAG_OLD ;
@@ -1127,7 +1129,7 @@ compat_fontx_ioctl(int cmd, struct compa op->height = cfdarg.charheight; op->charcount = cfdarg.charcount; op->data =compat_ptr (cfdarg.chardata); - i =con_font_op (vc_cons[fg_console].d, op); + i =con_font_op (vc, op);if (i)return i; cfdarg.charheight = op->height;
@@ -1217,7 +1219,7 @@ long vt_compat_ioctl(struct tty_struct **/ case PIO_FONTX :case GIO_FONTX : -return compat_fontx_ioctl (cmd, up, perm, &op); +return compat_fontx_ioctl (vc, cmd, up, perm, &op);case KDFONTOP :return compat_kdfontop_ioctl (up, perm, &op, vc);
Greg Kroah-Hartman
maintainerPATCH 201/214 arm64: berlin: Select DW_APB_TIMER_OF
In reply to Greg Kroah-HartmanFrom: Jisheng Zhang <[email protected]>
commit b0fc70ce1f028e14a37c186d9f7a55e51439b83a upstream.
Berlin SoCs always contain some DW APB timers which can be used as an always-on broadcast timer.
--- arch/arm64/Kconfig.platforms | 1 + 1 file changed, 1 insertion(+)
arch/arm64/Kconfig.platforms +1 -0
@@ -54,6 +54,7 @@ config ARCH_BCM_IPROC config ARCH_BERLIN bool "Marvell Berlin SoC Family" select DW_APB_ICTL + select DW_APB_TIMER_OF select GPIOLIB select PINCTRL help
Greg Kroah-Hartman
maintainerPATCH 202/214 cachefiles: Handle readpage error correctly
In reply to Greg Kroah-HartmanFrom: Matthew Wilcox (Oracle) <[email protected]>
commit 9480b4e75b7108ee68ecf5bc6b4bd68e8031c521 upstream.
If ->readpage returns an error, it has already unlocked the page.
--- fs/cachefiles/rdwr.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
fs/cachefiles/rdwr.c +2 -1
@@ -121,7 +121,7 @@ static int cachefiles_read_reissue(struc_debug ("reissue read" ); ret = bmapping->a_ops->readpage (NULL , backpage);if (ret <0 ) - goto unlock_discard; + goto discard; }/* but the page may have been read before the monitor was installed, so
@@ -138,6 +138,7 @@ static int cachefiles_read_reissue(struc unlock_discard:unlock_page (backpage); +discard:spin_lock_irq (&object->work_lock);list_del (&monitor->op_link);spin_unlock_irq (&object->work_lock);
Greg Kroah-Hartman
maintainerPATCH 203/214 hil/parisc: Disable HIL driver when it gets stuck
In reply to Greg Kroah-HartmanFrom: Helge Deller <[email protected]>
commit 879bc2d27904354b98ca295b6168718e045c4aa2 upstream.
When starting a HP machine with HIL driver but without an HIL keyboard or HIL mouse attached, it may happen that data written to the HIL loop gets stuck (e.g. because the transaction queue is full). Usually one will then have to reboot the machine because all you see is and endless output of:
Transaction add failed: transaction already queued?
In the higher layers hp_sdc_enqueue_transaction() is called to queued up a HIL packet. This function returns an error code, and this patch adds the necessary checks for this return code and disables the HIL driver if further packets can't be sent.
Tested on a HP 730 and a HP 715/64 machine.
--- drivers/input/serio/hil_mlc.c | 21 ++++++++++++++++++--- drivers/input/serio/hp_sdc_mlc.c | 8 ++++---- include/linux/hil_mlc.h | 2 +- 3 files changed, 23 insertions(+), 8 deletions(-)
drivers/input/serio/hil_mlc.c +18 -3
@@ -74,7 +74,7 @@ EXPORT_SYMBOL(hil_mlc_unregister);static LIST_HEAD (hil_mlcs);static DEFINE_RWLOCK (hil_mlcs_lock);static struct timer_list hil_mlcs_kicker; -static int hil_mlcs_probe; +static int hil_mlcs_probe, hil_mlc_stop;static void hil_mlcs_process (unsigned long unused); static DECLARE_TASKLET_DISABLED(hil_mlcs_tasklet, hil_mlcs_process, 0);
@@ -702,9 +702,13 @@ static int hilse_donode(hil_mlc *mlc)if (!mlc->ostarted) { mlc->ostarted =1 ; mlc->opacket = pack; - mlc->out (mlc); + rc = mlc->out (mlc); nextidx =HILSEN_DOZE ;write_unlock_irqrestore (&mlc->lock, flags); +if (rc) { + hil_mlc_stop =1 ; +return 1 ; + }break ; } mlc->ostarted =0 ;
@@ -715,8 +719,13 @@ static int hilse_donode(hil_mlc *mlc)case HILSE_CTS :write_lock_irqsave (&mlc->lock, flags); - nextidx = mlc->cts (mlc) ? node->bad : node->good; + rc = mlc->cts (mlc); + nextidx = rc ? node->bad : node->good;write_unlock_irqrestore (&mlc->lock, flags); +if (rc) { + hil_mlc_stop =1 ; +return 1 ; + }break ;default :
@@ -780,6 +789,12 @@ static void hil_mlcs_process(unsigned lostatic void hil_mlcs_timer (struct timer_list *unused) { +if (hil_mlc_stop) { +/* could not send packet - stop immediately. */ +pr_warn (PREFIX "HIL seems stuck - Disabling HIL MLC.\n" ); +return ; + } + hil_mlcs_probe =1 ;tasklet_schedule (&hil_mlcs_tasklet);/* Re-insert the periodic task. */
drivers/input/serio/hp_sdc_mlc.c +4 -4
@@ -210,7 +210,7 @@ static int hp_sdc_mlc_cts(hil_mlc *mlc) priv->tseq[2 ] =1 ; priv->tseq[3 ] =0 ; priv->tseq[4 ] =0 ; -__hp_sdc_enqueue_transaction (&priv->trans); +return __hp_sdc_enqueue_transaction (&priv->trans); busy:return 1 ; done:
@@ -219,7 +219,7 @@ static int hp_sdc_mlc_cts(hil_mlc *mlc)return 0 ; } -static void hp_sdc_mlc_out (hil_mlc *mlc) +static int hp_sdc_mlc_out (hil_mlc *mlc) {struct hp_sdc_mlc_priv_s *priv;
@@ -234,7 +234,7 @@ static void hp_sdc_mlc_out(hil_mlc *mlc) do_data:if (priv->emtestmode) {up (&mlc->osem); -return ; +return 0 ; }/* Shouldn't be sending commands when loop may be busy */ BUG_ON (down_trylock (&mlc->csem));
@@ -296,7 +296,7 @@ static void hp_sdc_mlc_out(hil_mlc *mlc)BUG_ON (down_trylock (&mlc->csem)); } enqueue: -hp_sdc_enqueue_transaction (&priv->trans); +return hp_sdc_enqueue_transaction (&priv->trans); }static int __init hp_sdc_mlc_init (void )
include/linux/hil_mlc.h +1 -1
@@ -103,7 +103,7 @@ struct hilse_node {/* Methods for back-end drivers, e.g. hp_sdc_mlc */ typedef int (hil_mlc_cts ) (hil_mlc *mlc); -typedef void (hil_mlc_out ) (hil_mlc *mlc); +typedef int (hil_mlc_out ) (hil_mlc *mlc);typedef int (hil_mlc_in ) (hil_mlc *mlc,suseconds_t timeout);struct hil_mlc_devinfo {
Greg Kroah-Hartman
maintainerPATCH 204/214 arm: dts: mt7623: add missing pause for switchport
In reply to Greg Kroah-HartmanFrom: Frank Wunderlich <[email protected]>
commit 36f0a5fc5284838c544218666c63ee8cfa46a9c3 upstream.
port6 of mt7530 switch (= cpu port 0) on bananapi-r2 misses pause option which causes rx drops on running iperf.
--- arch/arm/boot/dts/mt7623n-bananapi-bpi-r2.dts | 1 + 1 file changed, 1 insertion(+)
arch/arm/boot/dts/mt7623n-bananapi-bpi-r2.dts +1 -0
@@ -192,6 +192,7 @@ fixed-link { speed = <1000>; full-duplex; + pause; }; }; };
Greg Kroah-Hartman
maintainerPATCH 205/214 ARM: samsung: fix PM debug build with DEBUG_LL but !MMU
In reply to Greg Kroah-HartmanFrom: Krzysztof Kozlowski <[email protected]>
commit 7be0d19c751b02db778ca95e3274d5ea7f31891c upstream.
Selecting CONFIG_SAMSUNG_PM_DEBUG (depending on CONFIG_DEBUG_LL) but without CONFIG_MMU leads to build errors:
arch/arm/plat-samsung/pm-debug.c: In function ‘s3c_pm_uart_base’:
arch/arm/plat-samsung/pm-debug.c:57:2: error:
implicit declaration of function ‘debug_ll_addr’ [-Werror=implicit-function-declaration]
--- arch/arm/plat-samsung/Kconfig | 1 + 1 file changed, 1 insertion(+)
arch/arm/plat-samsung/Kconfig +1 -0
@@ -241,6 +241,7 @@ config SAMSUNG_PM_DEBUG depends on PM && DEBUG_KERNEL depends on PLAT_S3C24XX || ARCH_S3C64XX || ARCH_S5PV210 depends on DEBUG_EXYNOS_UART || DEBUG_S3C24XX_UART || DEBUG_S3C2410_UART + depends on DEBUG_LL && MMU help Say Y here if you want verbose debugging from the PM Suspend and Resume code. See <file:Documentation/arm/samsung-s3c24xx/suspend.rst>
Greg Kroah-Hartman
maintainerPATCH 206/214 ARM: s3c24xx: fix missing system reset
In reply to Greg Kroah-HartmanFrom: Krzysztof Kozlowski <[email protected]>
commit f6d7cde84f6c5551586c8b9b68d70f8e6dc9a000 upstream.
Commit f6361c6b3880 ("ARM: S3C24XX: remove separate restart code") removed usage of the watchdog reset platform code in favor of the Samsung SoC watchdog driver. However the latter was not selected thus S3C24xx platforms lost reset abilities.
--- arch/arm/Kconfig | 2 ++ 1 file changed, 2 insertions(+)
arch/arm/Kconfig +2 -0
@@ -507,8 +507,10 @@ config ARCH_S3C24XX select HAVE_S3C2410_WATCHDOG if WATCHDOG select HAVE_S3C_RTC if RTC_CLASS select NEED_MACH_IO_H + select S3C2410_WATCHDOG select SAMSUNG_ATAGS select USE_OF + select WATCHDOG help Samsung S3C2410, S3C2412, S3C2413, S3C2416, S3C2440, S3C2442, S3C2443 and S3C2450 SoCs based systems, such as the Simtec Electronics BAST
Greg Kroah-Hartman
maintainerPATCH 207/214 device property: Keep secondary firmware node secondary by type
In reply to Greg Kroah-HartmanFrom: Andy Shevchenko <[email protected]>
commit d5dcce0c414fcbfe4c2037b66ac69ea5f9b3f75c upstream.
Behind primary and secondary we understand the type of the nodes which might define their ordering. However, if primary node gone, we can't maintain the ordering by definition of the linked list. Thus, by ordering secondary node becomes first in the list. But in this case the meaning of it is still secondary (or auxiliary). The type of the node is maintained by the secondary pointer in it:
secondary pointer Meaning
NULL or valid primary node
ERR_PTR(-ENODEV) secondary node
So, if by some reason we do the following sequence of calls
set_primary_fwnode(dev, NULL); set_primary_fwnode(dev, primary);
we should preserve secondary node.
This concept is supported by the description of set_primary_fwnode() along with implementation of set_secondary_fwnode(). Hence, fix the commit c15e1bdda436 to follow this as well.
--- drivers/base/core.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/base/core.c +1 -1
@@ -3414,7 +3414,7 @@ void set_primary_fwnode(struct device *d }else {if (fwnode_is_primary (fn)) { dev->fwnode = fn->secondary; - fn->secondary =NULL ; + fn->secondary =ERR_PTR (-ENODEV ); }else { dev->fwnode =NULL ; }
Greg Kroah-Hartman
maintainerPATCH 208/214 device property: Dont clear secondary pointer for shared primary firmware node
In reply to Greg Kroah-HartmanFrom: Andy Shevchenko <[email protected]>
commit 99aed9227073fb34ce2880cbc7063e04185a65e1 upstream.
It appears that firmware nodes can be shared between devices. In such case when a (child) device is about to be deleted, its firmware node may be shared and ACPI_COMPANION_SET(..., NULL) call for it breaks the secondary link of the shared primary firmware node.
In order to prevent that, check, if the device has a parent and parent's firmware node is shared with its child, and avoid crashing the link.
--- drivers/base/core.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
drivers/base/core.c +3 -1
@@ -3400,6 +3400,7 @@ static inline bool fwnode_is_primary(str*/ void set_primary_fwnode (struct device *dev,struct fwnode_handle *fwnode) { +struct device *parent = dev->parent;struct fwnode_handle *fn = dev->fwnode;if (fwnode) {
@@ -3414,7 +3415,8 @@ void set_primary_fwnode(struct device *d }else {if (fwnode_is_primary (fn)) { dev->fwnode = fn->secondary; - fn->secondary =ERR_PTR (-ENODEV ); +if (!(parent && fn == parent->fwnode)) + fn->secondary =ERR_PTR (-ENODEV ); }else { dev->fwnode =NULL ; }
Greg Kroah-Hartman
maintainerPATCH 209/214 KVM: arm64: Fix AArch32 handling of DBGD{CCINT,SCRext} and DBGVCR
In reply to Greg Kroah-HartmanFrom: Marc Zyngier <[email protected]>
commit 4a1c2c7f63c52ccb11770b5ae25920a6b79d3548 upstream.
The DBGD{CCINT,SCRext} and DBGVCR register entries in the cp14 array are missing their target register, resulting in all accesses being targetted at the guard sysreg (indexed by __INVALID_SYSREG__).
Point the emulation code at the actual register entries.
--- arch/arm64/include/asm/kvm_host.h | 1 + arch/arm64/kvm/sys_regs.c | 6 +++--- 2 files changed, 4 insertions(+), 3 deletions(-)
arch/arm64/include/asm/kvm_host.h +1 -0
@@ -209,6 +209,7 @@ enum vcpu_sysreg {#define cp14_DBGWCR0 (DBGWCR0_EL1 * 2)#define cp14_DBGWVR0 (DBGWVR0_EL1 * 2)#define cp14_DBGDCCINT (MDCCINT_EL1 * 2) +#define cp14_DBGVCR (DBGVCR32_EL2 * 2)#define NR_COPRO_REGS (NR_SYS_REGS * 2)
arch/arm64/kvm/sys_regs.c +3 -3
@@ -1746,9 +1746,9 @@ static const struct sys_reg_desc cp14_re { Op1( 0), CRn( 0), CRm( 1), Op2( 0), trap_raz_wi },DBG_BCR_BVR_WCR_WVR (1 ),/* DBGDCCINT */ - { Op1( 0), CRn( 0), CRm( 2), Op2( 0), trap_debug32 }, + { Op1( 0), CRn( 0), CRm( 2), Op2( 0), trap_debug32, NULL, cp14_DBGDCCINT },/* DBGDSCRext */ - { Op1( 0), CRn( 0), CRm( 2), Op2( 2), trap_debug32 }, + { Op1( 0), CRn( 0), CRm( 2), Op2( 2), trap_debug32, NULL, cp14_DBGDSCRext },DBG_BCR_BVR_WCR_WVR (2 ),/* DBGDTR[RT]Xint */ { Op1( 0), CRn( 0), CRm( 3), Op2( 0), trap_raz_wi },
@@ -1763,7 +1763,7 @@ static const struct sys_reg_desc cp14_re { Op1( 0), CRn( 0), CRm( 6), Op2( 2), trap_raz_wi },DBG_BCR_BVR_WCR_WVR (6 ),/* DBGVCR */ - { Op1( 0), CRn( 0), CRm( 7), Op2( 0), trap_debug32 }, + { Op1( 0), CRn( 0), CRm( 7), Op2( 0), trap_debug32, NULL, cp14_DBGVCR },DBG_BCR_BVR_WCR_WVR (7 ),DBG_BCR_BVR_WCR_WVR (8 ), DBG_BCR_BVR_WCR_WVR(9),
Greg Kroah-Hartman
maintainerPATCH 210/214 staging: fieldbus: anybuss: jump to correct label in an error path
In reply to Greg Kroah-HartmanFrom: Jing Xiangfeng <[email protected]>
commit 7e97e4cbf30026b49b0145c3bfe06087958382c5 upstream.
In current code, controller_probe() misses to call ida_simple_remove() in an error path. Jump to correct label to fix it.
--- drivers/staging/fieldbus/anybuss/arcx-anybus.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/staging/fieldbus/anybuss/arcx-anybus.c +1 -1
@@ -297,7 +297,7 @@ static int controller_probe(struct platf regulator =devm_regulator_register (dev, &can_power_desc, &config);if (IS_ERR (regulator)) { err =PTR_ERR (regulator); - goto out_reset; + goto out_ida; }/* make controller info visible to userspace */ cd->class_dev =kzalloc (sizeof (*cd->class_dev),GFP_KERNEL );
Greg Kroah-Hartman
maintainerPATCH 211/214 staging: comedi: cb_pcidas: Allow 2-channel commands for AO subdevice
In reply to Greg Kroah-HartmanFrom: Ian Abbott <[email protected]>
commit 647a6002cb41d358d9ac5de101a8a6dc74748a59 upstream.
The "cb_pcidas" driver supports asynchronous commands on the analog output (AO) subdevice for those boards that have an AO FIFO. The code (in cb_pcidas_ao_check_chanlist() and cb_pcidas_ao_cmd()) to validate and set up the command supports output to a single channel or to two channels simultaneously (the boards have two AO channels). However, the code in cb_pcidas_auto_attach() that initializes the subdevices neglects to initialize the AO subdevice's len_chanlist member, leaving it set to 0, but the Comedi core will "correct" it to 1 if the driver neglected to set it. This limits commands to use a single channel (either channel 0 or 1), but the limit should be two channels. Set the AO subdevice's len_chanlist member to be the same value as the n_chan member, which will be 2.
--- drivers/staging/comedi/drivers/cb_pcidas.c | 1 + 1 file changed, 1 insertion(+)
drivers/staging/comedi/drivers/cb_pcidas.c +1 -0
@@ -1342,6 +1342,7 @@ static int cb_pcidas_auto_attach(structif (dev->irq && board->has_ao_fifo) { dev->write_subdev = s; s->subdev_flags |=SDF_CMD_WRITE ; + s->len_chanlist = s->n_chan; s->do_cmdtest = cb_pcidas_ao_cmdtest; s->do_cmd = cb_pcidas_ao_cmd; s->cancel = cb_pcidas_ao_cancel;
Greg Kroah-Hartman
maintainerPATCH 212/214 staging: octeon: repair "fixed-link" support
In reply to Greg Kroah-HartmanFrom: Alexander Sverdlin <[email protected]>
commit 179f5dc36b0a1aa31538d7d8823deb65c39847b3 upstream.
The PHYs must be registered once in device probe function, not in device open callback because it's only possible to register them once.
--- drivers/staging/octeon/ethernet-mdio.c | 6 ------ drivers/staging/octeon/ethernet.c | 9 +++++++++ 2 files changed, 9 insertions(+), 6 deletions(-)
drivers/staging/octeon/ethernet-mdio.c +0 -6
@@ -147,12 +147,6 @@ int cvm_oct_phy_setup_device(struct net_ phy_node =of_parse_phandle (priv->of_node,"phy-handle" ,0 );if (!phy_node &&of_phy_is_fixed_link (priv->of_node)) { -int rc; - - rc =of_phy_register_fixed_link (priv->of_node); -if (rc) -return rc; - phy_node =of_node_get (priv->of_node); }if (!phy_node)
drivers/staging/octeon/ethernet.c +9 -0
@@ -13,6 +13,7 @@#include <linux/phy.h> #include <linux/slab.h> #include <linux/interrupt.h> +#include <linux/of_mdio.h> #include <linux/of_net.h> #include <linux/if_ether.h> #include <linux/if_vlan.h>
@@ -894,6 +895,14 @@ static int cvm_oct_probe(struct platformbreak ; } +if (priv->of_node &&of_phy_is_fixed_link (priv->of_node)) { +if (of_phy_register_fixed_link (priv->of_node)) { +netdev_err (dev,"Failed to register fixed link for interface %d, port %d\n" , + interface, priv->port); + dev->netdev_ops =NULL ; + } + } +if (!dev->netdev_ops) {free_netdev (dev); }else if (register_netdev (dev) <0 ) {
Greg Kroah-Hartman
maintainerPATCH 213/214 staging: octeon: Drop on uncorrectable alignment or FCS error
In reply to Greg Kroah-HartmanFrom: Alexander Sverdlin <[email protected]>
commit 49d28ebdf1e30d806410eefc7de0a7a1ca5d747c upstream.
Currently in case of alignment or FCS error if the packet cannot be corrected it's still not dropped. Report the error properly and drop the packet while making the code around a little bit more readable.
--- drivers/staging/octeon/ethernet-rx.c | 34 +++++++++++++++++++--------------- 1 file changed, 19 insertions(+), 15 deletions(-)
drivers/staging/octeon/ethernet-rx.c +19 -15
@@ -69,15 +69,17 @@ static inline int cvm_oct_check_rcv_erroelse port = work->word1.cn38xx.ipprt; -if ((work->word2.snoip.err_code ==10 ) && (work->word1.len <=64 )) { +if ((work->word2.snoip.err_code ==10 ) && (work->word1.len <=64 ))/* * Ignore length errors on min size packets. Some * equipment incorrectly pads packets to 64+4FCS * instead of 60+4FCS. Note these packets still get * counted as frame errors. */ - }else if (work->word2.snoip.err_code ==5 || - work->word2.snoip.err_code ==7 ) { +return 0 ; + +if (work->word2.snoip.err_code ==5 || + work->word2.snoip.err_code ==7 ) {/* * We received a packet with either an alignment error * or a FCS error. This may be signalling that we are
@@ -108,7 +110,10 @@ static inline int cvm_oct_check_rcv_erro/* Port received 0xd5 preamble */ work->packet_ptr.s.addr += i +1 ; work->word1.len -= i +5 ; - }else if ((*ptr &0xf ) ==0xd ) { +return 0 ; + } + +if ((*ptr &0xf ) ==0xd ) {/* Port received 0xd preamble */ work->packet_ptr.s.addr += i; work->word1.len -= i +4 ;
@@ -118,21 +123,20 @@ static inline int cvm_oct_check_rcv_erro ((*(ptr +1 ) &0xf ) <<4 ); ptr++; } - }else { -printk_ratelimited ("Port %d unknown preamble, packet dropped\n" , - port); -cvm_oct_free_work (work); -return 1 ; +return 0 ; } + +printk_ratelimited ("Port %d unknown preamble, packet dropped\n" , + port); +cvm_oct_free_work (work); +return 1 ; } - }else { -printk_ratelimited ("Port %d receive error code %d, packet dropped\n" , - port, work->word2.snoip.err_code); -cvm_oct_free_work (work); -return 1 ; } -return 0 ; +printk_ratelimited ("Port %d receive error code %d, packet dropped\n" , + port, work->word2.snoip.err_code); +cvm_oct_free_work (work); +return 1 ; }static void copy_segments_to_skb (cvmx_wqe_t *work,struct sk_buff *skb)
Greg Kroah-Hartman
maintainerPATCH 214/214 KVM: arm64: ARM_SMCCC_ARCH_WORKAROUND_1 doesnt return SMCCC_RET_NOT_REQUIRED
In reply to Greg Kroah-HartmanFrom: Stephen Boyd <[email protected]>
commit 1de111b51b829bcf01d2e57971f8fd07a665fa3f upstream.
According to the SMCCC spec[1](7.5.2 Discovery) the ARM_SMCCC_ARCH_WORKAROUND_1 function id only returns 0, 1, and SMCCC_RET_NOT_SUPPORTED.
0 is "workaround required and safe to call this function"
1 is "workaround not required but safe to call this function" SMCCC_RET_NOT_SUPPORTED is "might be vulnerable or might not be, who knows, I give up!"
SMCCC_RET_NOT_SUPPORTED might as well mean "workaround required, except calling this function may not work because it isn't implemented in some cases". Wonderful. We map this SMC call to
0 is SPECTRE_MITIGATED
1 is SPECTRE_UNAFFECTED
SMCCC_RET_NOT_SUPPORTED is SPECTRE_VULNERABLE
For KVM hypercalls (hvc), we've implemented this function id to return SMCCC_RET_NOT_SUPPORTED, 0, and SMCCC_RET_NOT_REQUIRED. One of those isn't supposed to be there. Per the code we call arm64_get_spectre_v2_state() to figure out what to return for this feature discovery call.
0 is SPECTRE_MITIGATED
SMCCC_RET_NOT_REQUIRED is SPECTRE_UNAFFECTED
SMCCC_RET_NOT_SUPPORTED is SPECTRE_VULNERABLE
Let's clean this up so that KVM tells the guest this mapping:
0 is SPECTRE_MITIGATED
1 is SPECTRE_UNAFFECTED
SMCCC_RET_NOT_SUPPORTED is SPECTRE_VULNERABLE
Note: SMCCC_RET_NOT_AFFECTED is 1 but isn't part of the SMCCC spec
--- include/linux/arm-smccc.h | 2 ++ virt/kvm/arm/psci.c | 2 +- 2 files changed, 3 insertions(+), 1 deletion(-)
include/linux/arm-smccc.h +2 -0
@@ -76,6 +76,8 @@ ARM_SMCCC_SMC_32, \ 0, 0x7fff) +#define SMCCC_ARCH_WORKAROUND_RET_UNAFFECTED 1 +#ifndef __ASSEMBLY__#include <linux/linkage.h>
virt/kvm/arm/psci.c +1 -1
@@ -408,7 +408,7 @@ int kvm_hvc_call_handler(struct kvm_vcpu val =SMCCC_RET_SUCCESS ;break ;case KVM_BP_HARDEN_NOT_REQUIRED : - val =SMCCC_RET_NOT_REQUIRED ; + val =SMCCC_ARCH_WORKAROUND_RET_UNAFFECTED ;break ; }break ;
Quoted 9 lines · Greg Kroah-Hartman
This is the start of the stable review cycle for the 5.4.75 release. There are 214 patches in this series, all will be posted as a response to this one. If anyone has any issues with these being applied, please let me know.
Responses should be made by Thu, 05 Nov 2020 20:29:58 +0000. Anything received after that time might be too late.
The whole patch series can be found in one patch at:
Quoted 8 lines
https://www.kernel.org/pub/linux/kernel/v5.x/stable-review/patch-5.4.75-rc1.gzor in the git tree and branch at:
git://git.kernel.org/pub/scm/linux/kernel/git/stable/linux-stable-rc.gitlinux-5.4.y
and the diffstat can be found below.thanks,
greg k-h
All tests passing for Tegra ...
Test results for stable-v5.4:
15 builds: 15 pass, 0 fail
26 boots: 26 pass, 0 fail
56 tests: 56 pass, 0 failLinux version: 5.4.75-rc1-g1b513bf28609
Boards tested: tegra124-jetson-tk1, tegra186-p2771-0000,
tegra194-p2972-0000, tegra20-ventana,
tegra210-p2371-2180, tegra210-p3450-0000,
tegra30-cardhu-a04Jon
Quoted 10 lines · Greg Kroah-Hartman
This is the start of the stable review cycle for the 5.4.75 release. There are 214 patches in this series, all will be posted as a response to this one. If anyone has any issues with these being applied, please let me know.
Responses should be made by Thu, 05 Nov 2020 20:29:58 +0000. Anything received after that time might be too late.
The whole patch series can be found in one patch at:
Quoted 9 lines
https://www.kernel.org/pub/linux/kernel/v5.x/stable-review/patch-5.4.75-rc1.gzor in the git tree and branch at:
git://git.kernel.org/pub/scm/linux/kernel/git/stable/linux-stable-rc.gitlinux-5.4.y
and the diffstat can be found below.thanks,
greg k-h
Results from Linaro’s test farm.
No regressions on arm64, arm, x86_64, and i386.
Summary
------------------------------------------------------------------------
kernel: 5.4.75-rc1
git repo: https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux-stable-rc.git
git branch: linux-5.4.y
git commit: 1b513bf286096f9c66fc386cdc5e038980db8863
git describe: v5.4.74-215-g1b513bf28609
Test details: https://qa-reports.linaro.org/lkft/linux-stable-rc-linux-5.4.y/build/v5.4.74-215-g1b513bf28609
No regressions (compared to build v5.4.74)
No fixes (compared to build v5.4.74)
Ran 37086 total tests in the following environments and test suites.
Environments
--------------
- dragonboard-410c
- hi6220-hikey
- i386
- juno-r2
- juno-r2-compat
- nxp-ls2088-kasan
- qemu-arm64-kasan
- qemu-x86_64-kasan
- qemu_arm
- qemu_arm64
- qemu_i386
- qemu_x86_64
- x15
- x86
- x86-kasan
Test Suites
-----------
* build
* igt-gpu-tools
* install-android-platform-tools-r2600
* kselftest
* libhugetlbfs
* linux-log-parser
* ltp-cap_bounds-tests
* ltp-commands-tests
* ltp-containers-tests
* ltp-controllers-tests
* ltp-cpuhotplug-tests
* ltp-crypto-tests
* ltp-dio-tests
* ltp-fcntl-locktests-tests
* ltp-filecaps-tests
* ltp-fs-tests
* ltp-fs_bind-tests
* ltp-fs_perms_simple-tests
* ltp-fsx-tests
* ltp-io-tests
* ltp-ipc-tests
* ltp-math-tests
* ltp-sched-tests
* ltp-syscalls-tests
* ltp-tracing-tests
* perf
* v4l2-compliance
* ltp-cve-tests
* ltp-hugetlb-tests
* ltp-mm-tests
* ltp-nptl-tests
* ltp-pty-tests
* ltp-securebits-tests
* network-basic-tests
* ltp-open-posix-tests
* kvm-unit-tests
* kselftest-vsyscall-mode-native
* kselftest-vsyscall-mode-none
Signature · 2 lines
Linaro LKFT https://lkft.linaro.org
Quoted 8 lines · Greg Kroah-Hartman
This is the start of the stable review cycle for the 5.4.75 release. There are 214 patches in this series, all will be posted as a response to this one. If anyone has any issues with these being applied, please let me know.
Responses should be made by Thu, 05 Nov 2020 20:29:58 +0000. Anything received after that time might be too late.
All sparc images fail to build.
Building sparc32:defconfig ... failed
--------------
Error log:
<stdin>:1511:2: warning: #warning syscall clone3 not implemented [-Wcpp] In file included from arch/sparc/include/asm/io_32.h:14,
from arch/sparc/include/asm/io.h:7,
from include/linux/io.h:13,
from include/linux/irq.h:20,
from include/asm-generic/hardirq.h:13,
from arch/sparc/include/asm/hardirq_32.h:11,
from arch/sparc/include/asm/hardirq.h:7,
from include/linux/hardirq.h:9,
from include/linux/interrupt.h:11,
from include/linux/kernel_stat.h:9,
from arch/sparc/kernel/irq_32.c:15:include/asm-generic/io.h: In function '__pci_ioport_unmap':include/asm-generic/io.h:1012:2: error: implicit declaration of function 'iounmap'; did you mean 'ioremap'?
Guenter
Greg Kroah-Hartman
maintainerQuoted 27 lines · Guenter Roeck
Quoted 8 lines · Greg Kroah-Hartman
This is the start of the stable review cycle for the 5.4.75 release. There are 214 patches in this series, all will be posted as a response to this one. If anyone has any issues with these being applied, please let me know.
Responses should be made by Thu, 05 Nov 2020 20:29:58 +0000. Anything received after that time might be too late.
All sparc images fail to build.
Building sparc32:defconfig ... failed
--------------
Error log:
<stdin>:1511:2: warning: #warning syscall clone3 not implemented [-Wcpp] In file included fromarch/sparc/include/asm/io_32.h:14,from arch/sparc/include/asm/io.h:7, from include/linux/io.h:13, from include/linux/irq.h:20, from include/asm-generic/hardirq.h:13, from arch/sparc/include/asm/hardirq_32.h:11, from arch/sparc/include/asm/hardirq.h:7, from include/linux/hardirq.h:9, from include/linux/interrupt.h:11, from include/linux/kernel_stat.h:9, from arch/sparc/kernel/irq_32.c:15:
Quoted 2 lines
include/asm-generic/io.h: In function '__pci_ioport_unmap':include/asm-generic/io.h:1012:2: error: implicit declaration of function 'iounmap'; did you mean 'ioremap'?
Thanks, I'll go drop f5810e5c3292 ("asm-generic/io.h: Fix !CONFIG_GENERIC_IOMAP pci_iounmap() implementation") which seems to be causing this.
Sasha, any reason you only added it to the 5.4 and 4.14 queues and not 5.9 and 4.19?
thanks,
greg k-h
Quoted 8 lines · Greg Kroah-Hartman
This is the start of the stable review cycle for the 5.4.75 release. There are 214 patches in this series, all will be posted as a response to this one. If anyone has any issues with these being applied, please let me know.
Responses should be made by Thu, 05 Nov 2020 20:29:58 +0000. Anything received after that time might be too late.
Build results:
total: 157 pass: 150 fail: 7 Failed builds: <all sparc> Qemu test results: total: 426 pass: 394 fail: 32
Failed tests:
<all sparc>
Guenter