aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/tty/n_gsm.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/tty/n_gsm.c')
-rw-r--r--drivers/tty/n_gsm.c26
1 files changed, 20 insertions, 6 deletions
diff --git a/drivers/tty/n_gsm.c b/drivers/tty/n_gsm.c
index 09e8c7d53af3..19b4ae052af8 100644
--- a/drivers/tty/n_gsm.c
+++ b/drivers/tty/n_gsm.c
@@ -875,7 +875,8 @@ static int gsm_dlci_data_output_framed(struct gsm_mux *gsm,
875 *dp++ = last << 7 | first << 6 | 1; /* EA */ 875 *dp++ = last << 7 | first << 6 | 1; /* EA */
876 len--; 876 len--;
877 } 877 }
878 memcpy(dp, skb_pull(dlci->skb, len), len); 878 memcpy(dp, dlci->skb->data, len);
879 skb_pull(dlci->skb, len);
879 __gsm_data_queue(dlci, msg); 880 __gsm_data_queue(dlci, msg);
880 if (last) 881 if (last)
881 dlci->skb = NULL; 882 dlci->skb = NULL;
@@ -984,10 +985,22 @@ static void gsm_control_reply(struct gsm_mux *gsm, int cmd, u8 *data,
984 */ 985 */
985 986
986static void gsm_process_modem(struct tty_struct *tty, struct gsm_dlci *dlci, 987static void gsm_process_modem(struct tty_struct *tty, struct gsm_dlci *dlci,
987 u32 modem) 988 u32 modem, int clen)
988{ 989{
989 int mlines = 0; 990 int mlines = 0;
990 u8 brk = modem >> 6; 991 u8 brk = 0;
992
993 /* The modem status command can either contain one octet (v.24 signals)
994 or two octets (v.24 signals + break signals). The length field will
995 either be 2 or 3 respectively. This is specified in section
996 5.4.6.3.7 of the 27.010 mux spec. */
997
998 if (clen == 2)
999 modem = modem & 0x7f;
1000 else {
1001 brk = modem & 0x7f;
1002 modem = (modem >> 7) & 0x7f;
1003 };
991 1004
992 /* Flow control/ready to communicate */ 1005 /* Flow control/ready to communicate */
993 if (modem & MDM_FC) { 1006 if (modem & MDM_FC) {
@@ -1061,7 +1074,7 @@ static void gsm_control_modem(struct gsm_mux *gsm, u8 *data, int clen)
1061 return; 1074 return;
1062 } 1075 }
1063 tty = tty_port_tty_get(&dlci->port); 1076 tty = tty_port_tty_get(&dlci->port);
1064 gsm_process_modem(tty, dlci, modem); 1077 gsm_process_modem(tty, dlci, modem, clen);
1065 if (tty) { 1078 if (tty) {
1066 tty_wakeup(tty); 1079 tty_wakeup(tty);
1067 tty_kref_put(tty); 1080 tty_kref_put(tty);
@@ -1482,12 +1495,13 @@ static void gsm_dlci_begin_close(struct gsm_dlci *dlci)
1482 * open we shovel the bits down it, if not we drop them. 1495 * open we shovel the bits down it, if not we drop them.
1483 */ 1496 */
1484 1497
1485static void gsm_dlci_data(struct gsm_dlci *dlci, u8 *data, int len) 1498static void gsm_dlci_data(struct gsm_dlci *dlci, u8 *data, int clen)
1486{ 1499{
1487 /* krefs .. */ 1500 /* krefs .. */
1488 struct tty_port *port = &dlci->port; 1501 struct tty_port *port = &dlci->port;
1489 struct tty_struct *tty = tty_port_tty_get(port); 1502 struct tty_struct *tty = tty_port_tty_get(port);
1490 unsigned int modem = 0; 1503 unsigned int modem = 0;
1504 int len = clen;
1491 1505
1492 if (debug & 16) 1506 if (debug & 16)
1493 pr_debug("%d bytes for tty %p\n", len, tty); 1507 pr_debug("%d bytes for tty %p\n", len, tty);
@@ -1507,7 +1521,7 @@ static void gsm_dlci_data(struct gsm_dlci *dlci, u8 *data, int len)
1507 if (len == 0) 1521 if (len == 0)
1508 return; 1522 return;
1509 } 1523 }
1510 gsm_process_modem(tty, dlci, modem); 1524 gsm_process_modem(tty, dlci, modem, clen);
1511 /* Line state will go via DLCI 0 controls only */ 1525 /* Line state will go via DLCI 0 controls only */
1512 case 1: 1526 case 1:
1513 default: 1527 default: