Пример #1
0
text* String_createText(jstring javaString)
{
	text* result = 0;
	if(javaString != 0)
	{
		/* Would be nice if a direct conversion from UTF16 was provided.
		 */
		char* utf8 = (char*)JNI_getStringUTFChars(javaString, 0);
		char* denc = (char*)pg_do_encoding_conversion(
			(unsigned char*)utf8, strlen(utf8), PG_UTF8, GetDatabaseEncoding());
		int dencLen = strlen(denc);
		int varSize = dencLen + VARHDRSZ;

		/* Allocate and initialize the text structure.
		 */
		result = (text*)palloc(varSize);
#if (PGSQL_MAJOR_VER == 8 && PGSQL_MINOR_VER < 3)
		VARATT_SIZEP(result) = varSize;	/* Total size of structure, not just data */
#else
		SET_VARSIZE(result, varSize);	/* Total size of structure, not just data */
#endif
		memcpy(VARDATA(result), denc, dencLen);

		/* pg_do_encoding_conversion will return the source argument
		 * when no conversion is required. We don't want to accidentally
		 * free that pointer.
		 */
		if(denc != utf8)
			pfree(denc);
		JNI_releaseStringUTFChars(javaString, utf8);
	}
	return result;
}
Пример #2
0
jstring String_createJavaString(text* t)
{
	jstring result = 0;
	if(t != 0)
	{
		char* utf8;
		char* src = VARDATA(t);
		int srcLen = VARSIZE(t) - VARHDRSZ;
		if(srcLen == 0)
			return 0;
	
		/* Would be nice if a direct conversion to UTF16 was provided.
		 */
		utf8 = (char*)pg_do_encoding_conversion((unsigned char*)src, srcLen, GetDatabaseEncoding(), PG_UTF8);
		result = JNI_newStringUTF(utf8);

		/* pg_do_encoding_conversion will return the source argument
		 * when no conversion is required. We don't want to accidentally
		 * free that pointer.
		 */
		if(utf8 != src)
			pfree(utf8);
	}
	return result;
}
Пример #3
0
/*
 * Read the next line from a tsearch data file (expected to be in UTF-8), and
 * convert it to database encoding if needed. The returned string is palloc'd.
 * NULL return means EOF.
 *
 * Note: direct use of this function is now deprecated.  Go through
 * tsearch_readline() to provide better error reporting.
 */
char *
t_readline(FILE *fp)
{
	int			len;
	char	   *recoded;
	char		buf[4096];		/* lines must not be longer than this */

	if (fgets(buf, sizeof(buf), fp) == NULL)
		return NULL;

	len = strlen(buf);

	/* Make sure the input is valid UTF-8 */
	(void) pg_verify_mbstr(PG_UTF8, buf, len, false);

	/* And convert */
	recoded = (char *) pg_do_encoding_conversion((unsigned char *) buf,
												 len,
												 PG_UTF8,
												 GetDatabaseEncoding());
	if (recoded == buf)
	{
		/*
		 * conversion didn't pstrdup, so we must. We can use the length of the
		 * original string, because no conversion was done.
		 */
		recoded = pnstrdup(recoded, len);
	}

	return recoded;
}
Пример #4
0
/*
 * Converts OpenSSL ASN1_STRING structure into text
 *
 * Converts ASN1_STRING into text, converting all the characters into
 * current database encoding if possible.  Any invalid characters are
 * replaced by question marks.
 *
 * Parameter: str - OpenSSL ASN1_STRING structure.	Memory managment
 * of this structure is responsibility of caller.
 *
 * Returns Datum, which can be directly returned from a C language SQL
 * function.
 */
datum_t
ASN1_STRING_to_text(ASN1_STRING *str)
{
	BIO		   *membuf;
	size_t		size;
	char		nullterm;
	char	   *sp;
	char	   *dp;
	text	   *result;

	membuf = BIO_new(BIO_s_mem());
	(void) BIO_set_close(membuf, BIO_CLOSE);
	ASN1_STRING_print_ex(membuf, str,
						 ((ASN1_STRFLGS_RFC2253 & ~ASN1_STRFLGS_ESC_MSB)
						  | ASN1_STRFLGS_UTF8_CONVERT));
	/* ensure null termination of the BIO's content */
	nullterm = '\0';
	BIO_write(membuf, &nullterm, 1);
	size = BIO_get_mem_data(membuf, &sp);
	dp = (char *) pg_do_encoding_conversion((unsigned char *) sp,
											size - 1,
											PG_UTF8,
											get_db_encoding());
	result = cstring_to_text(dp);
	if (dp != sp)
		pfree(dp);
	BIO_free(membuf);

	RET_TEXT_P(result);
}
Пример #5
0
/*
 * Converts OpenSSL ASN1_STRING structure into text
 *
 * Converts ASN1_STRING into text, converting all the characters into
 * current database encoding if possible.  Any invalid characters are
 * replaced by question marks.
 *
 * Parameter: str - OpenSSL ASN1_STRING structure.	Memory managment
 * of this structure is responsibility of caller.
 *
 * Returns Datum, which can be directly returned from a C language SQL
 * function.
 */
