/* Copyright (C) 2005-2021 Free Software Foundation, Inc.
   Contributed by Richard Henderson <rth@redhat.com>.

   This file is part of the GNU Offloading and Multi Processing Library
   (libgomp).

   Libgomp is free software; you can redistribute it and/or modify it
   under the terms of the GNU General Public License as published by
   the Free Software Foundation; either version 3, or (at your option)
   any later version.

   Libgomp is distributed in the hope that it will be useful, but WITHOUT ANY
   WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
   FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
   more details.

   Under Section 7 of GPL version 3, you are granted additional
   permissions described in the GCC Runtime Library Exception, version
   3.1, as published by the Free Software Foundation.

   You should have received a copy of the GNU General Public License and
   a copy of the GCC Runtime Library Exception along with this program;
   see the files COPYING3 and COPYING.RUNTIME respectively.  If not, see
   <http://www.gnu.org/licenses/>.  */

/* This file defines the OpenMP internal control variables and arranges
   for them to be initialized from environment variables at startup.  */

#define _GNU_SOURCE
#include "libgomp.h"
#include "gomp-constants.h"
#include <limits.h>
#ifndef LIBGOMP_OFFLOADED_ONLY
#include "libgomp_f.h"
#include "oacc-int.h"
#include <ctype.h>
#include <stdlib.h>
#include <stdio.h>
#ifdef HAVE_INTTYPES_H
# include <inttypes.h>	/* For PRIu64.  */
#endif
#ifdef STRING_WITH_STRINGS
# include <string.h>
# include <strings.h>
#else
# ifdef HAVE_STRING_H
#  include <string.h>
# else
#  ifdef HAVE_STRINGS_H
#   include <strings.h>
#  endif
# endif
#endif
#include <errno.h>
#include "thread-stacksize.h"

#ifndef HAVE_STRTOULL
# define strtoull(ptr, eptr, base) strtoul (ptr, eptr, base)
#endif
#endif /* LIBGOMP_OFFLOADED_ONLY */

#include "secure_getenv.h"

struct gomp_task_icv gomp_global_icv = {
  .nthreads_var = 1,
  .thread_limit_var = UINT_MAX,
  .run_sched_var = GFS_DYNAMIC,
  .run_sched_chunk_size = 1,
  .default_device_var = 0,
  .dyn_var = false,
  .max_active_levels_var = 1,
  .bind_var = omp_proc_bind_false,
  .target_data = NULL
};

bool gomp_cancel_var = false;
enum gomp_target_offload_t gomp_target_offload_var
  = GOMP_TARGET_OFFLOAD_DEFAULT;
int gomp_max_task_priority_var = 0;
#ifndef HAVE_SYNC_BUILTINS
gomp_mutex_t gomp_managed_threads_lock;
#endif
unsigned long gomp_available_cpus = 1, gomp_managed_threads = 1;
unsigned long long gomp_spin_count_var, gomp_throttled_spin_count_var;
unsigned long *gomp_nthreads_var_list, gomp_nthreads_var_list_len;
char *gomp_bind_var_list;
unsigned long gomp_bind_var_list_len;
void **gomp_places_list;
unsigned long gomp_places_list_len;
uintptr_t gomp_def_allocator = omp_default_mem_alloc;
int gomp_debug_var;
unsigned int gomp_num_teams_var;
int gomp_nteams_var;
int gomp_teams_thread_limit_var;
bool gomp_display_affinity_var;
char *gomp_affinity_format_var = "level %L thread %i affinity %A";
size_t gomp_affinity_format_len;
char *goacc_device_type;
int goacc_device_num;
int goacc_default_dims[GOMP_DIM_MAX];

#ifndef LIBGOMP_OFFLOADED_ONLY

static int wait_policy;
static unsigned long stacksize = GOMP_DEFAULT_STACKSIZE;

/* Parse the OMP_SCHEDULE environment variable.  */

static void
parse_schedule (void)
{
  char *env, *end;
  unsigned long value;
  int monotonic = 0;

  env = getenv ("OMP_SCHEDULE");
  if (env == NULL)
    return;

  while (isspace ((unsigned char) *env))
    ++env;
  if (strncasecmp (env, "monotonic", 9) == 0)
    {
      monotonic = 1;
      env += 9;
    }
  else if (strncasecmp (env, "nonmonotonic", 12) == 0)
    {
      monotonic = -1;
      env += 12;
    }
  if (monotonic)
    {
      while (isspace ((unsigned char) *env))
	++env;
      if (*env != ':')
	goto unknown;
      ++env;
      while (isspace ((unsigned char) *env))
	++env;
    }
  if (strncasecmp (env, "static", 6) == 0)
    {
      gomp_global_icv.run_sched_var = GFS_STATIC;
      env += 6;
    }
  else if (strncasecmp (env, "dynamic", 7) == 0)
    {
      gomp_global_icv.run_sched_var = GFS_DYNAMIC;
      env += 7;
    }
  else if (strncasecmp (env, "guided", 6) == 0)
    {
      gomp_global_icv.run_sched_var = GFS_GUIDED;
      env += 6;
    }
  else if (strncasecmp (env, "auto", 4) == 0)
    {
      gomp_global_icv.run_sched_var = GFS_AUTO;
      env += 4;
    }
  else
    goto unknown;

  if (monotonic == 1
      || (monotonic == 0 && gomp_global_icv.run_sched_var == GFS_STATIC))
    gomp_global_icv.run_sched_var |= GFS_MONOTONIC;

  while (isspace ((unsigned char) *env))
    ++env;
  if (*env == '\0')
    {
      gomp_global_icv.run_sched_chunk_size
	= (gomp_global_icv.run_sched_var & ~GFS_MONOTONIC) != GFS_STATIC;
      return;
    }
  if (*env++ != ',')
    goto unknown;
  while (isspace ((unsigned char) *env))
    ++env;
  if (*env == '\0')
    goto invalid;

  errno = 0;
  value = strtoul (env, &end, 10);
  if (errno || end == env)
    goto invalid;

  while (isspace ((unsigned char) *end))
    ++end;
  if (*end != '\0')
    goto invalid;

  if ((int)value != value)
    goto invalid;

  if (value == 0
      && (gomp_global_icv.run_sched_var & ~GFS_MONOTONIC) != GFS_STATIC)
    value = 1;
  gomp_global_icv.run_sched_chunk_size = value;
  return;

 unknown:
  gomp_error ("Unknown value for environment variable OMP_SCHEDULE");
  return;

 invalid:
  gomp_error ("Invalid value for chunk size in "
	      "environment variable OMP_SCHEDULE");
  return;
}

