ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/gvpe/src/rohc/d_ip.c
Revision: 1.3
Committed: Tue Apr 26 00:55:56 2005 UTC (19 years, 1 month ago) by pcg
Content type: text/plain
Branch: MAIN
CVS Tags: rel-2_01, rel-3_0, rel-2_2, rel-2_0, rel-2_21, rel-2_22, rel-2_25, HEAD
Changes since 1.2: +1 -1 lines
Log Message:
*** empty log message ***

File Contents

# Content
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., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 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 sn = ntohs(* ((u16 *)s));
297 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 sn = ntohs(* ((u16 *)src2));
766 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 *id = ntohs(*((u16 *)src));
824 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 *id2 = ntohs(*((u16 *)src));
838
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 *id = ntohs(*((u16 *)src2));
960 src2 +=2; field_counter +=2; *payload_size -= 2;
961 }
962
963 // Multiple ip-header
964
965 if (( pro->multiple_ip )&&( active2->rnd )){
966 *id2 = ntohs(*((u16 *)src2));
967 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 active2->ip.id = *((u16 *)fields);
1084 fields += 2;
1085 *update_id2 = 1;
1086 }else{
1087 active1->ip.id = *((u16 *)fields);
1088 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 ip->id = *((u16 *)fields);
1218 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 }