Datum
ASN1_STRING_to_text(ASN1_STRING *str)
{
	BIO		   *membuf = NULL;
	size_t		size,
				outlen;
	char	   *sp;
	char	   *dp;
	text	   *result;

	membuf = BIO_new(BIO_s_mem());
	(void) BIO_set_close(membuf, BIO_CLOSE);
	ASN1_STRING_print_ex(membuf, str,
						 ((ASN1_STRFLGS_RFC2253 & ~ASN1_STRFLGS_ESC_MSB)
						  | ASN1_STRFLGS_UTF8_CONVERT));

	outlen = 0;
	BIO_write(membuf, &outlen, 1);
	size = BIO_get_mem_data(membuf, &sp);
	dp = (char *) pg_do_encoding_conversion((unsigned char *) sp,
											size - 1,
											PG_UTF8,
											GetDatabaseEncoding());
	outlen = strlen(dp);
	result = palloc(VARHDRSZ + outlen);
	memcpy(VARDATA(result), dp, outlen);
	if (dp != sp)
		pfree(dp);

	BIO_free(membuf);
	VARATT_SIZEP(result) = outlen + VARHDRSZ;
	PG_RETURN_TEXT_P(result);
}
Пример #6
0
jstring String_createJavaStringFromNTS(const char* cp)
{
	jstring result = 0;
	if(cp != 0)
	{
		jobject bytebuf;
		jobject charbuf;
		Size sz = strlen(cp);
		char const * utf8 = cp;
		if ( s_two_step_conversion )
		{
			utf8 = (char*)pg_do_encoding_conversion((unsigned char*)cp,
				(int)sz, s_server_encoding, PG_UTF8);
			sz = strlen(utf8);
		}
		bytebuf = JNI_newDirectByteBuffer((void *)utf8, sz);
		charbuf = JNI_callObjectMethodLocked(s_CharsetDecoder_instance,
			s_CharsetDecoder_decode, bytebuf);
		result = JNI_callObjectMethodLocked(charbuf, s_Object_toString);

		JNI_deleteLocalRef(bytebuf);
		JNI_deleteLocalRef(charbuf);
		/* pg_do_encoding_conversion will return the source argument
		 * when no conversion is required. We don't want to accidentally
		 * free that pointer.
		 */
		if(utf8 != cp)
			pfree((void *)utf8);
	}
	return result;
}
Пример #7
0
jstring String_createJavaString(text* t)
{
	jstring result = 0;
	if(t != 0)
	{
		jobject bytebuf;
		jobject charbuf;
		char* src = VARDATA(t);
		char* utf8 = src;
		Size srcLen = VARSIZE(t) - VARHDRSZ;
		if(srcLen == 0)
			return s_the_empty_string;
	
		if ( s_two_step_conversion )
		{
			utf8 = (char*)pg_do_encoding_conversion((unsigned char*)src,
				(int)srcLen, s_server_encoding, PG_UTF8);
			srcLen = strlen(utf8);
		}
		bytebuf = JNI_newDirectByteBuffer(utf8, srcLen);
		charbuf = JNI_callObjectMethodLocked(s_CharsetDecoder_instance,
			s_CharsetDecoder_decode, bytebuf);
		result = JNI_callObjectMethodLocked(charbuf, s_Object_toString);

		JNI_deleteLocalRef(bytebuf);
		JNI_deleteLocalRef(charbuf);
		/* pg_do_encoding_conversion will return the source argument
		 * when no conversion is required. We don't want to accidentally
		 * free that pointer.
		 */
		if(utf8 != src)
			pfree(utf8);
	}
	return result;
}
Пример #8
0
/*
 * On win32, strftime() returns the encoding in CP_ACP, which is likely
 * different from SERVER_ENCODING. This is especially important in Japanese
 * versions of Windows which will use SJIS encoding, which we don't support
 * as a server encoding.
 *
 * Replace strftime() with a version that gets the string in UTF16 and then
 * converts it to the appropriate encoding as necessary.
 *
 * Note that this only affects the calls to strftime() in this file, which are
 * used to get the locale-aware strings. Other parts of the backend use
 * pg_strftime(), which isn't locale-aware and does not need to be replaced.
 */
