ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/gvpe/src/rohc/d_ip.c
Revision: 1.2
Committed: Sun Feb 8 07:24:25 2004 UTC (20 years, 4 months ago) by pcg
Content type: text/plain
Branch: MAIN
CVS Tags: rel-1_9, rel-1_8, VPE_1_6, rel-1_7, VPE-1_6_1
Changes since 1.1: +9 -11 lines
Log Message:
*** empty log message ***

File Contents

# User Rev Content
1 pcg 1.1 /*
2     ROHC Project 2003 at Lulea University of Technology, Sweden.
3     Authors: Andreas Vernersson <andver-8@student.luth.se>
4     Daniel Pettersson <danpet-7@student.luth.se>
5     Erik Soderstrom <soderstrom@yahoo.com>
6     Fredrik Lindstrom <frelin-9@student.luth.se>
7     Johan Stenmark <johste-8@student.luth.se>
8     Martin Juhlin <juhlin@users.sourceforge.net>
9     Mikael Larsson <larmik-9@student.luth.se>
10     Robert Maxe <robmax-1@student.luth.se>
11    
12     Copyright (C) 2003 Andreas Vernersson, Daniel Pettersson,
13     Erik Soderström, Fredrik Lindström, Johan Stenmark,
14     Martin Juhlin, Mikael Larsson, Robert Maxe.
15    
16     This program is free software; you can redistribute it and/or modify
17     it under the terms of the GNU General Public License as published by
18     the Free Software Foundation; either version 2 of the License, or
19     (at your option) any later version.
20    
21     This program is distributed in the hope that it will be useful,
22     but WITHOUT ANY WARRANTY; without even the implied warranty of
23     MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
24     GNU General Public License for more details.
25    
26     You should have received a copy of the GNU General Public License
27     along with this program; if not, write to the Free Software
28     Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
29     */
30     // IP-Only profile in decompressor
31    
32     /* The decode functions decode the packet, control CRC
33     * and if crc-fails the try a new decompression with a
34     * other SN number. The decode functions returns some
35     * kind of ROHC_ERROR or if it is correct decoded the
36     * length of the decoded packet is returned.
37     */
38    
39     #include "rohc.h"
40     #include "decomp.h"
41    
42     #include "d_ip.h"
43     #include "d_util.h"
44     #include "comp.h"
45     #include "c_util.h"
46    
47     //--------------------------------------------------------- Helpfunctions
48    
49     /* Decode a UO-0 package */
50     static int decode_uo0(
51     struct sd_rohc * state,
52     struct sd_context * context,
53     unsigned char * head,
54     unsigned char * src,
55     unsigned char * dest,
56     int payload_size
57     );
58    
59     /* Decode a UO-1 package */
60     static int decode_uo1(
61     struct sd_rohc * state,
62     struct sd_context * context,
63     unsigned char * head,
64     unsigned char * src2,
65     unsigned char * dest,
66     int payload_size
67     );
68    
69     /* Decode a UO-2 package */
70     static int decode_uor2(
71     struct sd_rohc * state,
72     struct sd_context * context,
73     unsigned char * head,
74     unsigned char * src2,
75     unsigned char * dest,
76     int payload_size
77     );
78    
79     /* Decode a IR-Dyn package */
80     static int decode_irdyn(
81     struct sd_rohc * state,
82     struct sd_context * context,
83     unsigned char * head,
84     unsigned char * src2,
85     unsigned char * dest,
86     int payload_size
87     );
88    
89     /* Decode extention 0 */
90     static int decode_extention0(unsigned char * src, int * sn, int * ip_id);
91    
92     /* Decode extention 1 */
93     static int decode_extention1(unsigned char * src, int * sn, int * ip_id);
94    
95     /* Decode extention 2 */
96     static int decode_extention2(unsigned char * src, int * sn, int * ip_id, int * ip_id2);
97    
98     /* Decode extention 3
99     * - Updates random fields in the s_iponly_change
100     * - May update the SN value with 8 lower bits. sn_size is then changed
101     */
102     static int decode_extention3(unsigned char * src, struct sd_context * context, struct sd_rohc *state,
103     int * sn, int * sn_size, int * ip_id_changed, int * id2_updated);
104    
105     // Make a copy of the "active"-struct to the "last"-struct.
106     static void syncronize(struct s_iponly_profile_data *);
107    
108     // Decode package type
109     static int package_type(const unsigned char * p);
110    
111     /* Deceide the extention type */
112     static int extention_type(const unsigned char * p);
113    
114     /* Write a uncompressed IP v4 header */
115     static void write_uncompressed_ip4(
116     struct s_iponly_change * active1,
117     int ip_id,
118     unsigned char * dest,
119     int payload_size
120     );
121    
122    
123     /* Copy the last-struct to active-struct. */
124     static void sync_on_failure(struct s_iponly_profile_data * pro);
125    
126     /* Decode inner IP flags and fields. Storage the values
127     * in a IP-head struct.
128     */
129     static int decode_inner_header_flags(
130     unsigned char * flags,
131     unsigned char * fields,
132     struct iphdr * ip,
133     int * rnd, int * nbo);
134    
135     /* Decode outer IP flags and fields. Storage the values
136     * in a IP-head struct.
137     */
138     static int decode_outer_header_flags(
139     unsigned char * flags,
140     unsigned char * fields,
141     struct iphdr * ip,
142     int * rnd, int * nbo,
143     int * ip_changed);
144    
145     /* A functions that decode uo0 and uo1 packets
146     *
147     */
148     static int help_to_decode_uo0_and_uo1(
149     struct sd_context * context,
150     unsigned char * src,
151     unsigned char * dest,
152     int * payload_size,
153     int sn_bits,
154     int number_of_sn_bits,
155     int * id,
156     int number_of_id_bits,
157     int * id2,
158     int * sn,
159     int * calc_crc
160     );
161    
162     /* A functions that decode uor2 packets
163     *
164     */
165     static int help_to_decode_uor2(
166     struct sd_rohc * state,
167     struct sd_context * context,
168     unsigned char * src2,
169     unsigned char * dest,
170     int * payload_size,
171     int * id,
172     int * id2,
173     int * sn,
174     int * sn_size,
175     int sn_bits,
176     int ext,
177     int * calc_crc
178     );
179    
180     /* The function that try to correct a packet after
181     * a crc-failure.
182     * It try with an other SN value.
183     */
184     static int act_on_crc_failure(
185     struct sd_rohc * state,
186     struct sd_context * context,
187     unsigned char * src,
188     unsigned char * dest,
189     int sn_size,
190     int * sn_curr1,
191     int sn_bits,
192     int * payload_size,
193     int * id,
194     int id_size,
195     int * id2,
196     int * calc_crc,
197     int * real_crc,
198     int ext
199     );
200    
201     static void update_inter_packet(struct s_iponly_profile_data * pro);
202     //---------------------------------------------------------- Code
203    
204     // To allocate profile data
205     void * iponly_allocate_decode_data(void)
206     {
207     struct s_iponly_profile_data * data;
208     struct s_iponly_change * ch;
209     void * p = kmalloc(sizeof(struct s_iponly_profile_data) + 4 * sizeof(struct s_iponly_change),
210     GFP_ATOMIC);
211    
212     if (p==NULL) {
213     rohc_debugf(0, "iponly_allocate_decode_data(): no mem for ip profile data\n");
214     return NULL;
215     }
216    
217     data = (struct s_iponly_profile_data *)p;
218     ch = (struct s_iponly_change *)(data + 1);
219    
220     memset(p, 0, sizeof(struct s_iponly_profile_data) +
221     4 * sizeof(struct s_iponly_change) );
222    
223     data->last1 = ch; ch++;
224     data->active1 = ch; ch++;
225     data->last2 = ch; ch++;
226     data->active2 = ch;
227    
228     return p;
229     }
230    
231     // To deallocate profile data
232     void iponly_free_decode_data(void * p)
233     {
234     kfree(p);
235     }
236    
237     // Decode an IR-package and initalize context
238     int iponly_decode_ir(
239     struct sd_rohc * state,
240     struct sd_context * context,
241     unsigned char * src,
242     int copy_size,
243     int dynamic_present,
244     unsigned char * dest
245     )
246     {
247     struct s_iponly_profile_data * pro = context->data;
248     struct s_iponly_change * active1 = pro->active1;
249     struct s_iponly_change * active2 = pro->active2;
250    
251     unsigned char * s = src;
252     unsigned char * d = dest;
253    
254     int size, sn;
255    
256     pro->current_packet_time = get_microseconds();
257    
258     // Ip4 static
259     size = d_decode_static_ip4(s, &active1->ip);
260    
261     if (active1->ip.protocol == PROTOCOL_IP_IN_IP){
262     pro->multiple_ip = 1;
263     rohc_debugf(1, "Multiple IP header\n");
264     }else{
265     pro->multiple_ip = 0;
266     }
267    
268     if (size == -1) {
269     return ROHC_ERROR;
270     }
271     s += size; copy_size -= size;
272    
273     // If multiple-ip-header
274     if(pro->multiple_ip){
275     size = d_decode_static_ip4(s, &active2->ip);
276     s += size; copy_size -= size;
277     if (size == -1) {
278     return ROHC_ERROR;
279     }
280     }
281    
282     // Dynamic field
283     if (dynamic_present) {
284     size = d_decode_dynamic_ip4(s, &active1->ip, &active1->rnd, &active1->nbo);
285     s += size; copy_size -= (size + 2);
286    
287     // If multiple-ip-header
288     if(pro->multiple_ip){
289     size = d_decode_dynamic_ip4(s, &active2->ip, &active2->rnd, &active2->nbo);
290     s += size; copy_size -= size;
291     }
292     // Reset the correction-counter
293     pro->counter = 0;
294    
295     // Get and set SN
296 pcg 1.2 sn = ntohs(* ((u16 *)s));
297 pcg 1.1 d_lsb_init(&pro->sn, sn, -1);
298     d_ip_id_init(&pro->ip_id1, ntohs(active1->ip.id), sn);
299     s += 2;
300     context->state = ROHC_FULL_CONTEXT;
301    
302     // If multiple-ip-header
303     if(pro->multiple_ip){
304     d_ip_id_init(&pro->ip_id2, ntohs(active2->ip.id), sn);
305     }
306    
307    
308     } else if (context->state != ROHC_FULL_CONTEXT) {
309     // in static/no context and not get dynamic part
310     return ROHC_ERROR;
311     }
312    
313    
314     // Header write
315     if (pro->multiple_ip){
316     write_uncompressed_ip4(active1, ntohs(active1->ip.id), d, copy_size+sizeof(struct iphdr));
317     d += sizeof(struct iphdr);
318     write_uncompressed_ip4(active2, ntohs(active2->ip.id), d, copy_size);
319    
320     }else{
321     write_uncompressed_ip4(active1, ntohs(active1->ip.id), d, copy_size);
322     }
323     d += sizeof(struct iphdr);
324    
325     // Syncronizerar strukterna
326     syncronize(pro);
327    
328     // Update the inter-packet variable
329     update_inter_packet(pro);
330    
331     // Copy payload
332     if (copy_size == 0) return ROHC_OK_NO_DATA;
333    
334     memcpy(d, s, copy_size);
335    
336     // Statistics:
337     context->header_compressed_size += s - src;
338     c_add_wlsb(context->header_16_compressed, 0,0, s - src);
339     context->header_uncompressed_size += (pro->multiple_ip+1)*sizeof(struct iphdr);
340     c_add_wlsb(context->header_16_uncompressed, 0, 0, (pro->multiple_ip+1)*sizeof(struct iphdr));
341    
342     return copy_size + (pro->multiple_ip + 1) * sizeof(struct iphdr);
343     }
344    
345     // Calculate the size of data in an IR-package.
346     // return : size or zero.
347     int iponly_detect_ir_size(unsigned char * first_byte, int second_byte_add)
348     {
349     int ret = 10;
350     int d = GET_BIT_0(first_byte);
351     if (d) ret += 5 + 2;
352     if (first_byte[second_byte_add + 2] != 0x40) return 0;
353     if (first_byte[second_byte_add + 3] == PROTOCOL_IP_IN_IP){
354     ret += 10;
355     if (d) ret += 5;
356     if (first_byte[second_byte_add + 12] != 0x40) return 0;
357     }
358     return ret;
359     }
360    
361     // Calculate the size of data in an IR-package.
362     // return : size or zero.
363     int iponly_detect_ir_dyn_size(unsigned char * first_byte, struct sd_context *c)
364     {
365     struct s_iponly_profile_data * pro = c->data;
366     if (pro->active1->ip.protocol == PROTOCOL_IP_IN_IP) return 12;
367     return 7;
368     }
369    
370     // Decode all package except IR-package.
371     int iponly_decode(
372     struct sd_rohc * state,
373     struct sd_context * context,
374     unsigned char * src,
375     int size,
376     int second_byte,
377     unsigned char * dest
378     )
379     {
380     struct s_iponly_profile_data * pro = context->data;
381     // ---- DEBUG ----
382     int i; unsigned char * p;
383    
384     struct s_iponly_change * active1 = pro->active1;
385     struct s_iponly_change * active2 = pro->active2;
386     struct s_iponly_change * last1 = pro->last1;
387     struct s_iponly_change * last2 = pro->last2;
388    
389     pro->current_packet_time = get_microseconds();
390    
391     rohc_debugf(2,"(iponly_decode) nbo = %d rnd = %d\n", last1->nbo, last1->rnd);
392     if (pro->multiple_ip){
393     rohc_debugf(2,"Multiple ip-header\n");
394     rohc_debugf(2,"(iponly_decode) nbo2 = %d rnd2 = %d\n", last2->nbo, last2->rnd);
395     }
396     if (memcmp(active1, last1, sizeof(struct s_iponly_change)) != 0) {
397     rohc_debugf(0,"(iponly_decode) last1 and active1 struct is not synchronized\n");
398     p = (unsigned char *)last1;
399     for (i = 0; i < sizeof(struct s_iponly_change); i++) {
400     rohc_debugf(1, "%2x ", p[i]);
401     }
402     rohc_debugf(1, "\nvs\n");
403     p = (unsigned char *)active1;
404     for (i = 0; i < sizeof(struct s_iponly_change); i++) {
405     rohc_debugf(1, "%2x ", p[i]);
406     }
407     rohc_debugf(1,"\n");
408     }
409     if (memcmp(active2, last2, sizeof(struct s_iponly_change)) != 0) {
410     rohc_debugf(0,"(iponly_decode) last2 and active2 struct is not synchronized\n");
411     p = (unsigned char *)last2;
412     for (i = 0; i < sizeof(struct s_iponly_change); i++) {
413     rohc_debugf(1,"%2x ", p[i]);
414     }
415     rohc_debugf(1,"\nvs\n");
416     p = (unsigned char *)active2;
417     for (i = 0; i < sizeof(struct s_iponly_change); i++) {
418     rohc_debugf(1,"%2x ", p[i]);
419     }
420     rohc_debugf(1,"\n");
421     }
422     // ---- DEBUG ----
423    
424     if (context->state == ROHC_NO_CONTEXT) return ROHC_ERROR;
425    
426     switch(package_type(src)) {
427     case PACKAGE_UO_0:
428     pro->package_type = PACKAGE_UO_0;
429     if (context->state == ROHC_STATIC_CONTEXT) return ROHC_ERROR;
430     return decode_uo0(state, context, src, src + second_byte,
431     dest, size - second_byte);
432     case PACKAGE_UO_1:
433     pro->package_type = PACKAGE_UO_1;
434     if (context->state == ROHC_STATIC_CONTEXT) return ROHC_ERROR;
435     return decode_uo1(state, context, src, src + second_byte,
436     dest, size - second_byte);
437     case PACKAGE_UOR_2:
438     pro->package_type = PACKAGE_UOR_2;
439     return decode_uor2(state, context, src, src + second_byte,
440     dest, size - second_byte);
441     case PACKAGE_IR_DYN:
442     return decode_irdyn(state, context, src, src + second_byte,
443     dest, size - second_byte);
444     default:
445     rohc_debugf(0,"(Ip-only) Unknown package.\n");
446     return ROHC_ERROR;
447     }
448     }
449    
450     static int iponly_get_sn(struct sd_context * context)
451     {
452     struct s_iponly_profile_data * pro = context->data;
453     return d_get_lsb_ref(&pro->sn);
454     }
455    
456     static struct s_profile d_ip_profile = {4, "1.0", "IP / Decompressor",
457     iponly_decode,
458     iponly_decode_ir,
459     iponly_allocate_decode_data,
460     iponly_free_decode_data,
461     iponly_detect_ir_size,
462     iponly_detect_ir_dyn_size,
463     iponly_get_sn
464     };
465    
466     struct s_profile * iponly_profile_create()
467     {
468     return &d_ip_profile;
469     }
470    
471     // --------------------------------------------------------- Package type decoder
472    
473     /* Decode a UO-0 package */
474     static int decode_uo0(
475     struct sd_rohc * state,
476     struct sd_context * context,
477     unsigned char * head,
478     unsigned char * src,
479     unsigned char * dest,
480     int payload_size
481     )
482     {
483     unsigned char *saved_src = src;
484     struct s_iponly_profile_data * pro = context->data;
485     int multiple_ip = pro->multiple_ip;
486     int id, id2=-1, sn, sn_bits = GET_BIT_3_6(head), sn_size = 4;
487     int calc_crc, real_crc = GET_BIT_0_2(head);
488     int extra_fields = 0, org_payload_size = payload_size;
489     // Do the decoding / find ip-id
490     extra_fields = help_to_decode_uo0_and_uo1(context, src, dest, &payload_size, sn_bits, sn_size , &id, 0 , &id2, &sn, &calc_crc);
491    
492     if (calc_crc != real_crc) {
493     rohc_debugf(0,"UO-0: CRC failure (calc) %x vs %x (real)\n",
494     calc_crc, real_crc);
495    
496     payload_size = org_payload_size;
497     act_on_crc_failure(0,context, src, dest, sn_size, &sn, sn_bits, &payload_size, &id, 0, &id2, &calc_crc, &real_crc, 0);
498     return ROHC_ERROR_CRC;
499     }
500    
501     // if any crc-correction then three correct packet need to pass crc
502     if(pro->counter){
503     if(pro->counter==1){
504    
505     rohc_debugf(2,"Throw away packet, just 2 packages right so far\n");
506    
507     pro->counter++;
508    
509     // Update the inter-packet variable
510     update_inter_packet(pro);
511     syncronize(pro);
512    
513     d_lsb_sync_ref(&pro->sn);
514     d_lsb_update(&pro->sn, sn);
515     d_ip_id_update(&pro->ip_id1, id, sn);
516     if (pro->multiple_ip)
517     d_ip_id_update(&pro->ip_id2, id2, sn);
518    
519     return ROHC_ERROR_CRC;
520    
521     }else if(pro->counter==2){
522     pro->counter = 0;
523     rohc_debugf(2,"The rapair is deemed successful\n");
524     }else{
525     rohc_debugf(2,"XX Should not happen XX\n");
526     }
527     }
528    
529     src += extra_fields;
530    
531     // Update the inter-packet variable
532     update_inter_packet(pro);
533     syncronize(pro);
534    
535     // Update lsb and id structs on CRC-success
536     d_lsb_sync_ref(&pro->sn);
537     d_lsb_update(&pro->sn, sn);
538     d_ip_id_update(&pro->ip_id1, id, sn);
539     if (pro->multiple_ip){
540     d_ip_id_update(&pro->ip_id2, id2, sn);
541     dest += sizeof(struct iphdr);
542     }
543    
544     // Payload
545     dest += sizeof(struct iphdr);
546     memcpy(dest, src, payload_size);
547    
548     // Statistics:
549     context->header_compressed_size += src - saved_src;
550     c_add_wlsb(context->header_16_compressed, 0,0, src - saved_src);
551     context->header_uncompressed_size += (multiple_ip+1)*sizeof(struct iphdr);
552     c_add_wlsb(context->header_16_uncompressed, 0, 0, (multiple_ip+1)*sizeof(struct iphdr));
553    
554     return payload_size + (multiple_ip + 1) * sizeof(struct iphdr);
555     }
556    
557    
558    
559     /* Decode a UO-1 package */
560     static int decode_uo1(
561     struct sd_rohc * state,
562     struct sd_context * context,
563     unsigned char * head,
564     unsigned char * src,
565     unsigned char * dest,
566     int payload_size
567     )
568     {
569     unsigned char *saved_src = src;
570     struct s_iponly_profile_data * pro = context->data;
571    
572     int id = GET_BIT_0_5(head), id2=-1;
573     int sn, sn_bits = GET_BIT_3_7(src), sn_size = 5;
574     int org_payload_size, extra_fields=0;
575     int calc_crc, real_crc = GET_BIT_0_2(src);
576     src++; payload_size--;
577     org_payload_size = payload_size;
578    
579     // Decode the id and sn
580     extra_fields = help_to_decode_uo0_and_uo1(context, src, dest, &payload_size, sn_bits, sn_size , &id, 6 , &id2, &sn, &calc_crc);
581    
582     if (calc_crc != real_crc) {
583     rohc_debugf(0,"UO-1: CRC failure (calc) %x vs %x (real)\n",
584     calc_crc, real_crc);
585     payload_size = org_payload_size;
586     act_on_crc_failure(0,context, src, dest, sn_size, &sn, sn_bits, &payload_size, &id, 6, &id2, &calc_crc, &real_crc, 0);
587     return ROHC_ERROR_CRC;
588     }
589    
590     if(pro->counter){
591     if(pro->counter==1){
592    
593     rohc_debugf(2,"Throw away packet, just 2 packages right so far\n");
594    
595     pro->counter++;
596     // Update the inter-packet variable
597    
598     update_inter_packet(pro);
599     syncronize(pro);
600    
601     d_lsb_sync_ref(&pro->sn);
602     d_lsb_update(&pro->sn, sn);
603     d_ip_id_update(&pro->ip_id1, id, sn);
604     if (pro->multiple_ip)
605     d_ip_id_update(&pro->ip_id2, id2, sn);
606    
607     return ROHC_ERROR_CRC;
608    
609     }else if(pro->counter==2){
610     pro->counter = 0;
611     rohc_debugf(2,"The rapair is deemed successful\n");
612     }else{
613     rohc_debugf(2,"XX Should not happen XX\n");
614     }
615     }
616    
617     src += extra_fields;
618    
619     // Update the inter-packet variable
620     update_inter_packet(pro);
621    
622     syncronize(pro);
623    
624     d_lsb_sync_ref(&pro->sn);
625     d_lsb_update(&pro->sn, sn);
626     d_ip_id_update(&pro->ip_id1, id, sn);
627     if (pro->multiple_ip){
628     d_ip_id_update(&pro->ip_id2, id2, sn);
629     dest += sizeof(struct iphdr);
630     }
631    
632     // Payload
633     dest += sizeof(struct iphdr);
634     memcpy(dest, src, payload_size);
635    
636     // Statistics:
637     context->header_compressed_size += src - saved_src;
638     c_add_wlsb(context->header_16_compressed, 0,0, src - saved_src);
639     context->header_uncompressed_size += (pro->multiple_ip+1)*sizeof(struct iphdr);
640     c_add_wlsb(context->header_16_uncompressed, 0, 0, (pro->multiple_ip+1)*sizeof(struct iphdr));
641    
642     return payload_size + (pro->multiple_ip + 1) * sizeof(struct iphdr);
643     }
644    
645    
646     /* Decode a UO-2 package */
647     static int decode_uor2(
648     struct sd_rohc * state,
649     struct sd_context * context,
650     unsigned char * head,
651     unsigned char * src,
652     unsigned char * dest,
653     int payload_size
654     )
655     {
656     unsigned char *saved_src = src;
657     struct s_iponly_profile_data * pro = context->data;
658    
659     int org_payload_size = payload_size, extra_fields = 0;
660     int sn_size = 0;
661     int id = 0, id2 = 0, multiple_id = pro->multiple_ip;
662     int calc_crc = 0;
663     int sn_bits = GET_BIT_0_4(head) , sn = 0;
664     int real_crc = GET_BIT_0_6(src);
665     int ext = GET_BIT_7(src);
666     src++;
667    
668     // Decode
669     extra_fields = help_to_decode_uor2(state, context, src, dest, &payload_size, &id, &id2, &sn, &sn_size, sn_bits, ext, &calc_crc);
670    
671     if (calc_crc != real_crc) {
672     rohc_debugf(0,"UOR-2: CRC failure (calc) %x vs %x (real)\n",
673     calc_crc, real_crc);
674     payload_size = org_payload_size;
675     id =0 ; id2 = 0; calc_crc = 0;
676     act_on_crc_failure(state, context, src, dest, sn_size, &sn, sn_bits, &payload_size, &id, 0, &id2, &calc_crc, &real_crc, ext);
677     return ROHC_ERROR_CRC;
678     }
679    
680     if(pro->counter){
681     if(pro->counter==1){
682    
683     rohc_debugf(2,"Throw away packet, just 2 packages right so far\n");
684    
685     pro->counter++;
686     // Update the inter-packet variable
687    
688     update_inter_packet(pro);
689     syncronize(pro);
690    
691     d_lsb_sync_ref(&pro->sn);
692     d_lsb_update(&pro->sn, sn);
693     d_ip_id_update(&pro->ip_id1, id, sn);
694     if (pro->multiple_ip)
695     d_ip_id_update(&pro->ip_id2, id2, sn);
696    
697     return ROHC_ERROR_CRC;
698    
699     }else if(pro->counter==2){
700     pro->counter = 0;
701     rohc_debugf(2,"The rapair is deemed successful\n");
702     }else{
703     rohc_debugf(2,"XX Should not happen XX\n");
704     }
705     }
706    
707     context->state = ROHC_FULL_CONTEXT;
708    
709     src += extra_fields;
710    
711     // if crc success
712     syncronize(pro);
713    
714     // Update the inter-packet variable
715     update_inter_packet(pro);
716    
717     // Update
718     d_lsb_sync_ref(&pro->sn);
719     d_lsb_update(&pro->sn, sn);
720     d_ip_id_update(&pro->ip_id1, id, sn);
721     if (pro->multiple_ip){
722     d_ip_id_update(&pro->ip_id2, id2, sn);
723     dest += sizeof(struct iphdr);
724     rohc_debugf(2,"Decomps reference ID2 = %d SN = %d\n",pro->ip_id2.id_ref,pro->ip_id2.sn_ref );
725     }
726     // Payload
727     dest += sizeof(struct iphdr);
728     memcpy(dest, src, payload_size);
729     rohc_debugf(2,"Decomps reference ID1 = %d SN = %d\n",pro->ip_id1.id_ref,pro->ip_id1.sn_ref );
730     rohc_debugf(2,"Decomps reference SN = %d\n",d_get_lsb_ref(&pro->sn));
731    
732     // Statistics:
733     context->header_compressed_size += src - saved_src;
734     c_add_wlsb(context->header_16_compressed, 0,0, src - saved_src);
735     context->header_uncompressed_size += (multiple_id+1)*sizeof(struct iphdr);
736     c_add_wlsb(context->header_16_uncompressed, 0, 0, (multiple_id+1)*sizeof(struct iphdr));
737    
738     return payload_size + (multiple_id +1) *sizeof(struct iphdr);
739    
740     }
741    
742    
743     /* Decode a IR-Dyn package */
744     static int decode_irdyn(
745     struct sd_rohc * state,
746     struct sd_context * context,
747     unsigned char * head,
748     unsigned char * src2,
749     unsigned char * dest,
750     int payload_size
751     )
752     {
753     unsigned char *saved_src = src2;
754     struct s_iponly_profile_data * pro = context->data;
755     //struct s_iponly_change * last1 = pro->last1;
756     struct s_iponly_change * active1 = pro->active1;
757     struct s_iponly_change * active2 = pro->active2;
758     int sn = 0, size = d_decode_dynamic_ip4(src2, &active1->ip, &active1->rnd, &active1->nbo);
759     src2 += size; payload_size -= size + 2;
760    
761     if( pro->multiple_ip ){
762     size = d_decode_dynamic_ip4(src2, &active2->ip, &active2->rnd, &active2->nbo);
763     src2 += size; payload_size -= size;
764     }
765 pcg 1.2 sn = ntohs(* ((u16 *)src2));
766 pcg 1.1 d_lsb_init(&pro->sn, sn, -1);
767     d_ip_id_init(&pro->ip_id1,ntohs(active1->ip.id), sn);
768     syncronize(pro);
769     // reset the correction-counter
770     pro->counter = 0;
771     src2 += 2;
772    
773     if (pro->multiple_ip){
774     d_ip_id_init(&pro->ip_id2,ntohs(active2->ip.id), sn);
775     rohc_debugf(2,"Decomps reference ID2 = %d SN = %d\n",pro->ip_id2.id_ref,pro->ip_id2.sn_ref );
776     write_uncompressed_ip4(active1, ntohs(active1->ip.id), dest, payload_size+sizeof(struct iphdr));
777     dest += sizeof(struct iphdr);
778     write_uncompressed_ip4(active2, ntohs(active2->ip.id), dest, payload_size);
779     }else{
780     write_uncompressed_ip4(active1, ntohs(active1->ip.id), dest, payload_size);
781     }
782     context->state = ROHC_FULL_CONTEXT;
783     // Update the inter-packet variable
784     update_inter_packet(pro);
785    
786     dest += sizeof(struct iphdr);
787     memcpy(dest, src2, payload_size);
788     rohc_debugf(2,"Decomps reference ID = %d SN = %d\n",pro->ip_id1.id_ref,pro->ip_id1.sn_ref );
789     rohc_debugf(2,"Decomps reference SN = %d\n",d_get_lsb_ref(&pro->sn));
790    
791     // Statistics:
792     context->header_compressed_size += src2 - saved_src;
793     c_add_wlsb(context->header_16_compressed, 0,0, src2 - saved_src);
794     context->header_uncompressed_size += (pro->multiple_ip+1)*sizeof(struct iphdr);
795     c_add_wlsb(context->header_16_uncompressed, 0, 0, (pro->multiple_ip+1)*sizeof(struct iphdr));
796    
797     return payload_size + ((pro->multiple_ip)+1) * sizeof(struct iphdr);
798     }
799    
800     /* a help function that does the decoding of uo0 and uo1 packets */
801     static int help_to_decode_uo0_and_uo1(
802     struct sd_context * context,
803     unsigned char * src,
804     unsigned char * dest,
805     int * payload_size,
806     int sn_bits,
807     int number_of_sn_bits,
808     int * id,
809     int number_of_id_bits,
810     int * id2,
811     int * sn,
812     int * calc_crc
813     )
814     {
815     struct s_iponly_profile_data * pro = context->data;
816     struct s_iponly_change * active1 = pro->active1;
817     struct s_iponly_change * active2 = pro->active2;
818     int field_counter = 0;
819    
820     *sn = d_lsb_decode(&pro->sn, sn_bits, number_of_sn_bits);
821    
822     if (active1->rnd) {
823 pcg 1.2 *id = ntohs(*((u16 *)src));
824 pcg 1.1 src += 2; field_counter +=2; *payload_size -= 2;
825    
826     } else {
827     if(number_of_id_bits)
828     *id = d_ip_id_decode(&pro->ip_id1, *id, number_of_id_bits, *sn);
829     else
830     *id = d_ip_id_decode(&pro->ip_id1, 0, 0, *sn);
831     }
832    
833     // If multiple ip header
834     if (pro->multiple_ip){
835    
836     if (active2->rnd) {
837 pcg 1.2 *id2 = ntohs(*((u16 *)src));
838 pcg 1.1
839     src +=2; field_counter +=2; *payload_size -= 2;
840     } else {
841     *id2 = d_ip_id_decode(&pro->ip_id2, 0, 0, *sn);
842     }
843     }
844    
845     // Header write
846     if (pro->multiple_ip){
847     write_uncompressed_ip4(active1, *id, dest, *payload_size+sizeof(struct iphdr));
848     write_uncompressed_ip4(active2, *id2, dest+sizeof(struct iphdr),*payload_size);
849    
850     }else{
851     write_uncompressed_ip4(active1, *id, dest, *payload_size);
852     }
853    
854     // Check CRC
855     *calc_crc = crc_calculate(CRC_TYPE_3, dest, (pro->multiple_ip + 1) * sizeof(struct iphdr));
856    
857     return field_counter;
858     }
859    
860     /* a function that does the decoding of uor2 packets */
861     static int help_to_decode_uor2(
862     struct sd_rohc * state,
863     struct sd_context * context,
864     unsigned char * src2,
865     unsigned char * dest,
866     int * payload_size,
867     int * id,
868     int * id2,
869     int * sn,
870     int * sn_size,
871     int sn_bits,
872     int ext,
873     int * calc_crc
874     )
875     {
876     struct s_iponly_profile_data * pro = context->data;
877     struct s_iponly_change * active1 = pro->active1;
878     struct s_iponly_change * active2 = pro->active2;
879     int id2_updated = 0, size = 0;
880     int no_ip_id_update = 0;
881     int field_counter = 0;
882    
883     *sn = sn_bits;
884    
885     if (ext) {
886     // decode extention
887     switch(extention_type(src2)) {
888     case PACKAGE_EXT_0:
889     size = decode_extention0(src2, sn, id);
890     // ip_id_bits == 3
891     *sn_size = 8;
892     *sn = d_lsb_decode(&pro->sn, *sn, *sn_size );
893     *id = d_ip_id_decode(&pro->ip_id1, *id, 3, *sn);
894     *id2 = d_ip_id_decode(&pro->ip_id2, 0, 0, *sn);
895     break;
896    
897     case PACKAGE_EXT_1:
898     size = decode_extention1(src2, sn, id);
899     // ip_id bits == 11
900     *sn_size = 8;
901     *sn = d_lsb_decode(&pro->sn, *sn, *sn_size );
902     *id = d_ip_id_decode(&pro->ip_id1, *id, 11, *sn);
903     *id2 = d_ip_id_decode(&pro->ip_id2, 0, 0, *sn);
904     break;
905    
906     case PACKAGE_EXT_2:
907     size = decode_extention2(src2, sn, id, id2);
908     // ip_id bits == 8
909     *sn_size = 8;
910     *sn = d_lsb_decode(&pro->sn, *sn, *sn_size );
911     *id2 = d_ip_id_decode(&pro->ip_id1, *id, 8, *sn);//inner
912     *id = d_ip_id_decode(&pro->ip_id2, *id2, 11, *sn);//outer
913     break;
914    
915     case PACKAGE_EXT_3:
916     *sn_size = 5;
917     size = decode_extention3(src2, context, state, sn,
918     sn_size, &no_ip_id_update, &id2_updated);
919    
920     rohc_debugf(2,"(iponly_decode) after ext 3 : nbo = %d rnd = %d\n", active1->nbo, active1->rnd);
921    
922     *sn = d_lsb_decode(&pro->sn, *sn, *sn_size );
923    
924     if (no_ip_id_update) {
925     *id = ntohs(active1->ip.id);
926     } else {
927     *id = d_ip_id_decode(&pro->ip_id1, 0, 0, *sn);
928     }
929     if( pro->multiple_ip ){
930     rohc_debugf(2,"(iponly_decode) after ext 3 : nbo2 = %d rnd2 = %d\n", active2->nbo, active2->rnd);
931    
932     if (id2_updated){
933     *id2 = ntohs(active2->ip.id);
934     }else
935     *id2 = d_ip_id_decode(&pro->ip_id2, 0, 0, *sn);
936    
937     }
938     break;
939     }
940    
941    
942     src2 += size;
943     field_counter +=size;
944     *payload_size -= size + 1;
945     } else {
946     // No extention
947     *sn_size = 5;
948     *sn = d_lsb_decode(&pro->sn, *sn , *sn_size);
949    
950     *id = d_ip_id_decode(&pro->ip_id1, 0, 0, *sn);
951     if( pro->multiple_ip)
952     *id2 = d_ip_id_decode(&pro->ip_id1, 0, 0, *sn);
953     *payload_size -= 1;
954     }
955    
956    
957     // Random IP ID ?
958     if (active1->rnd) {
959 pcg 1.2 *id = ntohs(*((u16 *)src2));
960 pcg 1.1 src2 +=2; field_counter +=2; *payload_size -= 2;
961     }
962    
963     // Multiple ip-header
964    
965     if (( pro->multiple_ip )&&( active2->rnd )){
966 pcg 1.2 *id2 = ntohs(*((u16 *)src2));
967 pcg 1.1 src2 +=2; field_counter +=2; *payload_size -= 2;
968     }
969    
970    
971     // Header write
972     if (pro->multiple_ip){
973     write_uncompressed_ip4(active1, *id, dest, *payload_size+sizeof(struct iphdr));
974     write_uncompressed_ip4(active2, *id2, dest+sizeof(struct iphdr),*payload_size);
975     }else{
976     write_uncompressed_ip4(active1, *id, dest, *payload_size);
977     }
978    
979     // CRC-check
980     *calc_crc = crc_calculate(CRC_TYPE_7, dest, (pro->multiple_ip + 1) * sizeof(struct iphdr));
981    
982     return field_counter;
983     }
984    
985    
986    
987    
988    
989     // ---------------------------------------------------------
990    
991     /* Decode extention 0.
992     * - SN value is expanded with 3 lower bits
993     * - IP-ID is replaced with 3 bits
994     */
995     static int decode_extention0(unsigned char * src, int * sn, int * ip_id)
996     {
997     *sn = *sn << 3 | GET_BIT_3_5(src);
998     *ip_id = GET_BIT_0_2(src);
999     return 1;
1000     }
1001    
1002     /* Decode extention 1
1003     * - SN value is expanded with 3 lower bits
1004     * - IP-ID is replaced with 11 bits
1005     */
1006     static int decode_extention1(unsigned char * src, int * sn, int * ip_id)
1007     {
1008     *sn = *sn << 3 | GET_BIT_3_5(src);
1009     *ip_id = GET_BIT_0_2(src);
1010    
1011     src++;
1012     *ip_id = *ip_id << 8 | *src;
1013    
1014     return 2;
1015     }
1016    
1017     /* Decode extention 2
1018     * - SN value is expanded with 3 lower bits
1019     * - IP-ID is replaced with 8 bits
1020     */
1021     static int decode_extention2(unsigned char * src, int * sn, int * ip_id, int * ip_id2)
1022     {
1023    
1024     *sn = *sn << 3 | GET_BIT_3_5(src);
1025     *ip_id2 = GET_BIT_0_2(src);
1026     src++;
1027    
1028     *ip_id2 = *ip_id2 << 8 | *src;
1029     src++;
1030    
1031     *ip_id = *src;
1032     return 3;
1033     }
1034    
1035     /* Decode extention 3
1036     * - Updates random fields in the s_iponly_change
1037     * - May update the SN value with 8 lower bits. sn_size is then changed
1038     */
1039     static int decode_extention3(
1040     unsigned char * src,
1041     struct sd_context * context,
1042     struct sd_rohc * state,
1043     int * sn,
1044     int * sn_size,
1045     int * ip_id_changed,
1046     int * update_id2
1047     )
1048     {
1049     struct s_iponly_profile_data * pro = context->data;
1050     struct s_iponly_change * active1 = pro->active1;
1051     struct s_iponly_change * active2 = pro->active2;
1052     unsigned char * org = src;
1053     unsigned char * fields = src + 1;
1054     int S = GET_BIT_5(src);
1055     int mode = GET_BIT_3_4(src);
1056     int I = GET_BIT_2(src);
1057     int ip = GET_BIT_1(src);
1058     int ip2 = GET_BIT_0(src);
1059     int size;
1060    
1061     src++;
1062    
1063     if (ip) fields++;
1064     if (ip2) fields++;
1065    
1066     if (S) {
1067     *sn = (*sn << 8) + *fields;
1068     *sn_size += 8;
1069     fields++;
1070     }
1071    
1072     if (ip) {
1073     if(pro->multiple_ip){
1074     size = decode_inner_header_flags(src, fields, &active2->ip,
1075     &active2->rnd, &active2->nbo);
1076     }else
1077     size = decode_inner_header_flags(src, fields, &active1->ip,
1078     &active1->rnd, &active1->nbo);
1079     fields += size;
1080     }
1081     if (I) {
1082     if(pro->multiple_ip){
1083 pcg 1.2 active2->ip.id = *((u16 *)fields);
1084 pcg 1.1 fields += 2;
1085     *update_id2 = 1;
1086     }else{
1087 pcg 1.2 active1->ip.id = *((u16 *)fields);
1088 pcg 1.1 fields += 2;
1089     *ip_id_changed = 1;
1090     }
1091     }
1092     if (ip2) {
1093     size = decode_outer_header_flags(src, fields, &active1->ip,
1094     &active1->rnd, &active1->nbo, ip_id_changed);
1095     fields += size;
1096     }
1097    
1098     if(mode != context->mode){
1099     rohc_debugf(2,"mode is not equal on decomp and comp.\n");
1100     d_change_mode_feedback(state, context);
1101     }
1102     return fields - org;
1103     }
1104    
1105     // --------------------------------------------------------- Local utils functions
1106    
1107     // Deceide what package type
1108     static int package_type(const unsigned char * p)
1109     {
1110     if (!GET_BIT_7(p)) {
1111     return PACKAGE_UO_0;
1112     } else if (!GET_BIT_6(p)) {
1113     return PACKAGE_UO_1;
1114     } else if (GET_BIT_5_7(p) == 6) {
1115     return PACKAGE_UOR_2;
1116     } else if (*p == 0xf8) {
1117     return PACKAGE_IR_DYN;
1118     } else if ( (*p & 0xfe) == 0xfc) {
1119     return PACKAGE_IR;
1120     } else {
1121     return PACKAGE_UNKNOWN;
1122     }
1123     }
1124    
1125     // Copy the active-structs to last-structs.
1126     static void syncronize(struct s_iponly_profile_data * pro)
1127     {
1128     memcpy(pro->last1, pro->active1, sizeof(struct s_iponly_change));
1129     memcpy(pro->last2, pro->active2, sizeof(struct s_iponly_change));
1130     }
1131    
1132     // Copy the last-structs to the active-structs.
1133     static void sync_on_failure(struct s_iponly_profile_data * pro)
1134     {
1135     memcpy(pro->active1, pro->last1, sizeof(struct s_iponly_change));
1136     memcpy(pro->active2, pro->last2, sizeof(struct s_iponly_change));
1137     }
1138    
1139     // Deceide the extention type
1140     static int extention_type(const unsigned char * p)
1141     {
1142     return GET_BIT_6_7(p);
1143     }
1144    
1145     /* Decode inner IP flags and fields. Storage the values
1146     * in a IP-head struct.
1147     */
1148     static int decode_inner_header_flags(
1149     unsigned char * flags,
1150     unsigned char * fields,
1151     struct iphdr * ip,
1152     int * rnd, int * nbo)
1153     {
1154     int size = 0;
1155     if (GET_BIT_7(flags)) {
1156     ip->tos = *fields;
1157     fields++; size++;
1158     }
1159     if (GET_BIT_6(flags)) {
1160     ip->ttl = *fields;
1161     fields++; size++;
1162     }
1163     if (GET_BIT_5(flags)) {
1164     ip->frag_off = htons(IP_DF);
1165     } else {
1166     ip->frag_off = 0;
1167     }
1168     if (GET_BIT_4(flags)) {
1169     ip->protocol = *fields;
1170     fields++; size++;
1171     }
1172     if (GET_BIT_3(flags)) {
1173     // TODO, list compression
1174     rohc_debugf(0,"Listcompression is not supported\n");
1175     }
1176     *nbo = GET_BIT_2(flags);
1177     *rnd = GET_BIT_1(flags);
1178     return size;
1179     }
1180    
1181     /* Decode outer IP flags and fields. Storage the values
1182     * in a IP-head struct.
1183     */
1184     static int decode_outer_header_flags(
1185     unsigned char * flags,
1186     unsigned char * fields,
1187     struct iphdr * ip,
1188     int * rnd, int * nbo,
1189     int * updated_id)
1190     {
1191     int size = 0;
1192     if (GET_BIT_7(flags)) {
1193     ip->tos = *fields;
1194     fields++; size++;
1195     }
1196     if (GET_BIT_6(flags)) {
1197     ip->ttl = *fields;
1198     fields++; size++;
1199     }
1200     if (GET_BIT_5(flags)) {
1201     ip->frag_off = htons(IP_DF);
1202     } else {
1203     ip->frag_off = 0;
1204     }
1205     if (GET_BIT_4(flags)) {
1206     ip->protocol = *fields;
1207     fields++; size++;
1208     }
1209     if (GET_BIT_3(flags)) {
1210     // TODO, list compression
1211     rohc_debugf(0,"Listcompression is not supported\n");
1212     }
1213     *nbo = GET_BIT_2(flags);
1214     *rnd = GET_BIT_1(flags);
1215    
1216     if (GET_BIT_0(flags)) {
1217 pcg 1.2 ip->id = *((u16 *)fields);
1218 pcg 1.1 fields += 2; size += 2;
1219     *updated_id = 1;
1220     }
1221     return size;
1222     }
1223    
1224     /* Write a uncompressed IP v4 header */
1225     static void write_uncompressed_ip4(
1226     struct s_iponly_change * active,
1227     int ip_id,
1228     unsigned char * dest,
1229     int payload_size
1230     )
1231     {
1232     struct iphdr * ip = (struct iphdr *)dest;
1233    
1234     // --- static & some changing
1235     memcpy(dest, &active->ip, sizeof(struct iphdr));
1236    
1237     // --- ip-id
1238     ip->id = htons(ip_id);
1239     if (!active->nbo) ip->id = __swab16(ip->id);
1240    
1241     //--- Static-known fields
1242     ip->ihl = 5;
1243    
1244     //--- Interfered fields
1245     ip->tot_len = htons(payload_size + (ip->ihl * 4));
1246     ip->check = 0;
1247     ip->check = ip_fast_csum(dest, ip->ihl);
1248     }
1249    
1250    
1251    
1252     /* This function try to repair the SN in one of two different ways
1253     *
1254     */
1255     static int act_on_crc_failure(
1256     struct sd_rohc * state,
1257     struct sd_context * context,
1258     unsigned char * src,
1259     unsigned char * dest,
1260     int sn_size,
1261     int * sn,
1262     int sn_bits,
1263     int * payload_size,
1264     int * id,
1265     int id_size,
1266     int * id2,
1267     int * calc_crc,
1268     int * real_crc,
1269     int ext
1270     )
1271     {
1272     struct s_iponly_profile_data * pro = context->data;
1273    
1274     int sn_ref = 0, intervall = 0;
1275     int sn_curr2 = 0, sn_curr1 = 0;
1276     int sn_update = 0;
1277    
1278     sync_on_failure(pro);
1279    
1280     if(CRC_ACTION){
1281     rohc_debugf(0,"Try to repair the CRC\n");
1282    
1283     if(pro->last_packet_time) //if last packettime == 0 then IR was just sent and ...
1284     intervall = pro->current_packet_time - pro->last_packet_time;
1285    
1286     if(intervall > ((1 << sn_size)*(pro->inter_arrival_time))){
1287     rohc_debugf(0,"ROHC: repair with the assumption: SN LSB wraparound\n");
1288     rohc_debugf(2,"inter_arrival_time = %d and current intervall is = %d\n", pro->inter_arrival_time, intervall);
1289     rohc_debugf(2,"add %d to SN\n", 1 << sn_size);
1290    
1291     // Try and update the SN
1292     sn_ref = d_get_lsb_ref(&pro->sn);
1293     sn_ref += (1 << sn_size);
1294     d_lsb_sync_ref(&pro->sn);
1295     d_lsb_update(&pro->sn, sn_ref);
1296     *sn = d_lsb_decode(&pro->sn, sn_bits, sn_size );
1297    
1298     pro->counter = 0;
1299    
1300     }else{
1301     // try with the old sn_ref value
1302    
1303     rohc_debugf(0,"ROHC: repair with the assumption: incorrect SN-updates\n");
1304     rohc_debugf(2,"inter_arrival_time = %d and current intervall is = %d\n", pro->inter_arrival_time, intervall);
1305    
1306     // save current referece value
1307     sn_curr1 = d_get_lsb_ref(&pro->sn);
1308     // test with old reference value
1309     d_lsb_update(&pro->sn, d_get_lsb_old_ref(&pro->sn));
1310    
1311     sn_curr2 = d_lsb_decode(&pro->sn, sn_bits, sn_size );
1312    
1313     if( sn_curr2 == *sn){
1314     rohc_debugf(2,"with old ref value we get the same sn\n");
1315     return ROHC_ERROR_CRC;
1316     }
1317     *sn = sn_curr2;
1318     d_lsb_update(&pro->sn, sn_curr2);
1319     sn_update = 1;
1320     pro->counter = 0;
1321     }
1322     rohc_debugf(2,"Try a new decompression with another sn \n");
1323     // Try a new decompression with another SN
1324     switch (pro->package_type){
1325     case PACKAGE_UO_0:
1326     //fall through
1327     case PACKAGE_UO_1:
1328     help_to_decode_uo0_and_uo1(context, src, dest, payload_size, sn_bits, sn_size , id, id_size, id2, sn, calc_crc);
1329     break;
1330     case PACKAGE_UOR_2:
1331     *sn = sn_bits;
1332     help_to_decode_uor2(state, context, src, dest, payload_size, id, id2, sn, &sn_size, sn_bits, ext, calc_crc);
1333     break;
1334     default:
1335     rohc_debugf(0,"(Ip-only) A existing packet?\n");
1336     d_lsb_update(&pro->sn, sn_curr1);
1337     return ROHC_ERROR_CRC;
1338     }
1339    
1340     if (*calc_crc != *real_crc){
1341     rohc_debugf(0,"ROHC: CRC failure also on the second attempt (calc) %x vs %x (real)\n",*calc_crc, *real_crc);
1342     pro->counter = 0;
1343     if(sn_update)
1344     d_lsb_update(&pro->sn, sn_curr1); //reference curr1 should be used
1345     sync_on_failure(pro);
1346     return ROHC_ERROR_CRC;
1347     }
1348     //CRC-pass
1349     rohc_debugf(2,"Update and sync with the new SN then throw away the packet\n");
1350     pro->counter++;
1351     update_inter_packet(pro);
1352    
1353     syncronize(pro);
1354    
1355     if(!sn_update){
1356     d_lsb_sync_ref(&pro->sn);
1357     d_lsb_update(&pro->sn, *sn);
1358     }else
1359     d_lsb_update(&pro->sn, sn_curr2);
1360    
1361     d_ip_id_update(&pro->ip_id1, *id, *sn);
1362     if (pro->multiple_ip)
1363     d_ip_id_update(&pro->ip_id2, *id2, *sn);
1364    
1365     return ROHC_ERROR_CRC;
1366    
1367     }else{
1368     return ROHC_ERROR_CRC;
1369     }
1370     }
1371    
1372     /* Update the inter-packet time, a sort of averange over the last inter-packet times */
1373     static void update_inter_packet(struct s_iponly_profile_data * pro)
1374     {
1375     int last_time = pro->last_packet_time;
1376     int delta = 0;
1377     rohc_debugf(2,"current time = %d and last time = %d\n", pro->current_packet_time, last_time);
1378    
1379     if (last_time)
1380     delta = pro->current_packet_time - last_time;
1381     pro->last_packet_time = pro->current_packet_time;
1382     if (pro->inter_arrival_time){
1383     pro->inter_arrival_time = (pro->inter_arrival_time >> WEIGHT_OLD) + (delta >> WEIGHT_NEW);
1384    
1385     } else
1386     pro->inter_arrival_time = delta;
1387    
1388     rohc_debugf(2,"inter_arrival_time = %d and current arrival delta is = %d\n", pro->inter_arrival_time, delta);
1389     }