github.com/llvm-mirror/llgo@v0.0.0-20190322182713-bf6f0a60fce1/third_party/gofrontend/libgo/runtime/go-setenv.c (about)

     1  /* go-setenv.c -- set the C environment from Go.
     2  
     3     Copyright 2011 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 "config.h"
     8  
     9  #include <stddef.h>
    10  #include <stdlib.h>
    11  
    12  #include "go-alloc.h"
    13  #include "runtime.h"
    14  #include "arch.h"
    15  #include "malloc.h"
    16  
    17  /* Set the C environment from Go.  This is called by syscall.Setenv.  */
    18  
    19  void setenv_c (String, String) __asm__ (GOSYM_PREFIX "syscall.setenv_c");
    20  
    21  void
    22  setenv_c (String k, String v)
    23  {
    24    const byte *ks;
    25    unsigned char *kn;
    26    const byte *vs;
    27    unsigned char *vn;
    28    intgo len;
    29  
    30    ks = k.str;
    31    if (ks == NULL)
    32      ks = (const byte *) "";
    33    kn = NULL;
    34  
    35    vs = v.str;
    36    if (vs == NULL)
    37      vs = (const byte *) "";
    38    vn = NULL;
    39  
    40  #ifdef HAVE_SETENV
    41  
    42    if (ks != NULL && ks[k.len] != 0)
    43      {
    44        // Objects that are explicitly freed must be at least 16 bytes in size,
    45        // so that they are not allocated using tiny alloc.
    46        len = k.len + 1;
    47        if (len < TinySize)
    48  	len = TinySize;
    49        kn = __go_alloc (len);
    50        __builtin_memcpy (kn, ks, k.len);
    51        ks = kn;
    52      }
    53  
    54    if (vs != NULL && vs[v.len] != 0)
    55      {
    56        len = v.len + 1;
    57        if (len < TinySize)
    58  	len = TinySize;
    59        vn = __go_alloc (len);
    60        __builtin_memcpy (vn, vs, v.len);
    61        vs = vn;
    62      }
    63  
    64    setenv ((const char *) ks, (const char *) vs, 1);
    65  
    66  #else /* !defined(HAVE_SETENV) */
    67  
    68    len = k.len + v.len + 2;
    69    if (len < TinySize)
    70      len = TinySize;
    71    kn = __go_alloc (len);
    72    __builtin_memcpy (kn, ks, k.len);
    73    kn[k.len] = '=';
    74    __builtin_memcpy (kn + k.len + 1, vs, v.len);
    75    kn[k.len + v.len + 1] = '\0';
    76    putenv ((char *) kn);
    77  
    78  #endif /* !defined(HAVE_SETENV) */
    79  
    80    if (kn != NULL)
    81      __go_free (kn);
    82    if (vn != NULL)
    83      __go_free (vn);
    84  }