static size_t
strftime_win32(char *dst, size_t dstlen, const wchar_t *format, const struct tm *tm)
{
	size_t	len;
	wchar_t	wbuf[MAX_L10N_DATA];
	int		encoding;

	encoding = GetDatabaseEncoding();

	len = wcsftime(wbuf, MAX_L10N_DATA, format, tm);
	if (len == 0)
		/* strftime call failed - return 0 with the contents of dst unspecified */
		return 0;

	len = WideCharToMultiByte(CP_UTF8, 0, wbuf, len, dst, dstlen, NULL, NULL);
	if (len == 0)
		elog(ERROR,
			"could not convert string to UTF-8:error %lu", GetLastError());

	dst[len] = '\0';
	if (encoding != PG_UTF8)
	{
		char *convstr = pg_do_encoding_conversion(dst, len, PG_UTF8, encoding);
		if (dst != convstr)
		{
			strlcpy(dst, convstr, dstlen);
			len = strlen(dst);
		}
	}

	return len;
}
Пример #9
0
char* String_createNTS(jstring javaString)
{
	char* result = 0;

	if( 0 == javaString )
		return result;

	if ( uninitialized )
	{
		const char* u8buf;

		s_server_encoding = GetDatabaseEncoding();
		u8buf = JNI_getStringUTFChars( javaString, NULL);
		if ( 0 == u8buf )
			return result;
		result = (char*)pg_do_encoding_conversion(
			(unsigned char *)u8buf, (int)strlen( u8buf),
			PG_UTF8, s_server_encoding);
		if ( result == u8buf )
			result = pstrdup( result);
		JNI_releaseStringUTFChars( javaString, u8buf);
		return result;
	}
	else
	{
		jobject charbuf = JNI_callStaticObjectMethodLocked(s_CharBuffer_class,
			s_CharBuffer_wrap, javaString);
		StringInfoData sid;
		initStringInfo(&sid);
		appendCharBuffer(&sid, charbuf);
		JNI_deleteLocalRef(charbuf);

		result = (char*)pg_do_encoding_conversion(
			(unsigned char *)sid.data, sid.len, PG_UTF8, s_server_encoding);

		/* pg_do_encoding_conversion will return the source argument
		 * when no conversion is required. Don't free it in that case.
		 */
		if(result != sid.data)
			pfree(sid.data);
	}

	return result;
}
Пример #10
0
char *
CheckerConversion(Checker *checker, char *src)
{
	int	len;

	if (!checker->check_encoding)
		return src;

	len = strlen(src);

	if (checker->encoding == checker->db_encoding ||
		checker->encoding == PG_SQL_ASCII)
	{
		/*
		 * No conversion is needed, but we must still validate the data.
		 */
		pg_verify_mbstr(checker->db_encoding, src, len, false);
		return src;
	}

	if (checker->db_encoding == PG_SQL_ASCII)
	{
		/*
		 * No conversion is possible, but we must still validate the data,
		 * because the client-side code might have done string escaping using
		 * the selected client_encoding.  If the client encoding is ASCII-safe
		 * then we just do a straight validation under that encoding.  For an
		 * ASCII-unsafe encoding we have a problem: we dare not pass such data
		 * to the parser but we have no way to convert it.	We compromise by
		 * rejecting the data if it contains any non-ASCII characters.
		 */
		if (PG_VALID_BE_ENCODING(checker->encoding))
			pg_verify_mbstr(checker->encoding, src, len, false);
		else
		{
			int			i;

			for (i = 0; i < len; i++)
			{
				if (src[i] == '\0' || IS_HIGHBIT_SET(src[i]))
					ereport(ERROR,
							(errcode(ERRCODE_CHARACTER_NOT_IN_REPERTOIRE),
					 errmsg("invalid byte value for encoding \"%s\": 0x%02x",
							pg_enc2name_tbl[PG_SQL_ASCII].name,
							(unsigned char) src[i])));
			}
		}
		return src;
	}

	/* Convert the input into the database encoding. */
	return (char *) pg_do_encoding_conversion((unsigned char *) src,
											  len,
											  checker->encoding,
											  checker->db_encoding);
}
Пример #11
0
/*
 * Equivalent of X509_NAME_oneline that respects encoding
 *
 * This function converts X509_NAME structure to the text variable
 * converting all textual data into current database encoding.
 *
 * Parameter: X509_NAME *name X509_NAME structure to be converted
 *
 * Returns: text datum which contains string representation of
 * X509_NAME
 */
Datum
X509_NAME_to_text(X509_NAME *name)
{
	BIO		   *membuf = BIO_new(BIO_s_mem());
	int			i,
				nid,
				count = X509_NAME_entry_count(name);
	X509_NAME_ENTRY *e;
	ASN1_STRING *v;

	const char *field_name;
	size_t		size,
				outlen;
	char	   *sp;
	char	   *dp;
	text	   *result;

	(void) BIO_set_close(membuf, BIO_CLOSE);
	for (i = 0; i < count; i++)
	{
		e = X509_NAME_get_entry(name, i);
		nid = OBJ_obj2nid(X509_NAME_ENTRY_get_object(e));
		v = X509_NAME_ENTRY_get_data(e);
		field_name = OBJ_nid2sn(nid);
		if (!field_name)
			field_name = OBJ_nid2ln(nid);
		BIO_printf(membuf, "/%s=", field_name);
		ASN1_STRING_print_ex(membuf, v,
							 ((ASN1_STRFLGS_RFC2253 & ~ASN1_STRFLGS_ESC_MSB)
							  | ASN1_STRFLGS_UTF8_CONVERT));
	}

	i = 0;
	BIO_write(membuf, &i, 1);
	size = BIO_get_mem_data(membuf, &sp);

	dp = (char *) pg_do_encoding_conversion((unsigned char *) sp,
											size - 1,
											PG_UTF8,
											GetDatabaseEncoding());
	BIO_free(membuf);
	outlen = strlen(dp);
	result = palloc(VARHDRSZ + outlen);
	memcpy(VARDATA(result), dp, outlen);

	/*
	 * pg_do_encoding_conversion has annoying habit of returning source
	 * pointer
	 */
	if (dp != sp)
		pfree(dp);
	VARATT_SIZEP(result) = outlen + VARHDRSZ;
	PG_RETURN_TEXT_P(result);
}
Пример #12
0
/*
 * Convert string using encoding_nanme.
 *
 * TEXT convert2(TEXT string, NAME src_encoding_name, NAME dest_encoding_name)
 */
Datum
pg_convert2(PG_FUNCTION_ARGS)
{
	text	   *string = PG_GETARG_TEXT_P(0);
	char	   *src_encoding_name = NameStr(*PG_GETARG_NAME(1));
	int			src_encoding = pg_char_to_encoding(src_encoding_name);
	char	   *dest_encoding_name = NameStr(*PG_GETARG_NAME(2));
	int			dest_encoding = pg_char_to_encoding(dest_encoding_name);
	unsigned char *result;
	text	   *retval;
	unsigned char *str;
	int			len;

	if (src_encoding < 0)
		ereport(ERROR,
				(errcode(ERRCODE_INVALID_PARAMETER_VALUE),
				 errmsg("invalid source encoding name \"%s\"",
						src_encoding_name)));
	if (dest_encoding < 0)
		ereport(ERROR,
				(errcode(ERRCODE_INVALID_PARAMETER_VALUE),
				 errmsg("invalid destination encoding name \"%s\"",
						dest_encoding_name)));

	/* make sure that source string is null terminated */
	len = VARSIZE(string) - VARHDRSZ;
	str = palloc(len + 1);
	memcpy(str, VARDATA(string), len);
	*(str + len) = '\0';

	result = pg_do_encoding_conversion(str, len, src_encoding, dest_encoding);
	if (result == NULL)
		elog(ERROR, "encoding conversion failed");

	/*
	 * build text data type structure. we cannot use textin() here, since
	 * textin assumes that input string encoding is same as database
	 * encoding.
	 */
	len = strlen(result) + VARHDRSZ;
	retval = palloc(len);
	VARATT_SIZEP(retval) = len;
	memcpy(VARDATA(retval), result, len - VARHDRSZ);

	if (result != str)
		pfree(result);
	pfree(str);

	/* free memory if allocated by the toaster */
	PG_FREE_IF_COPY(string, 0);

	PG_RETURN_TEXT_P(retval);
}
Пример #13
0
Файл: file.c Проект: 50wu/gpdb
/* encode(t, encoding) */
static char *
encode_text(int encoding, text *t, int *length)
{
	char	   *src = VARDATA_ANY(t);
	char	   *encoded;

	encoded = (char *) pg_do_encoding_conversion((unsigned char *) src,
					VARSIZE_ANY_EXHDR(t), GetDatabaseEncoding(), encoding);

	*length = (src == encoded ? VARSIZE_ANY_EXHDR(t) : strlen(encoded));
	return encoded;
}
Пример #14
0
/*
 * Convert string using encoding_names.
 *
 * BYTEA convert(BYTEA string, NAME src_encoding_name, NAME dest_encoding_name)
 */
Datum
pg_convert(PG_FUNCTION_ARGS)
{
	bytea	   *string = PG_GETARG_BYTEA_P(0);
	char	   *src_encoding_name = NameStr(*PG_GETARG_NAME(1));
	int			src_encoding = pg_char_to_encoding(src_encoding_name);
	char	   *dest_encoding_name = NameStr(*PG_GETARG_NAME(2));
	int			dest_encoding = pg_char_to_encoding(dest_encoding_name);
	unsigned char *result;
	bytea	   *retval;
	unsigned char *str;
	int			len;

	if (src_encoding < 0)
		ereport(ERROR,
				(errcode(ERRCODE_INVALID_PARAMETER_VALUE),
				 errmsg("invalid source encoding name \"%s\"",
						src_encoding_name)));
	if (dest_encoding < 0)
		ereport(ERROR,
				(errcode(ERRCODE_INVALID_PARAMETER_VALUE),
				 errmsg("invalid destination encoding name \"%s\"",
						dest_encoding_name)));

	/* make sure that source string is valid and null terminated */
	len = VARSIZE(string) - VARHDRSZ;
	pg_verify_mbstr(src_encoding, VARDATA(string), len, false);
	str = palloc(len + 1);
	memcpy(str, VARDATA(string), len);
	*(str + len) = '\0';

	result = pg_do_encoding_conversion(str, len, src_encoding, dest_encoding);

	/*
	 * build bytea data type structure.
	 */
	len = strlen((char *) result) + VARHDRSZ;
	retval = palloc(len);
	SET_VARSIZE(retval, len);
	memcpy(VARDATA(retval), result, len - VARHDRSZ);

	if (result != str)
		pfree(result);
	pfree(str);

	/* free memory if allocated by the toaster */
	PG_FREE_IF_COPY(string, 0);

	PG_RETURN_BYTEA_P(retval);
}
Пример #15
0
/*
 * Return a strdup'ed string converted from the specified encoding to the
 * database encoding.
 */
static char *
db_encoding_strdup(int encoding, const char *str)
{
	char	   *pstr;
	char	   *mstr;

	/* convert the string to the database encoding */
	pstr = (char *) pg_do_encoding_conversion(
										  (unsigned char *) str, strlen(str),
											encoding, GetDatabaseEncoding());
	mstr = strdup(pstr);
	if (pstr != str)
		pfree(pstr);

	return mstr;
}
Пример #16
0
/*
 * returns src in case of no conversion or error
 */
static text *
convert_charset(text *src, int cset_from, int cset_to)
{
	int			src_len = VARSIZE(src) - VARHDRSZ;
	unsigned char *dst;
	unsigned char *csrc = (unsigned char *) VARDATA(src);
	text	   *res;

	dst = pg_do_encoding_conversion(csrc, src_len, cset_from, cset_to);
	if (dst == csrc)
		return src;

	res = cstring_to_text((char *) dst);
	pfree(dst);
	return res;
}
Пример #17
0
/*
 * Equivalent of X509_NAME_oneline that respects encoding
 *
 * This function converts X509_NAME structure to the text variable
 * converting all textual data into current database encoding.
 *
 * Parameter: X509_NAME *name X509_NAME structure to be converted
 *
 * Returns: text datum which contains string representation of
 * X509_NAME
 */
datum_t
X509_NAME_to_text(X509_NAME *name)
{
	BIO		   *membuf = BIO_new(BIO_s_mem());
	int			i,
				nid,
				count = X509_NAME_entry_count(name);
	X509_NAME_ENTRY *e;
	ASN1_STRING *v;
	const char *field_name;
	size_t		size;
	char		nullterm;
	char	   *sp;
	char	   *dp;
	text	   *result;

	(void) BIO_set_close(membuf, BIO_CLOSE);
	for (i = 0; i < count; i++)
	{
		e = X509_NAME_get_entry(name, i);
		nid = OBJ_obj2nid(X509_NAME_ENTRY_get_object(e));
		v = X509_NAME_ENTRY_get_data(e);
		field_name = OBJ_nid2sn(nid);
		if (!field_name)
			field_name = OBJ_nid2ln(nid);
		BIO_printf(membuf, "/%s=", field_name);
		ASN1_STRING_print_ex(membuf, v,
							 ((ASN1_STRFLGS_RFC2253 & ~ASN1_STRFLGS_ESC_MSB)
							  | ASN1_STRFLGS_UTF8_CONVERT));
	}

	/* ensure null termination of the BIO's content */
	nullterm = '\0';
	BIO_write(membuf, &nullterm, 1);
	size = BIO_get_mem_data(membuf, &sp);
	dp = (char *) pg_do_encoding_conversion((unsigned char *) sp,
											size - 1,
											PG_UTF8,
											get_db_encoding());
	result = cstring_to_text(dp);
	if (dp != sp)
		pfree(dp);
	BIO_free(membuf);

	RET_TEXT_P(result);
}
Пример #18
0
static char *
percent_encode(unsigned char *s, int srclen)
{
	unsigned char  *end;
	StringInfoData  buf;
	int				len;

	initStringInfo(&buf);

	if (srclen < 0)
		srclen = strlen((char *) s);

	end = s + srclen;

	for (; s < end; s += len)
	{
		unsigned char  *utf;
		int				ulen;

		len = pg_mblen((const char *) s);

		if (len == 1)
		{
			if (('0' <= s[0] && s[0] <= '9') ||
				('A' <= s[0] && s[0] <= 'Z') ||
				('a' <= s[0] && s[0] <= 'z') ||
				(s[0] == '-') || (s[0] == '.') ||
				(s[0] == '_') || (s[0] == '~'))
			{
				appendStringInfoChar(&buf, s[0]);
				continue;
			}
		}

		utf = pg_do_encoding_conversion(s, len, GetDatabaseEncoding(), PG_UTF8);
		ulen = pg_encoding_mblen(PG_UTF8, (const char *) utf);
		while(ulen--)
		{
			appendStringInfo(&buf, "%%%2X", *utf);
			utf++;
		}
	}

	return buf.data;
}
Пример #19
0
jstring String_createJavaStringFromNTS(const char* cp)
{
	jstring result = 0;
	if(cp != 0)
	{
		/* Would be nice if a direct conversion to UTF16 was provided.
		 */
		char* utf8 = (char*)pg_do_encoding_conversion((unsigned char*)cp, strlen(cp), GetDatabaseEncoding(), PG_UTF8);
		result = JNI_newStringUTF(utf8);

		/* pg_do_encoding_conversion will return the source argument
		 * when no conversion is required. We don't want to accidentally
		 * free that pointer.
		 */
		if(utf8 != cp)
			pfree(utf8);
	}
	return result;
}
Пример #20
0
char* String_createNTS(jstring javaString)
{
	char* result = 0;
	if(javaString != 0)
	{
		/* Would be nice if a direct conversion from UTF16 was provided.
		 */
		char* utf8 = (char*)JNI_getStringUTFChars(javaString, 0);
		result = (char*)pg_do_encoding_conversion(
			(unsigned char*)utf8, strlen(utf8), PG_UTF8, GetDatabaseEncoding());

		/* pg_do_encoding_conversion will return the source argument
		 * when no conversion is required. We always want a copy here.
		 */
		if(result == utf8)
			result = pstrdup(result);
		JNI_releaseStringUTFChars(javaString, utf8);
	}
	return result;
}
Пример #21
0
void String_appendJavaString(StringInfoData* buf, jstring javaString)
{
	if(javaString != 0)
	{
		/* Would be nice if a direct conversion from UTF16 was provided.
		 */
		char* utf8 = (char*)JNI_getStringUTFChars(javaString, 0);
		char* dbEnc = (char*)pg_do_encoding_conversion(
			(unsigned char*)utf8, strlen(utf8), PG_UTF8, GetDatabaseEncoding());

		appendStringInfoString(buf, dbEnc);

		/* pg_do_encoding_conversion will return the source argument
		 * when no conversion is required. We don't want to accidentally
		 * free that pointer.
		 */
		if(dbEnc != utf8)
			pfree(dbEnc);
		JNI_releaseStringUTFChars(javaString, utf8);
	}
}
Пример #22
0
text* String_createText(jstring javaString)
{
	text* result = 0;
	if(javaString != 0)
	{
		char* denc;
		Size dencLen;
		Size varSize;
		jobject charbuf = JNI_callStaticObjectMethodLocked(s_CharBuffer_class,
			s_CharBuffer_wrap, javaString);
		StringInfoData sid;
		initStringInfo(&sid);
		appendCharBuffer(&sid, charbuf);
		JNI_deleteLocalRef(charbuf);
		denc = sid.data;
		dencLen = sid.len;
		if ( s_two_step_conversion )
		{
			denc = (char*)pg_do_encoding_conversion(
				(unsigned char*)denc, (int)dencLen, PG_UTF8, s_server_encoding);
			dencLen = strlen(denc);
		}
		varSize = dencLen + VARHDRSZ;

		/* Allocate and initialize the text structure.
		 */
		result = (text*)palloc(varSize);
#if PG_VERSION_NUM < 80300
		VARATT_SIZEP(result) = varSize;	/* Total size of structure, not just data */
#else
		SET_VARSIZE(result, varSize);	/* Total size of structure, not just data */
#endif
		memcpy(VARDATA(result), denc, dencLen);

		if(denc != sid.data)
			pfree(denc);
		pfree(sid.data);
	}
	return result;
}
Пример #23
0
/*
 * Convert a C string in the PostgreSQL server encoding to a Python
 * unicode object.	Reference ownership is passed to the caller.
 */
PyObject *
PyString_FromStringAndSize(const char *s, Py_ssize_t size)
{
	char	   *utf8string;
	PyObject   *o;

	utf8string = (char *) pg_do_encoding_conversion((unsigned char *) s,
													strlen(s),
													GetDatabaseEncoding(),
													PG_UTF8);
	if (size < 0)
	{
		o = PyUnicode_FromString(utf8string);
	}
	else
	{
		o = PyUnicode_FromStringAndSize(utf8string, size);
	}
	if (utf8string != s)
		pfree(utf8string);

	return o;
}
Пример #24
0
/*
 * Retrieve statement statistics.
 */
Datum
pg_stat_statements(PG_FUNCTION_ARGS)
{
	ReturnSetInfo *rsinfo = (ReturnSetInfo *) fcinfo->resultinfo;
	TupleDesc	tupdesc;
	Tuplestorestate *tupstore;
	MemoryContext per_query_ctx;
	MemoryContext oldcontext;
	Oid			userid = GetUserId();
	bool		is_superuser = superuser();
	HASH_SEQ_STATUS hash_seq;
	pgssEntry  *entry;

	if (!pgss || !pgss_hash)
		ereport(ERROR,
				(errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE),
				 errmsg("pg_stat_statements must be loaded via shared_preload_libraries")));

	/* check to see if caller supports us returning a tuplestore */
	if (rsinfo == NULL || !IsA(rsinfo, ReturnSetInfo))
		ereport(ERROR,
				(errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
				 errmsg("set-valued function called in context that cannot accept a set")));
	if (!(rsinfo->allowedModes & SFRM_Materialize))
		ereport(ERROR,
				(errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
				 errmsg("materialize mode required, but it is not " \
						"allowed in this context")));

	/* Build a tuple descriptor for our result type */
	if (get_call_result_type(fcinfo, NULL, &tupdesc) != TYPEFUNC_COMPOSITE)
		elog(ERROR, "return type must be a row type");

	per_query_ctx = rsinfo->econtext->ecxt_per_query_memory;
	oldcontext = MemoryContextSwitchTo(per_query_ctx);

	tupstore = tuplestore_begin_heap(true, false, work_mem);
	rsinfo->returnMode = SFRM_Materialize;
	rsinfo->setResult = tupstore;
	rsinfo->setDesc = tupdesc;

	MemoryContextSwitchTo(oldcontext);

	LWLockAcquire(pgss->lock, LW_SHARED);

	hash_seq_init(&hash_seq, pgss_hash);
	while ((entry = hash_seq_search(&hash_seq)) != NULL)
	{
		Datum		values[PG_STAT_STATEMENTS_COLS];
		bool		nulls[PG_STAT_STATEMENTS_COLS];
		int			i = 0;
		Counters	tmp;

		memset(values, 0, sizeof(values));
		memset(nulls, 0, sizeof(nulls));

		values[i++] = ObjectIdGetDatum(entry->key.userid);
		values[i++] = ObjectIdGetDatum(entry->key.dbid);

		if (is_superuser || entry->key.userid == userid)
		{
			char	   *qstr;

			qstr = (char *)
				pg_do_encoding_conversion((unsigned char *) entry->query,
										  entry->key.query_len,
										  entry->key.encoding,
										  GetDatabaseEncoding());
			values[i++] = CStringGetTextDatum(qstr);
			if (qstr != entry->query)
				pfree(qstr);
		}
		else
			values[i++] = CStringGetTextDatum("<insufficient privilege>");

		/* copy counters to a local variable to keep locking time short */
		{
			volatile pgssEntry *e = (volatile pgssEntry *) entry;

			SpinLockAcquire(&e->mutex);
			tmp = e->counters;
			SpinLockRelease(&e->mutex);
		}

		values[i++] = Int64GetDatumFast(tmp.calls);
		values[i++] = Float8GetDatumFast(tmp.total_time);
		values[i++] = Int64GetDatumFast(tmp.rows);
		values[i++] = Int64GetDatumFast(tmp.shared_blks_hit);
		values[i++] = Int64GetDatumFast(tmp.shared_blks_read);
		values[i++] = Int64GetDatumFast(tmp.shared_blks_written);
		values[i++] = Int64GetDatumFast(tmp.local_blks_hit);
		values[i++] = Int64GetDatumFast(tmp.local_blks_read);
		values[i++] = Int64GetDatumFast(tmp.local_blks_written);
		values[i++] = Int64GetDatumFast(tmp.temp_blks_read);
		values[i++] = Int64GetDatumFast(tmp.temp_blks_written);

		Assert(i == PG_STAT_STATEMENTS_COLS);

		tuplestore_putvalues(tupstore, tupdesc, values, nulls);
	}

	LWLockRelease(pgss->lock);

	/* clean up and return the tuplestore */
	tuplestore_donestoring(tupstore);

	return (Datum) 0;
}
Пример #25
0
Файл: file.c Проект: 50wu/gpdb
static text *
get_line(FILE *f, int max_linesize, int encoding, bool *iseof)
{
	int c;
	char *buffer = NULL;
	char *bpt;
	int csize = 0;
	text *result = NULL;

	bool eof = true;

	buffer = palloc(max_linesize + 2);
	bpt = buffer;

	errno = 0;

	while (csize < max_linesize && (c = fgetc(f)) != EOF)
	{
		eof = false; 	/* I was able read one char */

		if (c == '\r')  /* lookin ahead \n */
		{
			c = fgetc(f);
			if (c == EOF)
				break;  /* last char */

			if (c != '\n')
				ungetc(c, f);
			/* skip \r\n */
			break;
		}
		else if (c == '\n')
			break;

		++csize;
		*bpt++ = c;
	}

	if (!eof)
	{
		char   *decoded;
		int		len;

		pg_verify_mbstr(encoding, buffer, csize, false);
		decoded = (char *) pg_do_encoding_conversion((unsigned char *) buffer,
									 csize, encoding, GetDatabaseEncoding());
		len = (decoded == buffer ? csize : strlen(decoded));
		result = palloc(len + VARHDRSZ);
		memcpy(VARDATA(result), decoded, len);
		SET_VARSIZE(result, len + VARHDRSZ);
		if (decoded != buffer)
			pfree(decoded);
		*iseof = false;
	}
	else
	{
		switch (errno)
		{
			case 0:
				break;

			case EBADF:
				CUSTOM_EXCEPTION(INVALID_OPERATION, "file descriptor isn't valid for reading");
				break;

			default:
				CUSTOM_EXCEPTION(READ_ERROR, strerror(errno));
				break;
		}

		*iseof = true;
	}

	pfree(buffer);
	return result;
}
Пример #26
0
Datum LWGEOM_to_latlon(PG_FUNCTION_ARGS)
{
	/* Get the parameters */
	GSERIALIZED *pg_lwgeom = (GSERIALIZED *) PG_DETOAST_DATUM(PG_GETARG_DATUM(0));
	text *format_text = PG_GETARG_TEXT_P(1);

	LWGEOM *lwgeom;
	char *format_str = NULL;

	char * formatted_str;
	text * formatted_text;
	char * tmp;

	/* Only supports points. */
	uint8_t geom_type = gserialized_get_type(pg_lwgeom);
	if (POINTTYPE != geom_type)
	{
		lwerror("Only points are supported, you tried type %s.", lwtype_name(geom_type));
	}
	/* Convert to LWGEOM type */
	lwgeom = lwgeom_from_gserialized(pg_lwgeom);

  if (format_text == NULL) {
    lwerror("ST_AsLatLonText: invalid format string (null");
    PG_RETURN_NULL();
  }

	format_str = text2cstring(format_text);
  assert(format_str != NULL);

  /* The input string supposedly will be in the database encoding,
     so convert to UTF-8. */
  tmp = (char *)pg_do_encoding_conversion(
    (uint8_t *)format_str, strlen(format_str), GetDatabaseEncoding(), PG_UTF8);
  assert(tmp != NULL);
  if ( tmp != format_str ) {
    pfree(format_str);
    format_str = tmp;
  }

	/* Produce the formatted string. */
	formatted_str = lwpoint_to_latlon((LWPOINT *)lwgeom, format_str);
  assert(formatted_str != NULL);
  pfree(format_str);

  /* Convert the formatted string from UTF-8 back to database encoding. */
  tmp = (char *)pg_do_encoding_conversion(
    (uint8_t *)formatted_str, strlen(formatted_str),
    PG_UTF8, GetDatabaseEncoding());
  assert(tmp != NULL);
  if ( tmp != formatted_str) {
    pfree(formatted_str);
    formatted_str = tmp;
  }

	/* Convert to the postgres output string type. */
	formatted_text = cstring2text(formatted_str);
  pfree(formatted_str);

	PG_RETURN_POINTER(formatted_text);
}
Пример #27
0
/**
 * Validation function take first argument as XML type, then check if is
 * well formated. If so, do the same for RNG document. If both success, check
 * XML document against RNG schema restrictions.
 * @return true if pass, false otherwise
 */
Datum
xmlvalidate_rng(PG_FUNCTION_ARGS)
{
#ifdef USE_LIBXML

    text        *data   = NULL;
	char        *rng    = NULL;
	xmlChar     *utf8rng    = NULL;
    xmltype     *xmldata    = NULL;
    char        *xmldataint = NULL;
    xmlChar     *xmldatastr = NULL;
    bool        result  = false;
    int         lenxml  = -1;       // length of xml data
    int         lenrng  = -1;       // length of xsd data
    xmlDocPtr               doc = NULL;
    int ret = -1;

    xmlRelaxNGParserCtxtPtr ctxt    = NULL;
    xmlRelaxNGPtr           schema  = NULL;
    xmlRelaxNGValidCtxtPtr   validctxt = NULL;


    // creating xmlChar * from internal xmltype of stored XML
    xmldata     = PG_GETARG_XML_P(0);
    xmldataint  = VARDATA(xmldata);
    lenxml      = VARSIZE(xmldata) - VARHDRSZ;
    xmldatastr  = (xmlChar *) palloc((lenxml + 1) * sizeof(xmlChar));
	memcpy(xmldatastr, xmldataint, lenxml);
	xmldatastr[lenxml] = '\0';

    // creating xmlChar* from text representation of XSD
    data = PG_GETARG_TEXT_P(1);
	lenrng = VARSIZE(data) - VARHDRSZ;
	rng = text_to_cstring(data);

    //encode XML to internal representation with UTF-8, only one used in LibXML
	utf8rng = pg_do_encoding_conversion((unsigned char*)rng,
										   lenrng,
										   GetDatabaseEncoding(),
										   PG_UTF8);

    //initialize LibXML structures, if allready done -> do nothing
    pg_xml_init();
	xmlInitParser();

    doc = xmlReadMemory((const char *)xmldatastr, lenxml, "include.xml", NULL, 0);

     if (doc == NULL) {
        elog(ERROR, "Failed to parse XML document");
        PG_RETURN_BOOL (false);
    }

    ctxt = xmlRelaxNGNewMemParserCtxt(rng, lenrng);

    if (ctxt == NULL)
    { // unable to create parser context
        elog(ERROR, "Error with creating schema, check if RelaxNG schema is valid");
        PG_RETURN_BOOL (false);
    }

    schema = xmlRelaxNGParse(ctxt);  // parse schema
    xmlRelaxNGFreeParserCtxt(ctxt);  // realease parser context

    validctxt = xmlRelaxNGNewValidCtxt(schema);
    if (validctxt == NULL)
    { // cant create validation context
        xmlRelaxNGFree(schema);
        elog(ERROR, "Cant create validation context");
        PG_RETURN_BOOL (false);
    }

    // set errors to SQL errors
	xmlRelaxNGSetValidErrors(validctxt,
			    xml_error_handler,
			    NULL,
			    0);

    ret = xmlRelaxNGValidateDoc(validctxt, doc);
    if (ret == 0)
    {
        elog(INFO, "Validates");
        result = true;
    } else if (ret > 0)
    {
        elog(INFO, "Dont validates");
        result = false;
    } else
    {
        elog(INFO, "Validation generated an internal error");
        result = false;
    }

    xmlRelaxNGFree(schema);
    xmlRelaxNGFreeValidCtxt(validctxt);

    xmlFreeDoc(doc);    // clean up document in memmory
    xmlCleanupParser(); // clean up stream parser

	PG_RETURN_BOOL (result);
#else
    NO_XML_SUPPORT();
    PG_RETURN_BOOL (false);
#endif
}
Пример #28
0
/* ----------
 * conv_proc(
 *		INTEGER,	-- source encoding id
 *		INTEGER,	-- destination encoding id
 *		CSTRING,	-- source string (null terminated C string)
 *		CSTRING,	-- destination string (null terminated C string)
 *		INTEGER		-- source string length
 * ) returns VOID;
 * ----------
 */
Datum
sjis_eudc_to_utf8(PG_FUNCTION_ARGS)
{
	unsigned char *src = (unsigned char *) PG_GETARG_CSTRING(2);
	unsigned char *dest = (unsigned char *) PG_GETARG_CSTRING(3);
	unsigned char *p;
	unsigned char *fallback_character = NULL;
	int			len = PG_GETARG_INT32(4);
	int			sjis_len;
	int			clen;

	CHECK_ENCODING_CONVERSION_ARGS(PG_SJIS, PG_UTF8);

	if (sjis_to_utf8 == NULL)
		sjis_to_utf8 = load_external_function(
			"utf8_and_sjis", "sjis_to_utf8", true, NULL);

	*dest = '\0';
	p = src;
	sjis_len = 0;
	for (; len > 0; len -= clen)
	{
		const unsigned char *c = p + sjis_len;

		if (c[0] == '\0')
			report_invalid_encoding(PG_SJIS, (const char *) p + sjis_len, len);

		if (c[0] >= 0xf0 && c[0] <= 0xf9 && len >= 2 && ISSJISTAIL(c[1]))
		{
			int	ucs;
			int	m;
			int	n;

			clen = 2;

			/* SJIS to UTF8 */
			if (sjis_len > 0)
			{
				DirectFunctionCall5(sjis_to_utf8, PG_SJIS, PG_UTF8,
									CStringGetDatum(p), CStringGetDatum(dest),
									sjis_len);
				dest = dest + strlen((char *) dest);
				p += sjis_len;
				sjis_len = 0;
			}
			p += clen;

			elog(eudc_log_level,
				"eudc character found: %02x%02x in SJIS to UTF8 conversion",
				c[0], c[1]);

			/* SJIS EUDC to UTF8 */
			if (eudc_fallback_character && eudc_fallback_character[0])
			{
				/* map to fallback character */
				int		i;

				if (fallback_character == NULL)
				{
					fallback_character = pg_do_encoding_conversion(
						(unsigned char *) eudc_fallback_character,
						strlen(eudc_fallback_character),
						GetDatabaseEncoding(),
						PG_UTF8);
				}

				for (i = 0; fallback_character[i]; i++)
					*dest++ = fallback_character[i];
			}
			else
			{
				/* linear mapping */
				n = c[0] - 0xf0;
				m = c[1] - 0x40;

				if (m >= 0x40)
					m--;

				ucs = 0xe000 + n * 188 + m;

				*dest++ = (ucs >> 12) | 0xe0;
				*dest++ = (ucs & 0x0fc0) >> 6 | 0x80;
				*dest++ = (ucs & 0x003f) | 0x80;
			}
			*dest = '\0';
		}
		else
		{