コード例 #1
0
ファイル: csql_result_format.c プロジェクト: CUBRID/cubrid
/*
 * string_to_string() - Copy the string and return it
 *   return: formatted string
 *   string_value(in): source string to duplicate
 *   string_delimiter(in): delimiter to surround string with (0 if none)
 *   string_introducer(in): introducer for the string (0 if none)
 *   length(in): length of the source string
 *   result_length(out): : length of output string
 *   plain_string(in): refine string for plain output
 */
static char *
string_to_string (const char *string_value, char string_delimiter, char string_introducer, int length,
		  int *result_length, bool plain_string)
{
  char *return_string;
  char *ptr;
  char *con_buf_ptr = NULL;
  int con_buf_size = 0;

  if (plain_string == true)
    {
      return csql_string_to_plain_string (string_value, length, result_length);
    }

  if (string_delimiter == '\0')
    {
      return (duplicate_string (string_value));
    }

  if (string_value == NULL)
    {
      return NULL;
    }

  if ((return_string = (char *) malloc (length + 4)) == NULL)
    {
      return (NULL);
    }

  ptr = return_string;
  if (string_introducer)
    {
      *ptr++ = string_introducer;
    }
  *ptr++ = string_delimiter;
  memcpy (ptr, string_value, length);
  ptr[length] = string_delimiter;
  ptr = ptr + length + 1;
  *ptr = 0;

  if (csql_text_utf8_to_console != NULL
      && (*csql_text_utf8_to_console) (return_string, strlen (return_string), &con_buf_ptr, &con_buf_size) == NO_ERROR)
    {
      if (con_buf_ptr != NULL)
	{
	  free (return_string);
	  return_string = con_buf_ptr;
	  ptr = con_buf_ptr + con_buf_size;
	}
    }

  if (result_length)
    {
      *result_length = CAST_STRLEN (ptr - return_string);
    }
  return return_string;
}
コード例 #2
0
ファイル: message_catalog.c プロジェクト: BogdanStroe/cubrid
nl_catd
catopen (const char *name, int type)
{
  int spcleft, saverr;
  char path[PATH_MAX];
  char *nlspath, *lang, *base, *cptr, *pathP, *tmpptr;
  char *cptr1, *plang, *pter, *pcode;
  struct stat sbuf;

  if (name == NULL || *name == '\0')
    {
      errno = EINVAL;
      return NULL;
    }

  /* is it absolute path ? if yes, load immediately */
  if (strchr (name, '/') != NULL)
    {
      return load_msgcat (name);
    }

  if (type == NL_CAT_LOCALE)
    {
      lang = setlocale (LC_MESSAGES, NULL);
    }
  else
    {
      lang = getenv ("CHARSET");
    }

  if (lang == NULL || *lang == '\0' || strlen (lang) > ENCODING_LEN
      || (lang[0] == '.' && (lang[1] == '\0' || (lang[1] == '.' && lang[2] == '\0'))) || strchr (lang, '/') != NULL)
    {
      lang = (char *) "C";
    }

  plang = cptr1 = strdup (lang);
  if (cptr1 == NULL)
    {
      return NULL;
    }

  cptr = strchr (cptr1, '@');
  if (cptr != NULL)
    {
      *cptr = '\0';
    }

  pter = pcode = (char *) "";
  cptr = strchr (cptr1, '_');
  if (cptr != NULL)
    {
      *cptr++ = '\0';
      pter = cptr1 = cptr;
    }

  cptr = strchr (cptr1, '.');
  if (cptr != NULL)
    {
      *cptr++ = '\0';
      pcode = cptr;
    }

  nlspath = getenv ("NLSPATH");
  if (nlspath == NULL)
    {
      nlspath = (char *) DEFAULT_NLS_PATH;
    }

  base = cptr = strdup (nlspath);
  if (cptr == NULL)
    {
      saverr = errno;
      free (plang);
      errno = saverr;
      return NULL;
    }

  while ((nlspath = strsep (&cptr, ":")) != NULL)
    {
      pathP = path;
      if (*nlspath)
	{
	  for (; *nlspath; ++nlspath)
	    {
	      if (*nlspath == '%')
		{
		  switch (*(nlspath + 1))
		    {
		    case 'l':
		      tmpptr = plang;
		      break;
		    case 't':
		      tmpptr = pter;
		      break;
		    case 'c':
		      tmpptr = pcode;
		      break;
		    case 'L':
		      tmpptr = lang;
		      break;
		    case 'N':
		      tmpptr = (char *) name;
		      break;
		    case '%':
		      ++nlspath;
		      /* fallthrough */
		    default:
		      if (pathP - path >= PATH_MAX - 1)
			{
			  goto too_long;
			}
		      *(pathP++) = *nlspath;
		      continue;
		    }
		  ++nlspath;

		put_tmpptr:
		  spcleft = PATH_MAX - (CAST_STRLEN (pathP - path)) - 1;
		  if (strlcpy (pathP, tmpptr, spcleft) >= (size_t) spcleft)
		    {
		    too_long:
		      free (plang);
		      free (base);
		      errno = ENAMETOOLONG;
		      return NULL;
		    }
		  pathP += strlen (tmpptr);
		}
	      else
		{
		  if (pathP - path >= PATH_MAX - 1)
		    {
		      goto too_long;
		    }
		  *(pathP++) = *nlspath;
		}
	    }
	  *pathP = '\0';
	  if (stat (path, &sbuf) == 0)
	    {
	      free (plang);
	      free (base);
	      return load_msgcat (path);
	    }
	}
      else
	{
	  tmpptr = (char *) name;
	  --nlspath;
	  goto put_tmpptr;
	}
    }

  free (plang);
  free (base);
  errno = ENOENT;

  return NULL;
}
コード例 #3
0
/*
 * xstats_get_statistics_from_server () - Retrieves the class statistics
 *   return: buffer contaning class statistics, or NULL on error
 *   class_id(in): Identifier of the class
 *   timestamp(in):
 *   length(in): Length of the buffer
 *
 * Note: This function retrieves the statistics for the given class from the
 *       catalog manager and stores them into a buffer. Note that since the
 *       statistics are kept on the current (last) representation structure of
 *       the catalog, only this structure is retrieved. Note further that
 *       since the statistics are used only on the client side they are not
 *       put into a structure here on the server side (not even temporarily),
 *       but stored into a buffer area to be transmitted to the client side.
 */
