~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~ [ freetext search ] ~ [ file search ] ~

Linux Cross Reference
Linux/net/irda/irlap_comp.c

Version: ~ [ 2.4.0 ] ~
Architecture: ~ [ i386 ] ~ [ alpha ] ~ [ m68k ] ~ [ mips ] ~ [ ppc ] ~ [ sparc ] ~ [ sparc64 ] ~

  1 /*********************************************************************
  2  *                
  3  * Filename:      irlap_comp.c
  4  * Version:       
  5  * Description:   
  6  * Status:        Experimental.
  7  * Author:        Dag Brattli <dagb@cs.uit.no>
  8  * Created at:    Fri Oct  9 09:18:07 1998
  9  * Modified at:   Tue Oct  5 11:34:52 1999
 10  * Modified by:   Dag Brattli <dagb@cs.uit.no>
 11  * Modified at:   Fri May 28  3:11 CST 1999
 12  * Modified by:   Horst von Brand <vonbrand@sleipnir.valparaiso.cl>
 13  * Sources:       ppp.c, isdn_ppp.c
 14  * 
 15  *     Copyright (c) 1998-1999 Dag Brattli, All Rights Reserved.
 16  *      
 17  *     This program is free software; you can redistribute it and/or 
 18  *     modify it under the terms of the GNU General Public License as 
 19  *     published by the Free Software Foundation; either version 2 of 
 20  *     the License, or (at your option) any later version.
 21  *  
 22  *     Neither Dag Brattli nor University of Tromsų admit liability nor
 23  *     provide warranty for any of this software. This material is 
 24  *     provided "AS-IS" and at no charge.
 25  *     
 26  ********************************************************************/
 27 
 28 #include <linux/string.h>
 29 
 30 #include <net/irda/irda.h>
 31 #include <net/irda/irqueue.h>
 32 #include <net/irda/irlap.h>
 33 #include <net/irda/irlap_comp.h>
 34 #include "../../drivers/net/zlib.h"
 35 
 36 hashbin_t *irlap_compressors = NULL;
 37 
 38 /*
 39  * Function irda_register_compressor (cp)
 40  *
 41  *    Register new compressor with the IrLAP
 42  *
 43  */
 44 int irda_register_compressor( struct compressor *cp)
 45 {
 46         struct irda_compressor *new;
 47 
 48         IRDA_DEBUG( 4, __FUNCTION__ "()\n");
 49 
 50         /* Check if this compressor has been registred before */
 51         if ( hashbin_find ( irlap_compressors, cp->compress_proto, NULL)) {
 52                 IRDA_DEBUG( 0, __FUNCTION__ "(), Compressor already registered\n");
 53                 return 0;
 54         }
 55         
 56         /* Make new IrDA compressor */
 57         new = (struct irda_compressor *) 
 58                 kmalloc( sizeof( struct irda_compressor), GFP_KERNEL);
 59         if (new == NULL)
 60                 return 1;
 61                 
 62         memset( new, 0, sizeof( struct irda_compressor));
 63         new->cp = cp;
 64 
 65         /* Insert IrDA compressor into hashbin */
 66         hashbin_insert( irlap_compressors, (irda_queue_t *) new, cp->compress_proto,
 67                         NULL);
 68         
 69         return 0;
 70 }
 71 
 72 /*
 73  * Function irda_unregister_compressor (cp)
 74  *
 75  *    Unregister compressor
 76  *
 77  */
 78 void irda_unregister_compressor ( struct compressor *cp)
 79 {
 80         struct irda_compressor *node;
 81 
 82         IRDA_DEBUG( 4, __FUNCTION__ "()\n");
 83 
 84         node = hashbin_remove( irlap_compressors, cp->compress_proto, NULL);
 85         if ( !node) {
 86                 IRDA_DEBUG( 0, __FUNCTION__ "(), compressor not found!\n");
 87                 return;
 88         }       
 89         kfree( node);
 90 }
 91 
 92 /*
 93  * Function irda_set_compression (self, proto)
 94  *
 95  *    The the compression protocol to be used by this session
 96  *
 97  */
 98 int irda_set_compression( struct irlap_cb *self, int proto)
 99 {
100         struct compressor *cp;
101         struct irda_compressor *comp;
102 
103         __u8 options[CILEN_DEFLATE];
104 
105         IRDA_DEBUG( 4, __FUNCTION__ "()\n");
106 
107         ASSERT( self != NULL, return -ENODEV;);
108         ASSERT( self->magic == LAP_MAGIC, return -EBADR;);
109 
110         /* Initialize options */
111         options[0] = CI_DEFLATE;
112         options[1] = CILEN_DEFLATE;
113         options[2] = DEFLATE_METHOD( DEFLATE_METHOD_VAL);
114         options[3] = DEFLATE_CHK_SEQUENCE;
115 
116         comp = hashbin_find( irlap_compressors, proto, NULL);
117         if ( !comp) {
118                 IRDA_DEBUG( 0, __FUNCTION__ "(), Unable to find compressor\n");
119                 return -1;
120         }
121 
122         cp = comp->cp;
123         /* 
124          *  Compressor part
125          */
126         if ( self->compressor.state != NULL)
127                 (*self->compressor.cp->comp_free)( self->compressor.state);
128         self->compressor.state = NULL;
129         
130         self->compressor.cp = cp;
131         self->compressor.state = cp->comp_alloc( options, sizeof( options));
132         if ( self->compressor.state == NULL) {
133                 IRDA_DEBUG( 0, __FUNCTION__ "(), Failed!\n");
134                 return -ENOBUFS;
135         }
136 
137         /* 
138          *  Decompress part
139          */
140         
141         if ( self->decompressor.state != NULL)
142                 irda_decomp_free( self->decompressor.state);
143         self->decompressor.state = NULL;
144         
145         self->decompressor.cp = cp;
146         self->decompressor.state = cp->decomp_alloc( options, sizeof( options));
147         if ( self->decompressor.state == NULL) {
148                 IRDA_DEBUG( 0, __FUNCTION__ "(), Failed!\n");
149                 return -ENOBUFS;
150         }
151         return 0;
152 }
153 
154 /*
155  * Function irda_free_compression (self)
156  *
157  *    
158  *
159  */
160 void irda_free_compression( struct irlap_cb *self)
161 {
162         IRDA_DEBUG( 4, __FUNCTION__ "()\n");
163 
164         if ( self->compressor.state) {
165                 irda_comp_free( self->compressor.state);
166                 self->compressor.state = NULL;
167         }
168         
169         if ( self->decompressor.state) {
170                 irda_decomp_free( self->decompressor.state);
171                 self->decompressor.state = NULL;
172         }
173 }
174 
175 /*
176  * Function irlap_compress_init (self)
177  *
178  *    
179  *
180  */
181 void irlap_compressor_init( struct irlap_cb *self, int compress)
182 {
183         int debug = TRUE;
184         __u8 options[CILEN_DEFLATE];
185 
186         IRDA_DEBUG(4, __FUNCTION__ "()\n");
187 
188         ASSERT( self != NULL, return;);
189         ASSERT( self->magic == LAP_MAGIC, return;);
190         
191         /* Initialize options */
192         options[0] = CI_DEFLATE;
193         options[1] = CILEN_DEFLATE;
194         options[2] = DEFLATE_METHOD_VAL;
195         options[3] = DEFLATE_CHK_SEQUENCE;
196         
197         /*
198          *  We're agreeing to send compressed packets.
199          */
200         if ( self->compressor.state == NULL) {
201                 IRDA_DEBUG( 0, __FUNCTION__ "(), state == NULL\n");
202                 return;
203         }
204         
205         if ((*self->compressor.cp->comp_init)( self->compressor.state, 
206                                                options, sizeof( options),
207                                                0, 0, debug)) 
208         {
209                 IRDA_DEBUG( 0, __FUNCTION__ "(), Compressor running!\n");
210                 /* ppp->flags |= SC_COMP_RUN; */
211         }
212         
213         /*
214          *  Initialize decompressor
215          */
216         if ( self->decompressor.state == NULL) {
217                 IRDA_DEBUG( 0, __FUNCTION__ "(), state == NULL\n");
218                 return;
219         }
220         
221         if (( self->decompressor.cp->decomp_init)( self->decompressor.state,
222                                                    options, sizeof( options),
223                                                    0, 0, 0, debug)) 
224         {
225                 IRDA_DEBUG( 0, __FUNCTION__ "(), Decompressor running!\n");     
226                 
227                 /* ppp->flags |= SC_DECOMP_RUN; */
228                 /* ppp->flags &= ~(SC_DC_ERROR | SC_DC_FERROR); */
229         }
230 }
231 
232 /*
233  * Function irlap_compress_frame (self, skb)
234  *
235  *
236  *
237  */
238 struct sk_buff *irlap_compress_frame( struct irlap_cb *self, 
239                                       struct sk_buff *skb)
240 {
241         struct sk_buff *new_skb;
242         int count;
243         
244         ASSERT( skb != NULL, return NULL;);
245         
246         IRDA_DEBUG(4, __FUNCTION__ "() skb->len=%d, jiffies=%ld\n", (int) skb->len,
247               jiffies);
248 
249         ASSERT( self != NULL, return NULL;);
250         ASSERT( self->magic == LAP_MAGIC, return NULL;);
251 
252         /* Check if compressor got initialized */
253         if ( self->compressor.state == NULL) {
254                 /* Tell peer that this frame is not compressed */
255                 skb_push( skb, LAP_COMP_HEADER);
256                 skb->data[0] = IRDA_NORMAL;
257 
258                 return skb;
259         }
260 
261         /* FIXME: Find out what is the max overhead (not 10) */
262         new_skb = dev_alloc_skb( skb->len+LAP_MAX_HEADER+10);
263         if(!new_skb)
264                 return skb;
265 
266         skb_reserve( new_skb, LAP_MAX_HEADER);
267         skb_put( new_skb, skb->len+10);
268         
269         count = (self->compressor.cp->compress)( self->compressor.state, 
270                                                  skb->data, new_skb->data, 
271                                                  skb->len, new_skb->len);
272         if( count <= 0) {
273                 IRDA_DEBUG(4, __FUNCTION__ "(), Unable to compress frame!\n");
274                 dev_kfree_skb( new_skb);
275 
276                 /* Tell peer that this frame is not compressed */
277                 skb_push( skb, 1);
278                 skb->data[0] = IRDA_NORMAL;
279 
280                 return skb;
281         }
282         skb_trim( new_skb, count);
283 
284         /* Tell peer that this frame is compressed */
285         skb_push( new_skb, 1);
286         new_skb->data[0] = IRDA_COMPRESSED;
287 
288         dev_kfree_skb( skb);
289         
290         IRDA_DEBUG(4, __FUNCTION__ "() new_skb->len=%d\n, jiffies=%ld", 
291               (int) new_skb->len, jiffies);
292         
293         return new_skb;
294 }
295 
296 /*
297  * Function irlap_decompress_frame (self, skb)
298  *
299  *    
300  *
301  */
302 struct sk_buff *irlap_decompress_frame( struct irlap_cb *self, 
303                                         struct sk_buff *skb)
304 {
305         struct sk_buff *new_skb;
306         int count;
307 
308         IRDA_DEBUG( 4, __FUNCTION__ "() skb->len=%d\n", (int) skb->len);
309 
310         ASSERT( self != NULL, return NULL;);
311         ASSERT( self->magic == LAP_MAGIC, return NULL;);
312 
313         ASSERT( self->compressor.state != NULL, return NULL;);
314 
315         /* Check if frame is compressed */
316         if ( skb->data[0] == IRDA_NORMAL) {
317 
318                 /* Remove compression header */
319                 skb_pull( skb, LAP_COMP_HEADER);
320 
321                 /*
322                  * The frame is not compressed. Pass it to the
323                  * decompression code so it can update its
324                  * dictionary if necessary.
325                  */
326                 irda_incomp( self->decompressor.state, skb->data, skb->len);
327 
328                 return skb;
329         }
330 
331         /* Remove compression header */
332         skb_pull( skb, LAP_COMP_HEADER);
333 
334         new_skb = dev_alloc_skb( 2048); /* FIXME: find the right size */
335         if(!new_skb)
336                 return skb;
337         skb_put( new_skb, 2048);
338 
339         count = irda_decompress( self->decompressor.state, skb->data, 
340                                  skb->len, new_skb->data, new_skb->len);
341         if ( count <= 0) {
342                 IRDA_DEBUG( 4, __FUNCTION__ "(), Unable to decompress frame!\n");
343                 
344                 dev_kfree_skb( new_skb);
345                 return skb;
346         }
347 
348         skb_trim( new_skb, count);
349         
350         IRDA_DEBUG( 4, __FUNCTION__ "() new_skb->len=%d\n", (int) new_skb->len);
351 
352         return new_skb;
353 }
354 
355 

~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~ [ freetext search ] ~ [ file search ] ~

This page was automatically generated by the LXR engine.
Visit the LXR main site for more information.