- Add Bugzilla PRs to ChangeLog reverting AIX long double size.
[official-gcc.git] / libgo / runtime / go-append.c
blob91493b1b78d7ecb4082e1f0f99b0ec723eaa43c9
1 /* go-append.c -- the go builtin append function.
3 Copyright 2010 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. */
7 #include "go-type.h"
8 #include "go-panic.h"
9 #include "array.h"
10 #include "runtime.h"
11 #include "malloc.h"
13 /* We should be OK if we don't split the stack here, since the only
14 libc functions we call are memcpy and memmove. If we don't do
15 this, we will always split the stack, because of memcpy and
16 memmove. */
17 extern struct __go_open_array
18 __go_append (struct __go_open_array, void *, size_t, size_t)
19 __attribute__ ((no_split_stack));
21 struct __go_open_array
22 __go_append (struct __go_open_array a, void *bvalues, size_t bcount,
23 size_t element_size)
25 size_t ucount;
26 int count;
28 if (bvalues == NULL || bcount == 0)
29 return a;
31 ucount = (size_t) a.__count + bcount;
32 count = (int) ucount;
33 if ((size_t) count != ucount || count <= a.__count)
34 __go_panic_msg ("append: slice overflow");
36 if (count > a.__capacity)
38 int m;
39 void *n;
41 m = a.__capacity;
42 if (m == 0)
43 m = (int) bcount;
44 else
48 if (a.__count < 1024)
49 m += m;
50 else
51 m += m / 4;
53 while (m < count);
56 n = __go_alloc (m * element_size);
57 __builtin_memcpy (n, a.__values, a.__count * element_size);
59 a.__values = n;
60 a.__capacity = m;
63 __builtin_memmove ((char *) a.__values + a.__count * element_size,
64 bvalues, bcount * element_size);
65 a.__count = count;
66 return a;