/* Parse an unsigned long environment variable.  Return true if one was
   present and it was successfully parsed.  If SECURE, use secure_getenv to the
   environment variable.  */

static bool
parse_unsigned_long_1 (const char *name, unsigned long *pvalue, bool allow_zero,
		       bool secure)
{
  char *env, *end;
  unsigned long value;

  env = (secure ? secure_getenv (name) : getenv (name));
  if (env == NULL)
    return false;

  while (isspace ((unsigned char) *env))
    ++env;
  if (*env == '\0')
    goto invalid;

  errno = 0;
  value = strtoul (env, &end, 10);
  if (errno || end == env || (long) value <= 0 - allow_zero)
    goto invalid;

  while (isspace ((unsigned char) *end))
    ++end;
  if (*end != '\0')
    goto invalid;

  *pvalue = value;
  return true;

 invalid:
  gomp_error ("Invalid value for environment variable %s", name);
  return false;
}

/* As parse_unsigned_long_1, but always use getenv.  */

static bool
parse_unsigned_long (const char *name, unsigned long *pvalue, bool allow_zero)
{
  return parse_unsigned_long_1 (name, pvalue, allow_zero, false);
}

/* Parse a positive int environment variable.  Return true if one was
   present and it was successfully parsed.  If SECURE, use secure_getenv to the
   environment variable.  */

static bool
parse_int_1 (const char *name, int *pvalue, bool allow_zero, bool secure)
{
  unsigned long value;
  if (!parse_unsigned_long_1 (name, &value, allow_zero, secure))
    return false;
  if (value > INT_MAX)
    {
      gomp_error ("Invalid value for environment variable %s", name);
      return false;
    }
  *pvalue = (int) value;
  return true;
}

/* As parse_int_1, but use getenv.  */

static bool
parse_int (const char *name, int *pvalue, bool allow_zero)
{
  return parse_int_1 (name, pvalue, allow_zero, false);
}

/* As parse_int_1, but use getenv_secure.  */

static bool
parse_int_secure (const char *name, int *pvalue, bool allow_zero)
{
  return parse_int_1 (name, pvalue, allow_zero, true);
}

/* Parse an unsigned long list environment variable.  Return true if one was
   present and it was successfully parsed.  */

static bool
parse_unsigned_long_list (const char *name, unsigned long *p1stvalue,
			  unsigned long **pvalues,
			  unsigned long *pnvalues)
{
  char *env, *end;
  unsigned long value, *values = NULL;

  env = getenv (name);
  if (env == NULL)
    return false;

  while (isspace ((unsigned char) *env))
    ++env;
  if (*env == '\0')
    goto invalid;

  errno = 0;
  value = strtoul (env, &end, 10);
  if (errno || (long) value <= 0)
    goto invalid;

  while (isspace ((unsigned char) *end))
    ++end;
  if (*end != '\0')
    {
      if (*end == ',')
	{
	  unsigned long nvalues = 0, nalloced = 0;

	  do
	    {
	      env = end + 1;
	      if (nvalues == nalloced)
		{
		  unsigned long *n;
		  nalloced = nalloced ? nalloced * 2 : 16;
		  n = realloc (values, nalloced * sizeof (unsigned long));
		  if (n == NULL)
		    {
		      free (values);
		      gomp_error ("Out of memory while trying to parse"
				  " environment variable %s", name);
		      return false;
		    }
		  values = n;
		  if (nvalues == 0)
		    values[nvalues++] = value;
		}

	      while (isspace ((unsigned char) *env))
		++env;
	      if (*env == '\0')
		goto invalid;

	      errno = 0;
	      value = strtoul (env, &end, 10);
	      if (errno || (long) value <= 0)
		goto invalid;

	      values[nvalues++] = value;
	      while (isspace ((unsigned char) *end))
		++end;
	      if (*end == '\0')
		break;
	      if (*end != ',')
		goto invalid;
	    }
	  while (1);
	  *p1stvalue = values[0];
	  *pvalues = values;
	  *pnvalues = nvalues;
	  return true;
	}
      goto invalid;
    }

  *p1stvalue = value;
  return true;

 invalid:
  free (values);
  gomp_error ("Invalid value for environment variable %s", name);
  return false;
}

static void
parse_target_offload (const char *name, enum gomp_target_offload_t *offload)
{
  const char *env;
  int new_offload = -1;

  env = getenv (name);
  if (env == NULL)
    return;

  while (isspace ((unsigned char) *env))
    ++env;
  if (strncasecmp (env, "default", 7) == 0)
    {
      env += 7;
      new_offload = GOMP_TARGET_OFFLOAD_DEFAULT;
    }
  else if (strncasecmp (env, "mandatory", 9) == 0)
    {
      env += 9;
      new_offload = GOMP_TARGET_OFFLOAD_MANDATORY;
    }
  else if (strncasecmp (env, "disabled", 8) == 0)
    {
      env += 8;
      new_offload = GOMP_TARGET_OFFLOAD_DISABLED;
    }
  while (isspace ((unsigned char) *env))
    ++env;
  if (new_offload != -1 && *env == '\0')
    {
      *offload = new_offload;
      return;
    }

  gomp_error ("Invalid value for environment variable OMP_TARGET_OFFLOAD");
}

/* Parse environment variable set to a boolean or list of omp_proc_bind_t
   enum values.  Return true if one was present and it was successfully
   parsed.  */

static bool
parse_bind_var (const char *name, char *p1stvalue,
		char **pvalues, unsigned long *pnvalues)
{
  char *env;
  char value = omp_proc_bind_false, *values = NULL;
  int i;
  static struct proc_bind_kinds
  {
    const char name[7];
    const char len;
    omp_proc_bind_t kind;
  } kinds[] =
  {
    { "false", 5, omp_proc_bind_false },
    { "true", 4, omp_proc_bind_true },
    { "master", 6, omp_proc_bind_master },
    { "primary", 7, omp_proc_bind_primary },
    { "close", 5, omp_proc_bind_close },
    { "spread", 6, omp_proc_bind_spread }
  };

  env = getenv (name);
  if (env == NULL)
    return false;

  while (isspace ((unsigned char) *env))
    ++env;
  if (*env == '\0')
    goto invalid;

  for (i = 0; i < 6; i++)
    if (strncasecmp (env, kinds[i].name, kinds[i].len) == 0)
      {
	value = kinds[i].kind;
	env += kinds[i].len;
	break;
      }
  if (i == 6)
    goto invalid;

  while (isspace ((unsigned char) *env))
    ++env;
  if (*env != '\0')
    {
      if (*env == ',')
	{
	  unsigned long nvalues = 0, nalloced = 0;

	  if (value == omp_proc_bind_false
	      || value == omp_proc_bind_true)
	    goto invalid;

	  do
	    {
	      env++;
	      if (nvalues == nalloced)
		{
		  char *n;
		  nalloced = nalloced ? nalloced * 2 : 16;
		  n = realloc (values, nalloced);
		  if (n == NULL)
		    {
		      free (values);
		      gomp_error ("Out of memory while trying to parse"
				  " environment variable %s", name);
		      return false;
		    }
		  values = n;
		  if (nvalues == 0)
		    values[nvalues++] = value;
		}

	      while (isspace ((unsigned char) *env))
		++env;
	      if (*env == '\0')
		goto invalid;

	      for (i = 2; i < 6; i++)
		if (strncasecmp (env, kinds[i].name, kinds[i].len) == 0)
		  {
		    value = kinds[i].kind;
		    env += kinds[i].len;
		    break;
		  }
	      if (i == 6)
		goto invalid;

	      values[nvalues++] = value;
	      while (isspace ((unsigned char) *env))
		++env;
	      if (*env == '\0')
		break;
	      if (*env != ',')
		goto invalid;
	    }
	  while (1);
	  *p1stvalue = values[0];
	  *pvalues = values;
	  *pnvalues = nvalues;
	  return true;
	}
      goto invalid;
    }

  *p1stvalue = value;
  return true;

 invalid:
  free (values);
  gomp_error ("Invalid value for environment variable %s", name);
  return false;
}

static bool
parse_one_place (char **envp, bool *negatep, unsigned long *lenp,
		 long *stridep)
{
  char *env = *envp, *start;
  void *p = gomp_places_list ? gomp_places_list[gomp_places_list_len] : NULL;
  unsigned long len = 1;
  long stride = 1;
  int pass;
  bool any_negate = false;
  bool has_braces = true;
  *negatep = false;
  while (isspace ((unsigned char) *env))
    ++env;
  if (*env == '!')
    {
      *negatep = true;
      ++env;
      while (isspace ((unsigned char) *env))
	++env;
    }
  if (*env != '{')
    {
      char *end;
      unsigned long this_num;

      errno = 0;
      this_num = strtoul (env, &end, 10);
      if (errno || end == env)
	return false;
      env = end - 1;
      has_braces = false;
      if (gomp_places_list
	  && !gomp_affinity_add_cpus (p, this_num, 1, 1, false))
	return false;
    }
  else
    {
      ++env;
      while (isspace ((unsigned char) *env))
	++env;
    }
  start = env;
  for (pass = 0; pass < (any_negate ? 2 : has_braces); pass++)
    {
      env = start;
      do
	{
	  unsigned long this_num, this_len = 1;
	  long this_stride = 1;
	  bool this_negate = (*env == '!');
	  char *end;
	  if (this_negate)
	    {
	      if (gomp_places_list)
		any_negate = true;
	      ++env;
	      while (isspace ((unsigned char) *env))
		++env;
	    }

	  errno = 0;
	  this_num = strtoul (env, &end, 10);
	  if (errno || end == env)
	    return false;
	  env = end;
	  while (isspace ((unsigned char) *env))
	    ++env;
	  if (*env == ':')
	    {
	      ++env;
	      if (this_negate)
		return false;
	      while (isspace ((unsigned char) *env))
		++env;
	      errno = 0;
	      this_len = strtoul (env, &env, 10);
	      if (errno || this_len == 0)
		return false;
	      while (isspace ((unsigned char) *env))
		++env;
	      if (*env == ':')
		{
		  ++env;
		  while (isspace ((unsigned char) *env))
		    ++env;
		  errno = 0;
		  this_stride = strtol (env, &end, 10);
		  if (errno || end == env)
		    return false;
		  env = end;
		  while (isspace ((unsigned char) *env))
		    ++env;
		}
	    }
	  if (gomp_places_list && pass == this_negate)
	    {
	      if (this_negate)
		{
		  if (!gomp_affinity_remove_cpu (p, this_num))
		    return false;
		}
	      else if (!gomp_affinity_add_cpus (p, this_num, this_len,
						this_stride, false))
		return false;
	    }
	  if (*env == '}')
	    break;
	  if (*env != ',')
	    return false;
	  ++env;
	}
      while (1);
    }

  ++env;
  while (isspace ((unsigned char) *env))
    ++env;
  if (*env == ':')
    {
      char *end;
      if (*negatep)
	return false;
      ++env;
      while (isspace ((unsigned char) *env))
	++env;
      errno = 0;
      len = strtoul (env, &env, 10);
      if (errno || len == 0 || len >= 65536)
	return false;
      while (isspace ((unsigned char) *env))
	++env;
      if (*env == ':')
	{
	  ++env;
	  while (isspace ((unsigned char) *env))
	    ++env;
	  errno = 0;
	  stride = strtol (env, &end, 10);
	  if (errno || end == env)
	    return false;
	  env = end;
	  while (isspace ((unsigned char) *env))
	    ++env;
	}
    }
  *envp = env;
  *lenp = len;
  *stridep = stride;
  return true;
}

static bool
parse_places_var (const char *name, bool ignore)
{
  char *env = getenv (name), *end;
  bool any_negate = false;
  int level = 0;
  unsigned long count = 0;
  if (env == NULL)
    return false;

  while (isspace ((unsigned char) *env))
    ++env;
  if (*env == '\0')
    goto invalid;

  if (strncasecmp (env, "threads", 7) == 0)
    {
      env += 7;
      level = 1;
    }
  else if (strncasecmp (env, "cores", 5) == 0)
    {
      env += 5;
      level = 2;
    }
  else if (strncasecmp (env, "sockets", 7) == 0)
    {
      env += 7;
      level = 3;
    }
  else if (strncasecmp (env, "ll_caches", 9) == 0)
    {
      env += 9;
      level = 4;
    }
  else if (strncasecmp (env, "numa_domains", 12) == 0)
    {
      env += 12;
      level = 5;
    }
  if (level)
    {
      count = ULONG_MAX;
      while (isspace ((unsigned char) *env))
	++env;
      if (*env != '\0')
	{
	  if (*env++ != '(')
	    goto invalid;
	  while (isspace ((unsigned char) *env))
	    ++env;

	  errno = 0;
	  count = strtoul (env, &end, 10);
	  if (errno || end == env)
	    goto invalid;
	  env = end;
	  while (isspace ((unsigned char) *env))
	    ++env;
	  if (*env != ')')
	    goto invalid;
	  ++env;
	  while (isspace ((unsigned char) *env))
	    ++env;
	  if (*env != '\0')
	    goto invalid;
	}

      if (ignore)
	return false;

      return gomp_affinity_init_level (level, count, false);
    }

  count = 0;
  end = env;
  do
    {
      bool negate;
      unsigned long len;
      long stride;
      if (!parse_one_place (&end, &negate, &len, &stride))
	goto invalid;
      if (negate)
	{
	  if (!any_negate)
	    count++;
	  any_negate = true;
	}
      else
	count += len;
      if (count > 65536)
	goto invalid;
      if (*end == '\0')
	break;
      if (*end != ',')
	goto invalid;
      end++;
    }
  while (1);

  if (ignore)
    return false;

  gomp_places_list_len = 0;
  gomp_places_list = gomp_affinity_alloc (count, false);
  if (gomp_places_list == NULL)
    return false;

  do
    {
      bool negate;
      unsigned long len;
      long stride;
      gomp_affinity_init_place (gomp_places_list[gomp_places_list_len]);
      if (!parse_one_place (&env, &negate, &len, &stride))
	goto invalid;
      if (negate)
	{
	  void *p;
	  for (count = 0; count < gomp_places_list_len; count++)
	    if (gomp_affinity_same_place
			(gomp_places_list[count],
			 gomp_places_list[gomp_places_list_len]))
	      break;
	  if (count == gomp_places_list_len)
	    {
	      gomp_error ("Trying to remove a non-existing place from list "
			  "of places");
	      goto invalid;
	    }
	  p = gomp_places_list[count];
	  memmove (&gomp_places_list[count],
		   &gomp_places_list[count + 1],
		   (gomp_places_list_len - count - 1) * sizeof (void *));
	  --gomp_places_list_len;
	  gomp_places_list[gomp_places_list_len] = p;
	}
      else if (len == 1)
	++gomp_places_list_len;
      else
	{
	  for (count = 0; count < len - 1; count++)
	    if (!gomp_affinity_copy_place
			(gomp_places_list[gomp_places_list_len + count + 1],
			 gomp_places_list[gomp_places_list_len + count],
			 stride))
	      goto invalid;
	  gomp_places_list_len += len;
	}
      if (*env == '\0')
	break;
      env++;
    }
  while (1);

  if (gomp_places_list_len == 0)
    {
      gomp_error ("All places have been removed");
      goto invalid;
    }
  if (!gomp_affinity_finalize_place_list (false))
    goto invalid;
  return true;

 invalid:
  free (gomp_places_list);
  gomp_places_list = NULL;
  gomp_places_list_len = 0;
  gomp_error ("Invalid value for environment variable %s", name);
  return false;
}

/* Parse the OMP_STACKSIZE environment varible.  Return true if one was
   present and it was successfully parsed.  */

static bool
parse_stacksize (const char *name, unsigned long *pvalue)
{
  char *env, *end;
  unsigned long value, shift = 10;

  env = getenv (name);
  if (env == NULL)
    return false;

  while (isspace ((unsigned char) *env))
    ++env;
  if (*env == '\0')
    goto invalid;

  errno = 0;
  value = strtoul (env, &end, 10);
  if (errno || end == env)
    goto invalid;

  while (isspace ((unsigned char) *end))
    ++end;
  if (*end != '\0')
    {
      switch (tolower ((unsigned char) *end))
	{
	case 'b':
	  shift = 0;
	  break;
	case 'k':
	  break;
	case 'm':
	  shift = 20;
	  break;
	case 'g':
	  shift = 30;
	  break;
	default:
	  goto invalid;
	}
      ++end;
      while (isspace ((unsigned char) *end))
	++end;
      if (*end != '\0')
	goto invalid;
    }

  if (((value << shift) >> shift) != value)
    goto invalid;

  *pvalue = value << shift;
  return true;

 invalid:
  gomp_error ("Invalid value for environment variable %s", name);
  return false;
}

/* Parse the GOMP_SPINCOUNT environment varible.  Return true if one was
   present and it was successfully parsed.  */

static bool
parse_spincount (const char *name, unsigned long long *pvalue)
{
  char *env, *end;
  unsigned long long value, mult = 1;

  env = getenv (name);
  if (env == NULL)
    return false;

  while (isspace ((unsigned char) *env))
    ++env;
  if (*env == '\0')
    goto invalid;

  if (strncasecmp (env, "infinite", 8) == 0
      || strncasecmp (env, "infinity", 8) == 0)
    {
      value = ~0ULL;
      end = env + 8;
      goto check_tail;
    }

  errno = 0;
  value = strtoull (env, &end, 10);
  if (errno || end == env)
    goto invalid;

  while (isspace ((unsigned char) *end))
    ++end;
  if (*end != '\0')
    {
      switch (tolower ((unsigned char) *end))
	{
	case 'k':
	  mult = 1000LL;
	  break;
	case 'm':
	  mult = 1000LL * 1000LL;
	  break;
	case 'g':
	  mult = 1000LL * 1000LL * 1000LL;
	  break;
	case 't':
	  mult = 1000LL * 1000LL * 1000LL * 1000LL;
	  break;
	default:
	  goto invalid;
	}
      ++end;
     check_tail:
      while (isspace ((unsigned char) *end))
	++end;
      if (*end != '\0')
	goto invalid;
    }

  if (value > ~0ULL / mult)
    value = ~0ULL;
  else
    value *= mult;

  *pvalue = value;
  return true;

 invalid:
  gomp_error ("Invalid value for environment variable %s", name);
  return false;
}

/* Parse a boolean value for environment variable NAME and store the
   result in VALUE.  Return true if one was present and it was
   successfully parsed.  */

static bool
parse_boolean (const char *name, bool *value)
{
  const char *env;

  env = getenv (name);
  if (env == NULL)
    return false;

  while (isspace ((unsigned char) *env))
    ++env;
  if (strncasecmp (env, "true", 4) == 0)
    {
      *value = true;
      env += 4;
    }
  else if (strncasecmp (env, "false", 5) == 0)
    {
      *value = false;
      env += 5;
    }
  else
    env = "X";
  while (isspace ((unsigned char) *env))
    ++env;
  if (*env != '\0')
    {
      gomp_error ("Invalid value for environment variable %s", name);
      return false;
    }
  return true;
}

/* Parse the OMP_WAIT_POLICY environment variable and return the value.  */

static int
parse_wait_policy (void)
{
  const char *env;
  int ret = -1;

  env = getenv ("OMP_WAIT_POLICY");
  if (env == NULL)
    return -1;

  while (isspace ((unsigned char) *env))
    ++env;
  if (strncasecmp (env, "active", 6) == 0)
    {
      ret = 1;
      env += 6;
    }
  else if (strncasecmp (env, "passive", 7) == 0)
    {
      ret = 0;
      env += 7;
    }
  else
    env = "X";
  while (isspace ((unsigned char) *env))
    ++env;
  if (*env == '\0')
    return ret;
  gomp_error ("Invalid value for environment variable OMP_WAIT_POLICY");
  return -1;
}

/* Parse the GOMP_CPU_AFFINITY environment varible.  Return true if one was
   present and it was successfully parsed.  */

static bool
parse_affinity (bool ignore)
{
  char *env, *end, *start;
  int pass;
  unsigned long cpu_beg, cpu_end, cpu_stride;
  size_t count = 0, needed;

  env = getenv ("GOMP_CPU_AFFINITY");
  if (env == NULL)
    return false;

  start = env;
  for (pass = 0; pass < 2; pass++)
    {
      env = start;
      if (pass == 1)
	{
	  if (ignore)
	    return false;

	  gomp_places_list_len = 0;
	  gomp_places_list = gomp_affinity_alloc (count, true);
	  if (gomp_places_list == NULL)
	    return false;
	}
      do
	{
	  while (isspace ((unsigned char) *env))
	    ++env;

	  errno = 0;
	  cpu_beg = strtoul (env, &end, 0);
	  if (errno || end == env || cpu_beg >= 65536)
	    goto invalid;
	  cpu_end = cpu_beg;
	  cpu_stride = 1;

	  env = end;
	  if (*env == '-')
	    {
	      errno = 0;
	      cpu_end = strtoul (++env, &end, 0);
	      if (errno || end == env || cpu_end >= 65536 || cpu_end < cpu_beg)
		goto invalid;

	      env = end;
	      if (*env == ':')
		{
		  errno = 0;
		  cpu_stride = strtoul (++env, &end, 0);
		  if (errno || cpu_stride == 0 || cpu_stride >= 65536)
		    goto invalid;

		  env = end;
		}
	    }

	  needed = (cpu_end - cpu_beg) / cpu_stride + 1;
	  if (pass == 0)
	    count += needed;
	  else
	    {
	      while (needed--)
		{
		  void *p = gomp_places_list[gomp_places_list_len];
		  gomp_affinity_init_place (p);
		  if (gomp_affinity_add_cpus (p, cpu_beg, 1, 0, true))
		    ++gomp_places_list_len;
		  cpu_beg += cpu_stride;
		}
	    }

	  while (isspace ((unsigned char) *env))
	    ++env;

	  if (*env == ',')
	    env++;
	  else if (*env == '\0')
	    break;
	}
      while (1);
    }

  if (gomp_places_list_len == 0)
    {
      free (gomp_places_list);
      gomp_places_list = NULL;
      return false;
    }
  return true;

 invalid:
  gomp_error ("Invalid value for enviroment variable GOMP_CPU_AFFINITY");
  return false;
}

