- ppp_print_buffer ("ppp outpkt", data, len);
-/*
- * At this point, the buffer will be transmitted. There is no other exit.
- *
- * Try to compress the header.
- */
- if (ppp->flags & SC_COMP_TCP) {
- len = slhc_compress (ppp->slcomp, data, len,
- buf_base (ppp->cbuf) + PPP_HARD_HDR_LEN,
- &data,
- !(ppp->flags & SC_NO_TCP_CCID));
-
- if (data[0] & SL_TYPE_COMPRESSED_TCP) {
- proto = PPP_VJC_COMP;
- data[0] ^= SL_TYPE_COMPRESSED_TCP;
+ ppp_print_buffer ("write frame", data, count);
+
+ /*
+ * Handle various types of protocol-specific compression
+ * and other processing, including:
+ * - VJ TCP header compression
+ * - updating LQR packets
+ * - updating CCP state on CCP packets
+ */
+ proto = PPP_PROTOCOL(data);
+ switch (proto) {
+ case PPP_IP:
+ if ((ppp->flags & SC_COMP_TCP) && ppp->slcomp != NULL)
+ skb = ppp_vj_compress(ppp, skb);
+ break;
+
+ case PPP_LQR:
+ /*
+ * Update the LQR frame with the current MIB information.
+ * This way the information is accurate and up-to-date.
+ */
+ if (count < 48)
+ break;
+ p = data + 40; /* Point to last two items. */
+ p = store_long(p, ppp->stats.ppp_opackets + 1);
+ p = store_long(p, ppp->stats.ppp_ooctects + count);
+ ++ppp->stats.ppp_olqrs;
+ break;
+
+ case PPP_CCP:
+ /*
+ * Outbound compression control frames
+ */
+ ppp_proto_ccp(ppp, data + PPP_HDRLEN, count - PPP_HDRLEN, 0);
+ break;
+ }
+ data = skb->data;
+ count = skb->len;
+
+ /*
+ * Compress the whole frame if possible.
+ */
+ if (((ppp->flags & SC_COMP_RUN) != 0) &&
+ (ppp->sc_xc_state != (void *) 0) &&
+ (proto != PPP_LCP) &&
+ (proto != PPP_CCP)) {
+ struct sk_buff *new_skb;
+ int new_count;
+
+ /* Allocate an skb for the compressed frame. */
+ new_skb = alloc_skb(ppp->mtu + PPP_HDRLEN, GFP_ATOMIC);
+ if (new_skb == NULL) {
+ printk(KERN_ERR "ppp_send_frame: no memory\n");
+ KFREE_SKB(skb);
+ ppp->xmit_busy = 0;
+ return;
+ }
+ LIBERATE_SKB(new_skb);
+
+ /* Compress the frame. */
+ new_count = (*ppp->sc_xcomp->compress)
+ (ppp->sc_xc_state, data, new_skb->data,
+ count, ppp->mtu + PPP_HDRLEN);
+
+ /* Did it compress? */
+ if (new_count > 0 && (ppp->flags & SC_CCP_UP)) {
+ skb_put(new_skb, new_count);
+ KFREE_SKB(skb);
+ skb = new_skb;