diff options
Diffstat (limited to 'drivers/char/amiserial.c')
-rw-r--r-- | drivers/char/amiserial.c | 33 |
1 files changed, 13 insertions, 20 deletions
diff --git a/drivers/char/amiserial.c b/drivers/char/amiserial.c index 10c81ecdace8..869518e4035f 100644 --- a/drivers/char/amiserial.c +++ b/drivers/char/amiserial.c | |||
@@ -265,8 +265,9 @@ static _INLINE_ void receive_chars(struct async_struct *info) | |||
265 | int status; | 265 | int status; |
266 | int serdatr; | 266 | int serdatr; |
267 | struct tty_struct *tty = info->tty; | 267 | struct tty_struct *tty = info->tty; |
268 | unsigned char ch; | 268 | unsigned char ch, flag; |
269 | struct async_icount *icount; | 269 | struct async_icount *icount; |
270 | int oe = 0; | ||
270 | 271 | ||
271 | icount = &info->state->icount; | 272 | icount = &info->state->icount; |
272 | 273 | ||
@@ -282,15 +283,12 @@ static _INLINE_ void receive_chars(struct async_struct *info) | |||
282 | status |= UART_LSR_OE; | 283 | status |= UART_LSR_OE; |
283 | 284 | ||
284 | ch = serdatr & 0xff; | 285 | ch = serdatr & 0xff; |
285 | if (tty->flip.count >= TTY_FLIPBUF_SIZE) | ||
286 | goto ignore_char; | ||
287 | *tty->flip.char_buf_ptr = ch; | ||
288 | icount->rx++; | 286 | icount->rx++; |
289 | 287 | ||
290 | #ifdef SERIAL_DEBUG_INTR | 288 | #ifdef SERIAL_DEBUG_INTR |
291 | printk("DR%02x:%02x...", ch, status); | 289 | printk("DR%02x:%02x...", ch, status); |
292 | #endif | 290 | #endif |
293 | *tty->flip.flag_buf_ptr = 0; | 291 | flag = TTY_NORMAL; |
294 | 292 | ||
295 | /* | 293 | /* |
296 | * We don't handle parity or frame errors - but I have left | 294 | * We don't handle parity or frame errors - but I have left |
@@ -319,7 +317,7 @@ static _INLINE_ void receive_chars(struct async_struct *info) | |||
319 | * should be ignored. | 317 | * should be ignored. |
320 | */ | 318 | */ |
321 | if (status & info->ignore_status_mask) | 319 | if (status & info->ignore_status_mask) |
322 | goto ignore_char; | 320 | goto out; |
323 | 321 | ||
324 | status &= info->read_status_mask; | 322 | status &= info->read_status_mask; |
325 | 323 | ||
@@ -327,33 +325,28 @@ static _INLINE_ void receive_chars(struct async_struct *info) | |||
327 | #ifdef SERIAL_DEBUG_INTR | 325 | #ifdef SERIAL_DEBUG_INTR |
328 | printk("handling break...."); | 326 | printk("handling break...."); |
329 | #endif | 327 | #endif |
330 | *tty->flip.flag_buf_ptr = TTY_BREAK; | 328 | flag = TTY_BREAK; |
331 | if (info->flags & ASYNC_SAK) | 329 | if (info->flags & ASYNC_SAK) |
332 | do_SAK(tty); | 330 | do_SAK(tty); |
333 | } else if (status & UART_LSR_PE) | 331 | } else if (status & UART_LSR_PE) |
334 | *tty->flip.flag_buf_ptr = TTY_PARITY; | 332 | flag = TTY_PARITY; |
335 | else if (status & UART_LSR_FE) | 333 | else if (status & UART_LSR_FE) |
336 | *tty->flip.flag_buf_ptr = TTY_FRAME; | 334 | flag = TTY_FRAME; |
337 | if (status & UART_LSR_OE) { | 335 | if (status & UART_LSR_OE) { |
338 | /* | 336 | /* |
339 | * Overrun is special, since it's | 337 | * Overrun is special, since it's |
340 | * reported immediately, and doesn't | 338 | * reported immediately, and doesn't |
341 | * affect the current character | 339 | * affect the current character |
342 | */ | 340 | */ |
343 | if (tty->flip.count < TTY_FLIPBUF_SIZE) { | 341 | oe = 1; |
344 | tty->flip.count++; | ||
345 | tty->flip.flag_buf_ptr++; | ||
346 | tty->flip.char_buf_ptr++; | ||
347 | *tty->flip.flag_buf_ptr = TTY_OVERRUN; | ||
348 | } | ||
349 | } | 342 | } |
350 | } | 343 | } |
351 | tty->flip.flag_buf_ptr++; | 344 | tty_insert_flip_char(tty, ch, flag); |
352 | tty->flip.char_buf_ptr++; | 345 | if (oe == 1) |
353 | tty->flip.count++; | 346 | tty_insert_flip_char(tty, 0, TTY_OVERRUN); |
354 | ignore_char: | ||
355 | |||
356 | tty_flip_buffer_push(tty); | 347 | tty_flip_buffer_push(tty); |
348 | out: | ||
349 | return; | ||
357 | } | 350 | } |
358 | 351 | ||
359 | static _INLINE_ void transmit_chars(struct async_struct *info) | 352 | static _INLINE_ void transmit_chars(struct async_struct *info) |