char *
xstats_get_statistics_from_server (THREAD_ENTRY * thread_p, OID * class_id_p,
				   unsigned int time_stamp, int *length_p)
{
  CLS_INFO *cls_info_p;
  REPR_ID repr_id;
  DISK_REPR *disk_repr_p;
  DISK_ATTR *disk_attr_p;
  BTREE_STATS *btree_stats_p;
  int estimated_npages, estimated_nobjs, estimated_avglen;
  int i, j, k, size, n_attrs, tot_n_btstats, tot_key_info_size;
  char *buf_p, *start_p;

  *length_p = -1;

  cls_info_p = catalog_get_class_info (thread_p, class_id_p);
  if (!cls_info_p)
    {
      return NULL;
    }

  if (time_stamp > 0 && time_stamp >= cls_info_p->time_stamp)
    {
      catalog_free_class_info (cls_info_p);
      *length_p = 0;
      return NULL;
    }

  if (catalog_get_last_representation_id (thread_p, class_id_p, &repr_id) !=
      NO_ERROR)
    {
      catalog_free_class_info (cls_info_p);
      return NULL;
    }

  disk_repr_p = catalog_get_representation (thread_p, class_id_p, repr_id);
  if (!disk_repr_p)
    {
      catalog_free_class_info (cls_info_p);
      return NULL;
    }

  n_attrs = disk_repr_p->n_fixed + disk_repr_p->n_variable;

  tot_n_btstats = tot_key_info_size = 0;
  for (i = 0; i < n_attrs; i++)
    {
      if (i < disk_repr_p->n_fixed)
	{
	  disk_attr_p = disk_repr_p->fixed + i;
	}
      else
	{
	  disk_attr_p = disk_repr_p->variable + (i - disk_repr_p->n_fixed);
	}

      tot_n_btstats += disk_attr_p->n_btstats;
      for (j = 0, btree_stats_p = disk_attr_p->bt_stats;
	   j < disk_attr_p->n_btstats; j++, btree_stats_p++)
	{
	  tot_key_info_size +=
	    (or_packed_domain_size (btree_stats_p->key_type, 0) +
	     (OR_INT_SIZE * btree_stats_p->key_size));
	}
    }

  size = (OR_INT_SIZE		/* time_stamp of CLS_INFO */
	  + OR_INT_SIZE		/* tot_objects of CLS_INFO */
	  + OR_INT_SIZE		/* tot_pages of CLS_INFO */
	  + OR_INT_SIZE		/* n_attrs from DISK_REPR */
	  + (OR_INT_SIZE	/* id of DISK_ATTR */
	     + OR_INT_SIZE	/* type of DISK_ATTR */
	     + STATS_MIN_MAX_SIZE	/* min_value of DISK_ATTR */
	     + STATS_MIN_MAX_SIZE	/* max_value of DISK_ATTR */
	     + OR_INT_SIZE	/* n_btstats of DISK_ATTR */
	  ) * n_attrs);		/* number of attributes */

  size += ((OR_BTID_ALIGNED_SIZE	/* btid of BTREE_STATS */
	    + OR_INT_SIZE	/* leafs of BTREE_STATS */
	    + OR_INT_SIZE	/* pages of BTREE_STATS */
	    + OR_INT_SIZE	/* height of BTREE_STATS */
	    + OR_INT_SIZE	/* keys of BTREE_STATS */
	    + OR_INT_SIZE	/* oids of BTREE_STATS */
	    + OR_INT_SIZE	/* nulls of BTREE_STATS */
	    + OR_INT_SIZE	/* ukeys of BTREE_STATS */
	   ) * tot_n_btstats);	/* total number of indexes */

  size += tot_key_info_size;	/* key_type, pkeys[] of BTREE_STATS */

  start_p = buf_p = (char *) malloc (size);
  if (buf_p == NULL)
    {
      catalog_free_representation (disk_repr_p);
      catalog_free_class_info (cls_info_p);
      return NULL;
    }
  memset (start_p, 0, size);

  OR_PUT_INT (buf_p, cls_info_p->time_stamp);
  buf_p += OR_INT_SIZE;

  if (!HFID_IS_NULL (&cls_info_p->hfid)
      && heap_estimate (thread_p, &cls_info_p->hfid, &estimated_npages,
			&estimated_nobjs, &estimated_avglen) > 0)
    {
      /* use estimates from the heap since it is likely that its estimates
         are more accurate than the ones gathered at update statistics time */

      OR_PUT_INT (buf_p, cls_info_p->tot_objects);
      buf_p += OR_INT_SIZE;

      OR_PUT_INT (buf_p, estimated_npages);
      buf_p += OR_INT_SIZE;
    }
  else
    {
      /* cannot get estimates from the heap, use ones from the catalog */

      OR_PUT_INT (buf_p, cls_info_p->tot_objects);
      buf_p += OR_INT_SIZE;

      OR_PUT_INT (buf_p, cls_info_p->tot_pages);
      buf_p += OR_INT_SIZE;

      estimated_npages = estimated_nobjs = estimated_avglen = 0;
    }

  OR_PUT_INT (buf_p, n_attrs);
  buf_p += OR_INT_SIZE;

  /* put the statistics information of each attribute to the buffer */
  for (i = 0; i < n_attrs; i++)
    {
      if (i < disk_repr_p->n_fixed)
	{
	  disk_attr_p = disk_repr_p->fixed + i;
	}
      else
	{
	  disk_attr_p = disk_repr_p->variable + (i - disk_repr_p->n_fixed);
	}

      OR_PUT_INT (buf_p, disk_attr_p->id);
      buf_p += OR_INT_SIZE;

      OR_PUT_INT (buf_p, disk_attr_p->type);
      buf_p += OR_INT_SIZE;

      switch (disk_attr_p->type)
	{
	case DB_TYPE_INTEGER:
	  OR_PUT_INT (buf_p, disk_attr_p->min_value.i);
	  buf_p += STATS_MIN_MAX_SIZE;
	  OR_PUT_INT (buf_p, disk_attr_p->max_value.i);
	  buf_p += STATS_MIN_MAX_SIZE;
	  break;

	case DB_TYPE_BIGINT:
	  OR_PUT_BIGINT (buf_p, disk_attr_p->min_value.bigint);
	  buf_p += STATS_MIN_MAX_SIZE;
	  OR_PUT_BIGINT (buf_p, disk_attr_p->max_value.bigint);
	  buf_p += STATS_MIN_MAX_SIZE;
	  break;

	case DB_TYPE_SHORT:
	  /* store these as full integers because of alignment */
	  OR_PUT_INT (buf_p, disk_attr_p->min_value.i);
	  buf_p += STATS_MIN_MAX_SIZE;
	  OR_PUT_INT (buf_p, disk_attr_p->max_value.i);
	  buf_p += STATS_MIN_MAX_SIZE;
	  break;

	case DB_TYPE_FLOAT:
	  OR_PUT_FLOAT (buf_p, &(disk_attr_p->min_value.f));
	  buf_p += STATS_MIN_MAX_SIZE;
	  OR_PUT_FLOAT (buf_p, &(disk_attr_p->max_value.f));
	  buf_p += STATS_MIN_MAX_SIZE;
	  break;

	case DB_TYPE_DOUBLE:
	  OR_PUT_DOUBLE (buf_p, &(disk_attr_p->min_value.d));
	  buf_p += STATS_MIN_MAX_SIZE;
	  OR_PUT_DOUBLE (buf_p, &(disk_attr_p->max_value.d));
	  buf_p += STATS_MIN_MAX_SIZE;
	  break;

	case DB_TYPE_DATE:
	  OR_PUT_DATE (buf_p, &(disk_attr_p->min_value.date));
	  buf_p += STATS_MIN_MAX_SIZE;
	  OR_PUT_DATE (buf_p, &(disk_attr_p->max_value.date));
	  buf_p += STATS_MIN_MAX_SIZE;
	  break;

	case DB_TYPE_TIME:
	  OR_PUT_TIME (buf_p, &(disk_attr_p->min_value.time));
	  buf_p += STATS_MIN_MAX_SIZE;
	  OR_PUT_TIME (buf_p, &(disk_attr_p->max_value.time));
	  buf_p += STATS_MIN_MAX_SIZE;
	  break;

	case DB_TYPE_UTIME:
	  OR_PUT_UTIME (buf_p, &(disk_attr_p->min_value.utime));
	  buf_p += STATS_MIN_MAX_SIZE;
	  OR_PUT_UTIME (buf_p, &(disk_attr_p->max_value.utime));
	  buf_p += STATS_MIN_MAX_SIZE;
	  break;

	case DB_TYPE_DATETIME:
	  OR_PUT_DATETIME (buf_p, &(disk_attr_p->min_value.datetime));
	  buf_p += STATS_MIN_MAX_SIZE;
	  OR_PUT_DATETIME (buf_p, &(disk_attr_p->max_value.datetime));
	  buf_p += STATS_MIN_MAX_SIZE;
	  break;

	case DB_TYPE_MONETARY:
	  OR_PUT_MONETARY (buf_p, &(disk_attr_p->min_value.money));
	  buf_p += STATS_MIN_MAX_SIZE;
	  OR_PUT_MONETARY (buf_p, &(disk_attr_p->max_value.money));
	  buf_p += STATS_MIN_MAX_SIZE;
	  break;

	default:
	  break;
	}

      OR_PUT_INT (buf_p, disk_attr_p->n_btstats);
      buf_p += OR_INT_SIZE;

      for (j = 0, btree_stats_p = disk_attr_p->bt_stats;
	   j < disk_attr_p->n_btstats; j++, btree_stats_p++)
	{
	  OR_PUT_BTID (buf_p, &btree_stats_p->btid);
	  buf_p += OR_BTID_ALIGNED_SIZE;

	  /* If the btree file has currently more pages than when we gathered
	     statistics, assume that all growth happen at the leaf level. If
	     the btree is smaller, we use the gathered statistics since the
	     btree may have an external file (unknown at this level) to keep
	     overflow keys. */
	  estimated_npages = file_get_numpages (thread_p,
						&btree_stats_p->btid.vfid);
	  if (estimated_npages > btree_stats_p->pages)
	    {
	      OR_PUT_INT (buf_p, (btree_stats_p->leafs +
				  (estimated_npages - btree_stats_p->pages)));
	      buf_p += OR_INT_SIZE;

	      OR_PUT_INT (buf_p, estimated_npages);
	      buf_p += OR_INT_SIZE;
	    }
	  else
	    {
	      OR_PUT_INT (buf_p, btree_stats_p->leafs);
	      buf_p += OR_INT_SIZE;

	      OR_PUT_INT (buf_p, btree_stats_p->pages);
	      buf_p += OR_INT_SIZE;
	    }

	  OR_PUT_INT (buf_p, btree_stats_p->height);
	  buf_p += OR_INT_SIZE;

	  /* If the estimated objects from heap manager is greater than the
	     estimate when the statistics were gathered, assume that the
	     difference is in distinct keys. */
	  if (estimated_nobjs > cls_info_p->tot_objects)
	    {
	      OR_PUT_INT (buf_p, (btree_stats_p->keys +
				  (estimated_nobjs -
				   cls_info_p->tot_objects)));
	      buf_p += OR_INT_SIZE;
	    }
	  else
	    {
	      OR_PUT_INT (buf_p, btree_stats_p->keys);
	      buf_p += OR_INT_SIZE;
	    }

	  OR_PUT_INT (buf_p, btree_stats_p->oids);
	  buf_p += OR_INT_SIZE;

	  OR_PUT_INT (buf_p, btree_stats_p->nulls);
	  buf_p += OR_INT_SIZE;

	  OR_PUT_INT (buf_p, btree_stats_p->ukeys);
	  buf_p += OR_INT_SIZE;

	  buf_p = or_pack_domain (buf_p, btree_stats_p->key_type, 0, 0);

	  for (k = 0; k < btree_stats_p->key_size; k++)
	    {
	      OR_PUT_INT (buf_p, btree_stats_p->pkeys[k]);
	      buf_p += OR_INT_SIZE;
	    }
	}
    }

  catalog_free_representation (disk_repr_p);
  catalog_free_class_info (cls_info_p);

  *length_p = CAST_STRLEN (buf_p - start_p);

  return start_p;
}
コード例 #4
0
ファイル: csql_result_format.c プロジェクト: CUBRID/cubrid
/*
 * csql_string_to_plain_string() - Refine the string and return it
 *   return: refined plain string
 *   string_value(in): source string to duplicate
 *   length(in): length of the source string
 *   result_length(out): : length of output string
 *
 *   note: replace newline and tab with escaped string
 */
