OSDN Git Service

compiler, runtime: Reject surrogate pair converting int to string.
[pf3gnuchains/gcc-fork.git] / libgo / runtime / go-int-to-string.c
1 /* go-int-to-string.c -- convert an integer to a string in Go.
2
3    Copyright 2009 The Go Authors. All rights reserved.
4    Use of this source code is governed by a BSD-style
5    license that can be found in the LICENSE file.  */
6
7 #include "go-string.h"
8 #include "runtime.h"
9 #include "arch.h"
10 #include "malloc.h"
11
12 struct __go_string
13 __go_int_to_string (int v)
14 {
15   char buf[4];
16   int len;
17   unsigned char *retdata;
18   struct __go_string ret;
19
20   /* A negative value is not valid UTF-8; turn it into the replacement
21      character.  */
22   if (v < 0)
23     v = 0xfffd;
24
25   if (v <= 0x7f)
26     {
27       buf[0] = v;
28       len = 1;
29     }
30   else if (v <= 0x7ff)
31     {
32       buf[0] = 0xc0 + (v >> 6);
33       buf[1] = 0x80 + (v & 0x3f);
34       len = 2;
35     }
36   else
37     {
38       /* If the value is out of range for UTF-8, turn it into the
39          "replacement character".  */
40       if (v > 0x10ffff)
41         v = 0xfffd;
42       /* If the value is a surrogate pair, which is invalid in UTF-8,
43          turn it into the replacement character.  */
44       if (v >= 0xd800 && v < 0xe000)
45         v = 0xfffd;
46
47       if (v <= 0xffff)
48         {
49           buf[0] = 0xe0 + (v >> 12);
50           buf[1] = 0x80 + ((v >> 6) & 0x3f);
51           buf[2] = 0x80 + (v & 0x3f);
52           len = 3;
53         }
54       else
55         {
56           buf[0] = 0xf0 + (v >> 18);
57           buf[1] = 0x80 + ((v >> 12) & 0x3f);
58           buf[2] = 0x80 + ((v >> 6) & 0x3f);
59           buf[3] = 0x80 + (v & 0x3f);
60           len = 4;
61         }
62     }
63
64   retdata = runtime_mallocgc (len, FlagNoPointers, 1, 0);
65   __builtin_memcpy (retdata, buf, len);
66   ret.__data = retdata;
67   ret.__length = len;
68
69   return ret;
70 }