ViewVC Help
View File | Revision Log | Show Annotations | Download File
/cvs/CBOR-XS/XS.xs
(Generate patch)

Comparing CBOR-XS/XS.xs (file contents):
Revision 1.1 by root, Fri Oct 25 23:09:45 2013 UTC vs.
Revision 1.4 by root, Sat Oct 26 21:06:37 2013 UTC

8#include <stdio.h> 8#include <stdio.h>
9#include <limits.h> 9#include <limits.h>
10#include <float.h> 10#include <float.h>
11 11
12#include "ecb.h" 12#include "ecb.h"
13
14#if defined(__BORLANDC__) || defined(_MSC_VER)
15# define snprintf _snprintf // C compilers have this in stdio.h
16#endif
17 13
18#define F_SHRINK 0x00000200UL 14#define F_SHRINK 0x00000200UL
19#define F_ALLOW_UNKNOWN 0x00002000UL 15#define F_ALLOW_UNKNOWN 0x00002000UL
20 16
21#define INIT_SIZE 32 // initial scalar size to be allocated 17#define INIT_SIZE 32 // initial scalar size to be allocated
138{ 134{
139 need (enc, 9); 135 need (enc, 9);
140 136
141 if (len < 24) 137 if (len < 24)
142 *enc->cur++ = major | len; 138 *enc->cur++ = major | len;
143 else if (len < 0x100) 139 else if (len <= 0xff)
144 { 140 {
145 *enc->cur++ = major | 24; 141 *enc->cur++ = major | 24;
146 *enc->cur++ = len; 142 *enc->cur++ = len;
147 } 143 }
148 else if (len < 0x10000) 144 else if (len <= 0xffff)
149 { 145 {
150 *enc->cur++ = major | 25; 146 *enc->cur++ = major | 25;
151 *enc->cur++ = len >> 8; 147 *enc->cur++ = len >> 8;
152 *enc->cur++ = len; 148 *enc->cur++ = len;
153 } 149 }
154 else if (len < 0x100000000) 150 else if (len <= 0xffffffff)
155 { 151 {
156 *enc->cur++ = major | 26; 152 *enc->cur++ = major | 26;
157 *enc->cur++ = len >> 24; 153 *enc->cur++ = len >> 24;
158 *enc->cur++ = len >> 16; 154 *enc->cur++ = len >> 16;
159 *enc->cur++ = len >> 8; 155 *enc->cur++ = len >> 8;
160 *enc->cur++ = len; 156 *enc->cur++ = len;
161 } 157 }
162 else if (len) 158 else
163 { 159 {
164 *enc->cur++ = major | 27; 160 *enc->cur++ = major | 27;
165 *enc->cur++ = len >> 56; 161 *enc->cur++ = len >> 56;
166 *enc->cur++ = len >> 48; 162 *enc->cur++ = len >> 48;
167 *enc->cur++ = len >> 40; 163 *enc->cur++ = len >> 40;
504 500
505 for (;;) 501 for (;;)
506 { 502 {
507 WANT (1); 503 WANT (1);
508 504
509 if (*dec->cur == 0xe0 | 31) 505 if (*dec->cur == (0xe0 | 31))
510 { 506 {
511 ++dec->cur; 507 ++dec->cur;
512 break; 508 break;
513 } 509 }
514 510
547 543
548 for (;;) 544 for (;;)
549 { 545 {
550 WANT (1); 546 WANT (1);
551 547
552 if (*dec->cur == 0xe0 | 31) 548 if (*dec->cur == (0xe0 | 31))
553 { 549 {
554 ++dec->cur; 550 ++dec->cur;
555 break; 551 break;
556 } 552 }
557 553
752 // not very fast, and certainly not robust against illegal input 748 // not very fast, and certainly not robust against illegal input
753 for (;;) 749 for (;;)
754 { 750 {
755 WANT (1); 751 WANT (1);
756 752
757 if (*dec->cur == 0xe0 | 31) 753 if (*dec->cur == (0xe0 | 31))
758 { 754 {
759 ++dec->cur; 755 ++dec->cur;
760 break; 756 break;
761 } 757 }
762 758
778 774
779 return sv; 775 return sv;
780 776
781fail: 777fail:
782 return &PL_sv_undef; 778 return &PL_sv_undef;
779}
780
781static SV *
782decode_tagged (dec_t *dec)
783{
784 UV tag = decode_uint (dec);
785 SV *sv = decode_sv (dec);
786
787 if (tag == 55799) // 2.4.5 Self-Describe CBOR
788 return sv;
789
790 AV *av = newAV ();
791 av_push (av, newSVuv (tag));
792 av_push (av, sv);
793 return newRV_noinc ((SV *)av);
783} 794}
784 795
785static SV * 796static SV *
786decode_sv (dec_t *dec) 797decode_sv (dec_t *dec)
787{ 798{
801 case 4: // array 812 case 4: // array
802 return decode_av (dec); 813 return decode_av (dec);
803 case 5: // map 814 case 5: // map
804 return decode_hv (dec); 815 return decode_hv (dec);
805 case 6: // tag 816 case 6: // tag
806 abort (); 817 return decode_tagged (dec);
807 break;
808 case 7: // misc 818 case 7: // misc
809 switch (*dec->cur++ & 31) 819 switch (*dec->cur++ & 31)
810 { 820 {
811 case 20: 821 case 20:
812#if CBOR_SLOW 822#if CBOR_SLOW
820 return newSVsv (cbor_true); 830 return newSVsv (cbor_true);
821 case 22: 831 case 22:
822 return newSVsv (&PL_sv_undef); 832 return newSVsv (&PL_sv_undef);
823 833
824 case 25: 834 case 25:
825 // half float
826 abort ();
827 break; 835 {
836 WANT (2);
837
838 uint16_t fp = (dec->cur[0] << 8) | dec->cur[1];
839 dec->cur += 2;
840
841 return newSVnv (ecb_binary16_to_float (fp));
842 }
828 843
829 case 26: 844 case 26:
830 { 845 {
831 uint32_t fp; 846 uint32_t fp;
832 WANT (4); 847 WANT (4);
975 990
976 if (offset_return) 991 if (offset_return)
977 *offset_return = dec.cur; 992 *offset_return = dec.cur;
978 993
979 if (!(offset_return || !sv)) 994 if (!(offset_return || !sv))
980 {
981 if (*dec.cur && !dec.err) 995 if (dec.cur != dec.end && !dec.err)
982 {
983 dec.err = "garbage after CBOR object"; 996 dec.err = "garbage after CBOR object";
997
998 if (dec.err)
999 {
984 SvREFCNT_dec (sv); 1000 SvREFCNT_dec (sv);
985 sv = 0;
986 }
987 }
988
989 if (!sv)
990 croak ("%s, at offset %d (octet 0x%02x)", dec.err, dec.cur - (U8 *)SvPVX (string), (int)(uint8_t)*dec.cur); 1001 croak ("%s, at offset %d (octet 0x%02x)", dec.err, dec.cur - (U8 *)SvPVX (string), (int)(uint8_t)*dec.cur);
1002 }
991 1003
992 sv = sv_2mortal (sv); 1004 sv = sv_2mortal (sv);
993 1005
994 return sv; 1006 return sv;
995} 1007}

Diff Legend

Removed lines
+ Added lines
< Changed lines
> Changed lines