char *
csql_string_to_plain_string (const char *string_value, int length, int *result_length)
{
  char *return_string;
  char *ptr;
  char *con_buf_ptr = NULL;
  int con_buf_size = 0;
  int num_found = 0;
  int i;

  if (string_value == NULL)
    {
      return NULL;
    }

  ptr = (char *) string_value;
  while (*ptr != '\0')
    {
      if (*ptr == '\t' || *ptr == '\n' || *ptr == '\\')
	{
	  num_found++;
	}
      ptr++;
    }

  if (num_found == 0)
    {
      if (result_length != NULL)
	{
	  *result_length = length;
	}
      return duplicate_string (string_value);
    }

  return_string = (char *) malloc (length + num_found + 1);
  if (return_string == NULL)
    {
      return NULL;
    }

  ptr = return_string;
  for (i = 0; i < length; i++)
    {
      if (string_value[i] == '\t')
	{
	  ptr += sprintf (ptr, "\\t");
	}
      else if (string_value[i] == '\n')
	{
	  ptr += sprintf (ptr, "\\n");
	}
      else if (string_value[i] == '\\')
	{
	  ptr += sprintf (ptr, "\\\\");
	}
      else
	{
	  *(ptr++) = string_value[i];
	}
    }
  *ptr = '\0';

  if (csql_text_utf8_to_console != NULL
      && (*csql_text_utf8_to_console) (return_string, strlen (return_string), &con_buf_ptr, &con_buf_size) == NO_ERROR)
    {
      if (con_buf_ptr != NULL)
	{
	  free (return_string);
	  return_string = con_buf_ptr;
	  ptr = con_buf_ptr + con_buf_size;
	}
    }

  if (result_length)
    {
      *result_length = CAST_STRLEN (ptr - return_string);
    }

  return return_string;
}