/* Parse the OMP_ALLOCATOR environment variable and return the value.  */

static uintptr_t
parse_allocator (void)
{
  const char *env;
  uintptr_t ret = omp_default_mem_alloc;

  env = getenv ("OMP_ALLOCATOR");
  if (env == NULL)
    return ret;

  while (isspace ((unsigned char) *env))
    ++env;
  if (0)
    ;
#define C(v) \
  else if (strncasecmp (env, #v, sizeof (#v) - 1) == 0)	\
    {							\
      ret = v;						\
      env += sizeof (#v) - 1;				\
    }
  C (omp_default_mem_alloc)
  C (omp_large_cap_mem_alloc)
  C (omp_const_mem_alloc)
  C (omp_high_bw_mem_alloc)
  C (omp_low_lat_mem_alloc)
  C (omp_cgroup_mem_alloc)
  C (omp_pteam_mem_alloc)
  C (omp_thread_mem_alloc)
#undef C
  else
    env = "X";
  while (isspace ((unsigned char) *env))
    ++env;
  if (*env == '\0')
    return ret;
  gomp_error ("Invalid value for environment variable OMP_ALLOCATOR");
  return omp_default_mem_alloc;
}

static void
parse_acc_device_type (void)
{
  const char *env = getenv ("ACC_DEVICE_TYPE");

  if (env && *env != '\0')
    goacc_device_type = strdup (env);
  else
    goacc_device_type = NULL;
}

static void
parse_gomp_openacc_dim (void)
{
  /* The syntax is the same as for the -fopenacc-dim compilation option.  */
  const char *var_name = "GOMP_OPENACC_DIM";
  const char *env_var = getenv (var_name);
  const char *pos = env_var;
  int i;

  if (!env_var)
    return;

  for (i = 0; *pos && i != GOMP_DIM_MAX; i++)
    {
      char *eptr;
      long val;

      if (i && *pos++ != ':')
	break;

      if (*pos == ':')
	continue;

      errno = 0;
      val = strtol (pos, &eptr, 10);
      if (errno || eptr != pos || val < 0 || (unsigned)val != val)
	break;

      goacc_default_dims[i] = (int)val;
      pos = (const char *) eptr;
    }
}

void
omp_display_env (int verbose)
{
  int i;

  fputs ("\nOPENMP DISPLAY ENVIRONMENT BEGIN\n", stderr);

  fputs ("  _OPENMP = '201511'\n", stderr);
  fprintf (stderr, "  OMP_DYNAMIC = '%s'\n",
	   gomp_global_icv.dyn_var ? "TRUE" : "FALSE");
  fprintf (stderr, "  OMP_NESTED = '%s'\n",
	   gomp_global_icv.max_active_levels_var > 1 ? "TRUE" : "FALSE");

  fprintf (stderr, "  OMP_NUM_THREADS = '%lu", gomp_global_icv.nthreads_var);
  for (i = 1; i < gomp_nthreads_var_list_len; i++)
    fprintf (stderr, ",%lu", gomp_nthreads_var_list[i]);
  fputs ("'\n", stderr);

  fprintf (stderr, "  OMP_SCHEDULE = '");
  if ((gomp_global_icv.run_sched_var & GFS_MONOTONIC))
    {
      if (gomp_global_icv.run_sched_var != (GFS_MONOTONIC | GFS_STATIC))
	fputs ("MONOTONIC:", stderr);
    }
  else if (gomp_global_icv.run_sched_var == GFS_STATIC)
    fputs ("NONMONOTONIC:", stderr);
  switch (gomp_global_icv.run_sched_var & ~GFS_MONOTONIC)
    {
    case GFS_RUNTIME:
      fputs ("RUNTIME", stderr);
      if (gomp_global_icv.run_sched_chunk_size != 1)
	fprintf (stderr, ",%d", gomp_global_icv.run_sched_chunk_size);
      break;
    case GFS_STATIC:
      fputs ("STATIC", stderr);
      if (gomp_global_icv.run_sched_chunk_size != 0)
	fprintf (stderr, ",%d", gomp_global_icv.run_sched_chunk_size);
      break;
    case GFS_DYNAMIC:
      fputs ("DYNAMIC", stderr);
      if (gomp_global_icv.run_sched_chunk_size != 1)
	fprintf (stderr, ",%d", gomp_global_icv.run_sched_chunk_size);
      break;
    case GFS_GUIDED:
      fputs ("GUIDED", stderr);
      if (gomp_global_icv.run_sched_chunk_size != 1)
	fprintf (stderr, ",%d", gomp_global_icv.run_sched_chunk_size);
      break;
    case GFS_AUTO:
      fputs ("AUTO", stderr);
      break;
    }
  fputs ("'\n", stderr);

  fputs ("  OMP_PROC_BIND = '", stderr);
  switch (gomp_global_icv.bind_var)
    {
    case omp_proc_bind_false:
      fputs ("FALSE", stderr);
      break;
    case omp_proc_bind_true:
      fputs ("TRUE", stderr);
      break;
    case omp_proc_bind_master:
      fputs ("MASTER", stderr); /* TODO: Change to PRIMARY for OpenMP 5.1.  */
      break;
    case omp_proc_bind_close:
      fputs ("CLOSE", stderr);
      break;
    case omp_proc_bind_spread:
      fputs ("SPREAD", stderr);
      break;
    }
  for (i = 1; i < gomp_bind_var_list_len; i++)
    switch (gomp_bind_var_list[i])
      {
      case omp_proc_bind_master:
	fputs (",MASTER", stderr); /* TODO: Change to PRIMARY for OpenMP 5.1. */
	break;
      case omp_proc_bind_close:
	fputs (",CLOSE", stderr);
	break;
      case omp_proc_bind_spread:
	fputs (",SPREAD", stderr);
	break;
      }
  fputs ("'\n", stderr);
  fputs ("  OMP_PLACES = '", stderr);
  for (i = 0; i < gomp_places_list_len; i++)
    {
      fputs ("{", stderr);
      gomp_affinity_print_place (gomp_places_list[i]);
      fputs (i + 1 == gomp_places_list_len ? "}" : "},", stderr);
    }
  fputs ("'\n", stderr);

  fprintf (stderr, "  OMP_STACKSIZE = '%lu'\n", stacksize);

  /* GOMP's default value is actually neither active nor passive.  */
  fprintf (stderr, "  OMP_WAIT_POLICY = '%s'\n",
	   wait_policy > 0 ? "ACTIVE" : "PASSIVE");
  fprintf (stderr, "  OMP_THREAD_LIMIT = '%u'\n",
	   gomp_global_icv.thread_limit_var);
  fprintf (stderr, "  OMP_MAX_ACTIVE_LEVELS = '%u'\n",
	   gomp_global_icv.max_active_levels_var);
  fprintf (stderr, "  OMP_NUM_TEAMS = '%u'\n", gomp_nteams_var);
  fprintf (stderr, "  OMP_TEAMS_THREAD_LIMIT = '%u'\n",
	   gomp_teams_thread_limit_var);

  fprintf (stderr, "  OMP_CANCELLATION = '%s'\n",
	   gomp_cancel_var ? "TRUE" : "FALSE");
  fprintf (stderr, "  OMP_DEFAULT_DEVICE = '%d'\n",
	   gomp_global_icv.default_device_var);
  fprintf (stderr, "  OMP_MAX_TASK_PRIORITY = '%d'\n",
	   gomp_max_task_priority_var);
  fprintf (stderr, "  OMP_DISPLAY_AFFINITY = '%s'\n",
	   gomp_display_affinity_var ? "TRUE" : "FALSE");
  fprintf (stderr, "  OMP_AFFINITY_FORMAT = '%s'\n",
	   gomp_affinity_format_var);
  fprintf (stderr, "  OMP_ALLOCATOR = '");
  switch (gomp_def_allocator)
    {
#define C(v) case v: fputs (#v, stderr); break;
    C (omp_default_mem_alloc)
    C (omp_large_cap_mem_alloc)
    C (omp_const_mem_alloc)
    C (omp_high_bw_mem_alloc)
    C (omp_low_lat_mem_alloc)
    C (omp_cgroup_mem_alloc)
    C (omp_pteam_mem_alloc)
    C (omp_thread_mem_alloc)
#undef C
    default: break;
    }
  fputs ("'\n", stderr);

  fputs ("  OMP_TARGET_OFFLOAD = '", stderr);
  switch (gomp_target_offload_var)
    {
    case GOMP_TARGET_OFFLOAD_DEFAULT:
      fputs ("DEFAULT", stderr);
      break;
    case GOMP_TARGET_OFFLOAD_MANDATORY:
      fputs ("MANDATORY", stderr);
      break;
    case GOMP_TARGET_OFFLOAD_DISABLED:
      fputs ("DISABLED", stderr);
      break;
    }
  fputs ("'\n", stderr);

  if (verbose)
    {
      fputs ("  GOMP_CPU_AFFINITY = ''\n", stderr);
      fprintf (stderr, "  GOMP_STACKSIZE = '%lu'\n", stacksize);
#ifdef HAVE_INTTYPES_H
      fprintf (stderr, "  GOMP_SPINCOUNT = '%"PRIu64"'\n",
	       (uint64_t) gomp_spin_count_var);
#else
      fprintf (stderr, "  GOMP_SPINCOUNT = '%lu'\n",
	       (unsigned long) gomp_spin_count_var);
#endif
    }

  fputs ("OPENMP DISPLAY ENVIRONMENT END\n", stderr);
}
ialias (omp_display_env)

static void
handle_omp_display_env (void)
{
  const char *env;
  bool display = false;
  bool verbose = false;

  env = getenv ("OMP_DISPLAY_ENV");
  if (env == NULL)
    return;

  while (isspace ((unsigned char) *env))
    ++env;
  if (strncasecmp (env, "true", 4) == 0)
    {
      display = true;
      env += 4;
    }
  else if (strncasecmp (env, "false", 5) == 0)
    {
      display = false;
      env += 5;
    }
  else if (strncasecmp (env, "verbose", 7) == 0)
    {
      display = true;
      verbose = true;
      env += 7;
    }
  else
    env = "X";
  while (isspace ((unsigned char) *env))
    ++env;
  if (*env != '\0')
    gomp_error ("Invalid value for environment variable OMP_DISPLAY_ENV");

  if (display)
    ialias_call (omp_display_env) (verbose);
}


static void __attribute__((constructor))
initialize_env (void)
{
  unsigned long thread_limit_var;
  unsigned long max_active_levels_var;

  /* Do a compile time check that mkomp_h.pl did good job.  */
  omp_check_defines ();

  parse_schedule ();
  parse_boolean ("OMP_DYNAMIC", &gomp_global_icv.dyn_var);
  parse_boolean ("OMP_CANCELLATION", &gomp_cancel_var);
  parse_boolean ("OMP_DISPLAY_AFFINITY", &gomp_display_affinity_var);
  parse_int ("OMP_DEFAULT_DEVICE", &gomp_global_icv.default_device_var, true);
  parse_target_offload ("OMP_TARGET_OFFLOAD", &gomp_target_offload_var);
  parse_int ("OMP_MAX_TASK_PRIORITY", &gomp_max_task_priority_var, true);
  gomp_def_allocator = parse_allocator ();
  if (parse_unsigned_long ("OMP_THREAD_LIMIT", &thread_limit_var, false))
    {
      gomp_global_icv.thread_limit_var
	= thread_limit_var > INT_MAX ? UINT_MAX : thread_limit_var;
    }
  parse_int_secure ("GOMP_DEBUG", &gomp_debug_var, true);
#ifndef HAVE_SYNC_BUILTINS
  gomp_mutex_init (&gomp_managed_threads_lock);
#endif
  gomp_init_num_threads ();
  gomp_available_cpus = gomp_global_icv.nthreads_var;
  if (!parse_unsigned_long_list ("OMP_NUM_THREADS",
				 &gomp_global_icv.nthreads_var,
				 &gomp_nthreads_var_list,
				 &gomp_nthreads_var_list_len))
    gomp_global_icv.nthreads_var = gomp_available_cpus;
  parse_int ("OMP_NUM_TEAMS", &gomp_nteams_var, false);
  parse_int ("OMP_TEAMS_THREAD_LIMIT", &gomp_teams_thread_limit_var, false);
  bool ignore = false;
  if (parse_bind_var ("OMP_PROC_BIND",
		      &gomp_global_icv.bind_var,
		      &gomp_bind_var_list,
		      &gomp_bind_var_list_len)
      && gomp_global_icv.bind_var == omp_proc_bind_false)
    ignore = true;
  if (parse_unsigned_long ("OMP_MAX_ACTIVE_LEVELS",
			   &max_active_levels_var, true))
    gomp_global_icv.max_active_levels_var
      = (max_active_levels_var > gomp_supported_active_levels)
	? gomp_supported_active_levels : max_active_levels_var;
  else
    {
      bool nested = true;

      /* OMP_NESTED is deprecated in OpenMP 5.0.  */
      if (parse_boolean ("OMP_NESTED", &nested))
	gomp_global_icv.max_active_levels_var
	  = nested ? gomp_supported_active_levels : 1;
      else if (gomp_nthreads_var_list_len > 1 || gomp_bind_var_list_len > 1)
	gomp_global_icv.max_active_levels_var = gomp_supported_active_levels;
    }
  /* Make sure OMP_PLACES and GOMP_CPU_AFFINITY env vars are always
     parsed if present in the environment.  If OMP_PROC_BIND was set
     explicitly to false, don't populate places list though.  If places
     list was successfully set from OMP_PLACES, only parse but don't process
     GOMP_CPU_AFFINITY.  If OMP_PROC_BIND was not set in the environment,
     default to OMP_PROC_BIND=true if OMP_PLACES or GOMP_CPU_AFFINITY
     was successfully parsed into a places list, otherwise to
     OMP_PROC_BIND=false.  */
  if (parse_places_var ("OMP_PLACES", ignore))
    {
      if (gomp_global_icv.bind_var == omp_proc_bind_false)
	gomp_global_icv.bind_var = true;
      ignore = true;
    }
  if (parse_affinity (ignore))
    {
      if (gomp_global_icv.bind_var == omp_proc_bind_false)
	gomp_global_icv.bind_var = true;
      ignore = true;
    }
  if (gomp_global_icv.bind_var != omp_proc_bind_false)
    gomp_init_affinity ();

  {
    const char *env = getenv ("OMP_AFFINITY_FORMAT");
    if (env != NULL)
      gomp_set_affinity_format (env, strlen (env));
  }

  wait_policy = parse_wait_policy ();
  if (!parse_spincount ("GOMP_SPINCOUNT", &gomp_spin_count_var))
    {
      /* Using a rough estimation of 100000 spins per msec,
	 use 5 min blocking for OMP_WAIT_POLICY=active,
	 3 msec blocking when OMP_WAIT_POLICY is not specificed
	 and 0 when OMP_WAIT_POLICY=passive.
	 Depending on the CPU speed, this can be e.g. 5 times longer
	 or 5 times shorter.  */
      if (wait_policy > 0)
	gomp_spin_count_var = 30000000000LL;
      else if (wait_policy < 0)
	gomp_spin_count_var = 300000LL;
    }
  /* gomp_throttled_spin_count_var is used when there are more libgomp
     managed threads than available CPUs.  Use very short spinning.  */
  if (wait_policy > 0)
    gomp_throttled_spin_count_var = 1000LL;
  else if (wait_policy < 0)
    gomp_throttled_spin_count_var = 100LL;
  if (gomp_throttled_spin_count_var > gomp_spin_count_var)
    gomp_throttled_spin_count_var = gomp_spin_count_var;

  /* Not strictly environment related, but ordering constructors is tricky.  */
  pthread_attr_init (&gomp_thread_attr);

  if (parse_stacksize ("OMP_STACKSIZE", &stacksize)
      || parse_stacksize ("GOMP_STACKSIZE", &stacksize)
      || GOMP_DEFAULT_STACKSIZE)
    {
      int err;

      err = pthread_attr_setstacksize (&gomp_thread_attr, stacksize);

#ifdef PTHREAD_STACK_MIN
      if (err == EINVAL)
	{
	  if (stacksize < PTHREAD_STACK_MIN)
	    gomp_error ("Stack size less than minimum of %luk",
			PTHREAD_STACK_MIN / 1024ul
			+ (PTHREAD_STACK_MIN % 1024 != 0));
	  else
	    gomp_error ("Stack size larger than system limit");
	}
      else
#endif
      if (err != 0)
	gomp_error ("Stack size change failed: %s", strerror (err));
    }

  handle_omp_display_env ();

  /* OpenACC.  */

  if (!parse_int ("ACC_DEVICE_NUM", &goacc_device_num, true))
    goacc_device_num = 0;

  parse_acc_device_type ();
  parse_gomp_openacc_dim ();

  goacc_runtime_initialize ();

  goacc_profiling_initialize ();
}
#endif /* LIBGOMP_OFFLOADED_ONLY */
