#include <linux/tty.h>
 #include <linux/ratelimit.h>
 #include <linux/tty_flip.h>
-#include <linux/serial_reg.h>
 #include <linux/serial_core.h>
 #include <linux/serial.h>
 #include <linux/serial_8250.h>
                .fifo_size      = 16,
                .tx_loadsz      = 16,
                .fcr            = UART_FCR_ENABLE_FIFO | UART_FCR_R_TRIG_10,
+               .rxtrig_bytes   = {1, 4, 8, 14},
                .flags          = UART_CAP_FIFO,
        },
        [PORT_CIRRUS] = {
                .tx_loadsz      = 16,
                .fcr            = UART_FCR_ENABLE_FIFO | UART_FCR_R_TRIG_01 |
                                  UART_FCR_T_TRIG_00,
+               .rxtrig_bytes   = {8, 16, 24, 28},
                .flags          = UART_CAP_FIFO | UART_CAP_EFR | UART_CAP_SLEEP,
        },
        [PORT_16750] = {
                .tx_loadsz      = 64,
                .fcr            = UART_FCR_ENABLE_FIFO | UART_FCR_R_TRIG_10 |
                                  UART_FCR7_64BYTE,
+               .rxtrig_bytes   = {1, 16, 32, 56},
                .flags          = UART_CAP_FIFO | UART_CAP_SLEEP | UART_CAP_AFE,
        },
        [PORT_STARTECH] = {
                .tx_loadsz      = 32,
                .fcr            = UART_FCR_ENABLE_FIFO | UART_FCR_R_TRIG_01 |
                                  UART_FCR_T_TRIG_10,
+               .rxtrig_bytes   = {8, 16, 56, 60},
                .flags          = UART_CAP_FIFO | UART_CAP_EFR | UART_CAP_SLEEP,
        },
        [PORT_16850] = {
                .tx_loadsz      = 8,
                .fcr            = UART_FCR_ENABLE_FIFO | UART_FCR_R_TRIG_01 |
                                  UART_FCR_T_TRIG_01,
+               .rxtrig_bytes   = {1, 4, 8, 14},
                .flags          = UART_CAP_FIFO | UART_CAP_RTOIE,
        },
        [PORT_XR17D15X] = {
 
 void serial8250_clear_and_reinit_fifos(struct uart_8250_port *p)
 {
-       unsigned char fcr;
-
        serial8250_clear_fifos(p);
-       fcr = uart_config[p->port.type].fcr;
-       serial_out(p, UART_FCR, fcr);
+       serial_out(p, UART_FCR, p->fcr);
 }
 EXPORT_SYMBOL_GPL(serial8250_clear_and_reinit_fifos);
 
                          struct ktermios *old)
 {
        struct uart_8250_port *up = up_to_u8250p(port);
-       unsigned char cval, fcr = 0;
+       unsigned char cval;
        unsigned long flags;
        unsigned int baud, quot;
-       int fifo_bug = 0;
 
        switch (termios->c_cflag & CSIZE) {
        case CS5:
        if (termios->c_cflag & PARENB) {
                cval |= UART_LCR_PARITY;
                if (up->bugs & UART_BUG_PARITY)
-                       fifo_bug = 1;
+                       up->fifo_bug = true;
        }
        if (!(termios->c_cflag & PARODD))
                cval |= UART_LCR_EPAR;
                quot++;
 
        if (up->capabilities & UART_CAP_FIFO && port->fifosize > 1) {
-               fcr = uart_config[port->type].fcr;
-               if ((baud < 2400 && !up->dma) || fifo_bug) {
-                       fcr &= ~UART_FCR_TRIGGER_MASK;
-                       fcr |= UART_FCR_TRIGGER_1;
+               /* NOTE: If fifo_bug is not set, a user can set RX_trigger. */
+               if ((baud < 2400 && !up->dma) || up->fifo_bug) {
+                       up->fcr &= ~UART_FCR_TRIGGER_MASK;
+                       up->fcr |= UART_FCR_TRIGGER_1;
                }
        }
 
         * is written without DLAB set, this mode will be disabled.
         */
        if (port->type == PORT_16750)
-               serial_port_out(port, UART_FCR, fcr);
+               serial_port_out(port, UART_FCR, up->fcr);
 
        serial_port_out(port, UART_LCR, cval);          /* reset DLAB */
        up->lcr = cval;                                 /* Save LCR */
        if (port->type != PORT_16750) {
                /* emulated UARTs (Lucent Venus 167x) need two steps */
-               if (fcr & UART_FCR_ENABLE_FIFO)
+               if (up->fcr & UART_FCR_ENABLE_FIFO)
                        serial_port_out(port, UART_FCR, UART_FCR_ENABLE_FIFO);
-               serial_port_out(port, UART_FCR, fcr);           /* set fcr */
+               serial_port_out(port, UART_FCR, up->fcr);       /* set fcr */
        }
        serial8250_set_mctrl(port, port->mctrl);
        spin_unlock_irqrestore(&port->lock, flags);
        return ret;
 }
 
+static int fcr_get_rxtrig_bytes(struct uart_8250_port *up)
+{
+       const struct serial8250_config *conf_type = &uart_config[up->port.type];
+       unsigned char bytes;
+
+       bytes = conf_type->rxtrig_bytes[UART_FCR_R_TRIG_BITS(up->fcr)];
+
+       return bytes ? bytes : -EOPNOTSUPP;
+}
+
+static int bytes_to_fcr_rxtrig(struct uart_8250_port *up, unsigned char bytes)
+{
+       const struct serial8250_config *conf_type = &uart_config[up->port.type];
+       int i;
+
+       if (!conf_type->rxtrig_bytes[UART_FCR_R_TRIG_BITS(UART_FCR_R_TRIG_00)])
+               return -EOPNOTSUPP;
+
+       for (i = 1; i < UART_FCR_R_TRIG_MAX_STATE; i++) {
+               if (bytes < conf_type->rxtrig_bytes[i])
+                       /* Use the nearest lower value */
+                       return (--i) << UART_FCR_R_TRIG_SHIFT;
+       }
+
+       return UART_FCR_R_TRIG_11;
+}
+
+static int do_get_rxtrig(struct tty_port *port)
+{
+       struct uart_state *state = container_of(port, struct uart_state, port);
+       struct uart_port *uport = state->uart_port;
+       struct uart_8250_port *up =
+               container_of(uport, struct uart_8250_port, port);
+
+       if (!(up->capabilities & UART_CAP_FIFO) || uport->fifosize <= 1)
+               return -EINVAL;
+
+       return fcr_get_rxtrig_bytes(up);
+}
+
+static int do_serial8250_get_rxtrig(struct tty_port *port)
+{
+       int rxtrig_bytes;
+
+       mutex_lock(&port->mutex);
+       rxtrig_bytes = do_get_rxtrig(port);
+       mutex_unlock(&port->mutex);
+
+       return rxtrig_bytes;
+}
+
+static ssize_t serial8250_get_attr_rx_trig_bytes(struct device *dev,
+       struct device_attribute *attr, char *buf)
+{
+       struct tty_port *port = dev_get_drvdata(dev);
+       int rxtrig_bytes;
+
+       rxtrig_bytes = do_serial8250_get_rxtrig(port);
+       if (rxtrig_bytes < 0)
+               return rxtrig_bytes;
+
+       return snprintf(buf, PAGE_SIZE, "%d\n", rxtrig_bytes);
+}
+
+static int do_set_rxtrig(struct tty_port *port, unsigned char bytes)
+{
+       struct uart_state *state = container_of(port, struct uart_state, port);
+       struct uart_port *uport = state->uart_port;
+       struct uart_8250_port *up =
+               container_of(uport, struct uart_8250_port, port);
+       int rxtrig;
+
+       if (!(up->capabilities & UART_CAP_FIFO) || uport->fifosize <= 1 ||
+           up->fifo_bug)
+               return -EINVAL;
+
+       rxtrig = bytes_to_fcr_rxtrig(up, bytes);
+       if (rxtrig < 0)
+               return rxtrig;
+
+       serial8250_clear_fifos(up);
+       up->fcr &= ~UART_FCR_TRIGGER_MASK;
+       up->fcr |= (unsigned char)rxtrig;
+       serial_out(up, UART_FCR, up->fcr);
+       return 0;
+}
+
+static int do_serial8250_set_rxtrig(struct tty_port *port, unsigned char bytes)
+{
+       int ret;
+
+       mutex_lock(&port->mutex);
+       ret = do_set_rxtrig(port, bytes);
+       mutex_unlock(&port->mutex);
+
+       return ret;
+}
+
+static ssize_t serial8250_set_attr_rx_trig_bytes(struct device *dev,
+       struct device_attribute *attr, const char *buf, size_t count)
+{
+       struct tty_port *port = dev_get_drvdata(dev);
+       unsigned char bytes;
+       int ret;
+
+       if (!count)
+               return -EINVAL;
+
+       ret = kstrtou8(buf, 10, &bytes);
+       if (ret < 0)
+               return ret;
+
+       ret = do_serial8250_set_rxtrig(port, bytes);
+       if (ret < 0)
+               return ret;
+
+       return count;
+}
+
+static DEVICE_ATTR(rx_trig_bytes, S_IRUSR | S_IWUSR | S_IRGRP,
+                  serial8250_get_attr_rx_trig_bytes,
+                  serial8250_set_attr_rx_trig_bytes);
+
+static struct attribute *serial8250_dev_attrs[] = {
+       &dev_attr_rx_trig_bytes.attr,
+       NULL,
+       };
+
+static struct attribute_group serial8250_dev_attr_group = {
+       .attrs = serial8250_dev_attrs,
+       };
+
+static void register_dev_spec_attr_grp(struct uart_8250_port *up)
+{
+       const struct serial8250_config *conf_type = &uart_config[up->port.type];
+
+       if (conf_type->rxtrig_bytes[0])
+               up->port.attr_group = &serial8250_dev_attr_group;
+}
+
 static void serial8250_config_port(struct uart_port *port, int flags)
 {
        struct uart_8250_port *up = up_to_u8250p(port);
        if ((port->type == PORT_XR17V35X) ||
           (port->type == PORT_XR17D15X))
                port->handle_irq = exar_handle_irq;
+
+       register_dev_spec_attr_grp(up);
+       up->fcr = uart_config[up->port.type].fcr;
 }
 
 static int