Пример #1
0
bool
PMDHandler::doLoad(Model& model, istream& stream) noexcept
{
	PMD _pmd;
	if (!stream.read((char*)&_pmd.Header, sizeof(_pmd.Header))) return false;

	// vertex
	if (!stream.read((char*)&_pmd.VertexCount, sizeof(_pmd.VertexCount))) return false;

	if (_pmd.VertexCount > 0)
	{
		_pmd.VertexList.resize(_pmd.VertexCount);

		if (!stream.read((char*)&_pmd.VertexList[0], (std::streamsize)(sizeof(PMD_Vertex)* _pmd.VertexCount))) return false;
	}

	// index
	if (!stream.read((char*)&_pmd.IndexCount, sizeof(_pmd.IndexCount))) return false;

	if (_pmd.IndexCount > 0)
	{
		_pmd.IndexList.resize(_pmd.IndexCount);

		if (!stream.read((char*)&_pmd.IndexList[0], (std::streamsize)(sizeof(PMD_Index)* _pmd.IndexCount))) return false;
	}

	// materal
	if (!stream.read((char*)&_pmd.MaterialCount, sizeof(_pmd.MaterialCount))) return false;

	if (_pmd.MaterialCount > 0)
	{
		_pmd.MaterialList.resize(_pmd.MaterialCount);

		if (!stream.read((char*)&_pmd.MaterialList[0], (std::streamsize)(sizeof(PMD_Material)* _pmd.MaterialCount))) return false;
	}

	// bone
	if (!stream.read((char*)&_pmd.BoneCount, sizeof(_pmd.BoneCount))) return false;

	if (_pmd.BoneCount > 0)
	{
		_pmd.BoneList.resize(_pmd.BoneCount);

		if (!stream.read((char*)&_pmd.BoneList[0], (std::streamsize)(sizeof(PMD_Bone)* _pmd.BoneCount))) return false;
	}

	// IK
	if (!stream.read((char*)&_pmd.IkCount, sizeof(_pmd.IkCount))) return false;

	if (_pmd.IkCount > 0)
	{
		_pmd.IkList.resize(_pmd.IkCount);

		for (std::size_t i = 0; i < (std::size_t)_pmd.IkCount; i++)
		{
			if (!stream.read((char*)&_pmd.IkList[i].IK, sizeof(_pmd.IkList[i].IK))) return false;
			if (!stream.read((char*)&_pmd.IkList[i].Target, sizeof(_pmd.IkList[i].Target))) return false;
			if (!stream.read((char*)&_pmd.IkList[i].LinkCount, sizeof(_pmd.IkList[i].LinkCount))) return false;
			if (!stream.read((char*)&_pmd.IkList[i].LoopCount, sizeof(_pmd.IkList[i].LoopCount))) return false;
			if (!stream.read((char*)&_pmd.IkList[i].LimitOnce, sizeof(_pmd.IkList[i].LimitOnce))) return false;

			_pmd.IkList[i].LinkList.resize(_pmd.IkList[i].LinkCount);

			if (!stream.read((char*)&_pmd.IkList[i].LinkList[0], (std::streamsize)(sizeof(PMD_Link)* _pmd.IkList[i].LinkCount))) return false;
		}
	}

	// Morph
	if (!stream.read((char*)&_pmd.MorphCount, sizeof(_pmd.MorphCount))) return false;

	if (_pmd.MorphCount > 0)
	{
		_pmd.MorphList.resize(_pmd.MorphCount);

		for (std::size_t i = 0; i < (std::size_t)_pmd.MorphCount; i++)
		{
			if (!stream.read((char*)&_pmd.MorphList[i].Name, sizeof(_pmd.MorphList[i].Name))) return false;
			if (!stream.read((char*)&_pmd.MorphList[i].VertexCount, sizeof(_pmd.MorphList[i].VertexCount))) return false;
			if (!stream.read((char*)&_pmd.MorphList[i].Category, sizeof(_pmd.MorphList[i].Category))) return false;

			if (_pmd.MorphList[i].VertexCount > 0)
			{
				_pmd.MorphList[i].VertexList.resize(_pmd.MorphList[i].VertexCount);

				if (!stream.read((char*)&_pmd.MorphList[i].VertexList[0], (std::streamsize)(sizeof(PMD_MorphVertex)* _pmd.MorphList[i].VertexCount))) return false;
			}
		}
	}

	// frame window
	if (!stream.read((char*)&_pmd.FrameWindow.ExpressionListCount, sizeof(_pmd.FrameWindow.ExpressionListCount))) return false;

	if (_pmd.FrameWindow.ExpressionListCount > 0)
	{
		_pmd.FrameWindow.ExpressionList.resize(_pmd.FrameWindow.ExpressionListCount);

		if (!stream.read((char*)&_pmd.FrameWindow.ExpressionList[0], (std::streamsize)(sizeof(PMD_Expression)* _pmd.FrameWindow.ExpressionListCount))) return false;
	}

	if (!stream.read((char*)&_pmd.FrameWindow.NodeNameCount, sizeof(_pmd.FrameWindow.NodeNameCount))) return false;

	if (_pmd.FrameWindow.NodeNameCount > 0)
	{
		_pmd.FrameWindow.NodeNameList.resize(_pmd.FrameWindow.NodeNameCount);

		if (!stream.read((char*)&_pmd.FrameWindow.NodeNameList[0].Name, (std::streamsize)(sizeof(PMD_NodeName)* _pmd.FrameWindow.NodeNameCount))) return false;
	}

	if (!stream.read((char*)&_pmd.FrameWindow.BoneToNodeCount, sizeof(_pmd.FrameWindow.BoneToNodeCount))) return false;

	if (_pmd.FrameWindow.BoneToNodeCount > 0)
	{
		_pmd.FrameWindow.BoneToNodeList.resize(_pmd.FrameWindow.BoneToNodeCount);

		if (!stream.read((char*)&_pmd.FrameWindow.BoneToNodeList[0].Bone, (std::streamsize)(sizeof(PMD_BoneToNode)* _pmd.FrameWindow.BoneToNodeCount))) return false;
	}

	// description
	if (!stream.read((char*)&_pmd.HasDescription, sizeof(_pmd.HasDescription))) return false;

	if (_pmd.HasDescription)
	{
		if (!stream.read((char*)&_pmd.Description.ModelName, sizeof(_pmd.Description.ModelName))) return false;

		if (!stream.read((char*)&_pmd.Description.Comment, sizeof(_pmd.Description.Comment))) return false;

		for (PMD_BoneCount i = 0; i < _pmd.BoneCount; i++)
		{
			PMD_BoneName name;

			if (!stream.read((char*)&name.Name, sizeof(name))) return false;

			_pmd.Description.BoneName.push_back(name);
		}

		for (PMD_uint8_t i = 0; i < _pmd.FrameWindow.ExpressionListCount; i++)
		{
			PMD_MorphName name;

			if (!stream.read((char*)&name.Name, sizeof(name))) return false;

			_pmd.Description.FaceName.push_back(name);
		}

		for (PMD_uint8_t i = 0; i < _pmd.FrameWindow.NodeNameCount; i++)
		{
			PMD_NodeName name;

			if (!stream.read((char*)&name.Name, sizeof(name))) return false;

			_pmd.Description.FrameName.push_back(name);
		}
	}

	// toon
	_pmd.ToonCount = PMD_NUM_TOON;

	_pmd.ToonList.resize(_pmd.ToonCount);

	if (!stream.read((char*)&_pmd.ToonList[0].Name, (std::streamsize)(sizeof(PMD_Toon) * _pmd.ToonCount))) return false;

	// rigidbody
	if (!stream.read((char*)&_pmd.BodyCount, sizeof(_pmd.BodyCount))) return false;

	if (_pmd.BodyCount > 0)
	{
		_pmd.BodyList.resize(_pmd.BodyCount);

		if (!stream.read((char*)&_pmd.BodyList[0], (std::streamsize)(sizeof(PMD_Body)* _pmd.BodyCount))) return false;
	}

	// joint
	if (!stream.read((char*)&_pmd.JointCount, sizeof(_pmd.JointCount))) return false;

	if (_pmd.JointCount > 0)
	{
		_pmd.JointList.resize(_pmd.JointCount);

		if (!stream.read((char*)&_pmd.JointList[0], (std::streamsize)(sizeof(PMD_Body)* _pmd.JointCount))) return false;
	}

	for (std::size_t index = 0; index < _pmd.MaterialList.size(); index++)
	{
		auto& it = _pmd.MaterialList[index];

		auto material = std::make_shared<MaterialProperty>();
		material->set(MATKEY_COLOR_DIFFUSE, it.Diffuse);
		material->set(MATKEY_COLOR_AMBIENT, it.Ambient);
		material->set(MATKEY_COLOR_SPECULAR, it.Specular);
		material->set(MATKEY_OPACITY, it.Opacity);
		material->set(MATKEY_SHININESS, it.Shininess);

		std::string name = it.TextureName;
		std::string::size_type substr = name.find_first_of("*");
		if (substr != std::string::npos)
		{
			name.erase(name.begin() + substr, name.end());
		}

		material->set(MATKEY_TEXTURE_DIFFUSE(0), name);
		material->set(MATKEY_TEXTURE_AMBIENT(0), name);

		model.addMaterial(material);
	}

	PMD_Index* indices = _pmd.IndexList.data();
	PMD_Vertex* vertices = _pmd.VertexList.data();

	MeshPropertyPtr root = std::make_shared<MeshProperty>();
	MeshPropertyPtr mesh = root;
	MeshPropertyPtr last = nullptr;

	for (std::size_t index = 0; index < _pmd.MaterialList.size(); index++)
	{
		auto& it = _pmd.MaterialList[index];

		Vector3Array points;
		Vector3Array normals;
		Vector2Array texcoords;
		VertexWeights weights;
		UintArray faces;

		for (PMD_IndexCount i = 0; i < it.FaceVertexCount; i++, indices++)
		{
			PMD_Vertex& v = vertices[*indices];

			points.push_back(v.Position);
			normals.push_back(v.Normal);
			texcoords.push_back(v.UV);
			faces.push_back(i);

			VertexWeight weight;
			weight.weight1 = v.Weight / 100.0;
			weight.weight2 = 1.0 - weight.weight1;
			weight.weight3 = 0.0f;
			weight.weight4 = 0.0f;
			weight.bone1 = v.Bone.Bone1;
			weight.bone2 = v.Bone.Bone2;
			weight.bone3 = 0;
			weight.bone4 = 0;

			weights.push_back(weight);
		}

		if (last == mesh)
		{
			mesh = std::make_shared<MeshProperty>();
			root->addChild(mesh);
		}

		mesh->setMaterialID(index);
		mesh->setVertexArray(points);
		mesh->setNormalArray(normals);
		mesh->setTexcoordArray(texcoords);
		mesh->setWeightArray(weights);
		mesh->setFaceArray(faces);

		last = mesh;
	}


	if (_pmd.BoneCount > 0)
	{
		Bones bones;
		InverseKinematics iks;

		for (auto& it : _pmd.BoneList)
		{
			Bone bone;

			char inbuf[MAX_PATH + 1] = { 0 };
			char outbuf[MAX_PATH + 1] = { 0 };
			char *in = inbuf;
			char *out = outbuf;
			std::size_t in_size = (size_t)MAX_PATH;
			std::size_t out_size = (size_t)MAX_PATH;

			memcpy(in, it.Name.Name, sizeof(it.Name.Name));

			iconv_t ic = iconv_open("GBK", "SJIS");
			iconv(ic, &in, &in_size, &out, &out_size);
			iconv_close(ic);

			bone.setName(std::string(outbuf));
			bone.setPosition(it.Position);
			bone.setParent(it.Parent);
			bone.setChild(it.Child);

			bones.push_back(bone);
		}

		for (auto& it : _pmd.IkList)
		{
			IKAttr attr;
			attr.IKBoneIndex = it.IK;
			attr.IKTargetBoneIndex = it.Target;
			attr.IKLimitedRadian = it.LimitOnce;
			attr.IKLinkCount = it.LinkCount;
			attr.IKLoopCount = it.LoopCount;
			for (auto& bone : it.LinkList)
			{
				IKChild child;
				child.BoneIndex = bone;
				child.MinimumRadian = Vector3::Zero;
				child.MaximumRadian = Vector3(3.14, 3.14, 3.14);
				child.RotateLimited = 1;

				attr.IKList.push_back(child);
			}

			iks.push_back(attr);
		}

		root->setInverseKinematics(iks);
		root->setBoneArray(bones);
	}

	model.addMesh(root);

	return true;
}
Пример #2
0
int main(int argC,char **argV)
{
	ros::init(argC,argV,"startBody");
	ros::NodeHandle n;
	std::string serverAddress;
	n.getParam("/serverNameOrIP",serverAddress);
	Socket mySocket(serverAddress.c_str(),"9003",streamSize);
	iconv_t charConverter = iconv_open("UTF-8","UTF-16");
	ros::Publisher bodyPub = n.advertise<k2_client::BodyArray>(topicName,1);
	char jsonCharArray[readSkipSize];
	while(ros::ok())
	{
		mySocket.readData();
		char *jsonCharArrayPtr;
		char *socketCharArrayPtr;
		jsonCharArrayPtr = jsonCharArray;
		socketCharArrayPtr = mySocket.mBuffer;
		iconv(charConverter,&socketCharArrayPtr,&readSkipSize,&jsonCharArrayPtr,&stringSize);
		double utcTime;
		memcpy(&utcTime,&mySocket.mBuffer[readSkipSize],sizeof(double));
		std::string jsonString(jsonCharArray);
		//std::cout<<jsonCharArray<<std::endl<<"***"<<std::endl;
		Json::Value jsonObject;
		Json::Reader jsonReader;
		bool parsingSuccessful = jsonReader.parse(jsonString,jsonObject,false);
		if(!parsingSuccessful)
		{
			std::cout<<"Failure to parse: "<<parsingSuccessful<<std::endl;
			continue;
		}
		k2_client::BodyArray bodyArray;
		try
		{
			for(int i=0;i<6;i++)
			{
				k2_client::Body body;
				body.header.stamp = ros::Time(utcTime);
				body.header.frame_id =  ros::this_node::getNamespace() + "/rgb";
				body.leanTrackingState = jsonObject[i]["LeanTrackingState"].asInt();
				body.lean.leanX = jsonObject[i]["Lean"]["X"].asDouble();
				body.lean.leanY = jsonObject[i]["Lean"]["Y"].asDouble();
				body.isTracked = jsonObject[i]["IsTracked"].asBool();
				body.trackingId = jsonObject[i]["TrackingId"].asUInt64();
				body.clippedEdges = jsonObject[i]["ClippedEdges"].asInt();
				body.engaged = jsonObject[i]["Engaged"].asBool();
				body.handRightConfidence = jsonObject[i]["HandRightConfidence"].asInt();
				body.handRightState = jsonObject[i]["HandRightState"].asInt();
				body.handLeftConfidence = jsonObject[i]["HandLeftConfidence"].asInt();
				body.handLeftState = jsonObject[i]["HandLeftState"].asInt();
				body.appearance.wearingGlasses = jsonObject[i]["Appearance"]["WearingGlasses"].asBool();
				body.activities.eyeLeftClosed = jsonObject[i]["Activities"]["EyeLeftClosed"].asBool();
				body.activities.eyeRightClosed = jsonObject[i]["Activities"]["EyeRightClosed"].asBool();
				body.activities.mouthOpen = jsonObject[i]["Activities"]["MouthOpen"].asBool();
				body.activities.mouthMoved = jsonObject[i]["Activities"]["MouthMoved"].asBool();
				body.activities.lookingAway = jsonObject[i]["Activities"]["LookingAway"].asBool();
				body.expressions.neutral = jsonObject[i]["Expressions"]["Neutral"].asBool();
				body.expressions.neutral = jsonObject[i]["Expressions"]["Happy"].asBool();
				for(int j=0;j<25;j++)
				{
					k2_client::JointOrientationAndType JOAT;
					k2_client::JointPositionAndState JPAS;
					std::string fieldName;
					switch (j)
					{
						case 0: fieldName = "SpineBase";break;
						case 1: fieldName = "SpineMid";break;
						case 2: fieldName = "Neck";break;
						case 3: fieldName = "Head";break;
						case 4: fieldName = "ShoulderLeft";break;
						case 5: fieldName = "ElbowLeft";break;
						case 6: fieldName = "WristLeft";break;
						case 7: fieldName = "HandLeft";break;
						case 8: fieldName = "ShoulderRight";break;
						case 9: fieldName = "ElbowRight";break;
						case 10: fieldName = "WristRight";break;
						case 11: fieldName = "HandRight";break;
						case 12: fieldName = "HipLeft";break;
						case 13: fieldName = "KneeLeft";break;
						case 14: fieldName = "AnkleLeft";break;
						case 15: fieldName = "SpineBase";break;
						case 16: fieldName = "HipRight";break;
						case 17: fieldName = "KneeRight";break;
						case 18: fieldName = "AnkleRight";break;
						case 19: fieldName = "FootRight";break;
						case 20: fieldName = "SpineShoulder";break;
						case 21: fieldName = "HandTipLeft";break;
						case 22: fieldName = "ThumbLeft";break;
						case 23: fieldName = "HandTipRight";break;
						case 24: fieldName = "ThumbRight";break;
					}
					
					JOAT.orientation.x = jsonObject[i][fieldName]["Orientation"]["X"].asDouble();
					JOAT.orientation.y = jsonObject[i][fieldName]["Orientation"]["Y"].asDouble();
					JOAT.orientation.z = jsonObject[i][fieldName]["Orientation"]["Z"].asDouble();
					JOAT.orientation.w = jsonObject[i][fieldName]["Orientation"]["W"].asDouble();
					JOAT.jointType = jsonObject[i][fieldName]["JointType"].asInt();

					JPAS.trackingState = jsonObject[i][fieldName]["TrackingState"].asBool();
					JPAS.position.x = jsonObject[i][fieldName]["Position"]["X"].asDouble();
					JPAS.position.y = jsonObject[i][fieldName]["Position"]["Y"].asDouble();
					JPAS.position.z = jsonObject[i][fieldName]["Position"]["Z"].asDouble();
					JPAS.jointType = jsonObject[i][fieldName]["JointType"].asInt();
					
					body.jointOrientations.push_back(JOAT);
					body.jointPositions.push_back(JPAS);
				}
				bodyArray.bodies.push_back(body);
			}
		}
		catch (...)
		{
			std::cout<<"An exception occured"<<std::endl;
			continue;
		}
		bodyPub.publish(bodyArray);
	}
	return 0;
}
Пример #3
0
iconv_t QIconvCodec::createIconv_t(const char *to, const char *from)
{
    Q_ASSERT((to == 0 && from != 0) || (to != 0 && from == 0));

    iconv_t cd = (iconv_t) -1;
#if defined(__GLIBC__) || defined(GNU_LIBICONV) || defined(Q_OS_QNX)
#if defined(Q_OS_QNX)
    // on QNX the default locale is UTF-8, and an empty string will cause iconv_open to fail
    static const char empty_codeset[] = "UTF-8";
#else
    // both GLIBC and libgnuiconv will use the locale's encoding if from or to is an empty string
    static const char empty_codeset[] = "";
#endif
    const char *codeset = empty_codeset;
    cd = iconv_open(to ? to : codeset, from ? from : codeset);
#else
    char *codeset = 0;
#endif

#if defined(_XOPEN_UNIX) && !defined(Q_OS_QNX) && !defined(Q_OS_OSF)
    if (cd == (iconv_t) -1) {
        codeset = nl_langinfo(CODESET);
        if (codeset)
            cd = iconv_open(to ? to : codeset, from ? from : codeset);
    }
#endif

    if (cd == (iconv_t) -1) {
        // Very poorly defined and followed standards causes lots of
        // code to try to get all the cases... This logic is
        // duplicated in QTextCodec, so if you change it here, change
        // it there too.

        // Try to determine locale codeset from locale name assigned to
        // LC_CTYPE category.

        // First part is getting that locale name.  First try setlocale() which
        // definitely knows it, but since we cannot fully trust it, get ready
        // to fall back to environment variables.
        char * ctype = qstrdup(setlocale(LC_CTYPE, 0));

        // Get the first nonempty value from $LC_ALL, $LC_CTYPE, and $LANG
        // environment variables.
        char * lang = qstrdup(qgetenv("LC_ALL").constData());
        if (!lang || lang[0] == 0 || strcmp(lang, "C") == 0) {
            if (lang) delete [] lang;
            lang = qstrdup(qgetenv("LC_CTYPE").constData());
        }
        if (!lang || lang[0] == 0 || strcmp(lang, "C") == 0) {
            if (lang) delete [] lang;
            lang = qstrdup(qgetenv("LANG").constData());
        }

        // Now try these in order:
        // 1. CODESET from ctype if it contains a .CODESET part (e.g. en_US.ISO8859-15)
        // 2. CODESET from lang if it contains a .CODESET part
        // 3. ctype (maybe the locale is named "ISO-8859-1" or something)
        // 4. locale (ditto)
        // 5. check for "@euro"

        // 1. CODESET from ctype if it contains a .CODESET part (e.g. en_US.ISO8859-15)
        codeset = ctype ? strchr(ctype, '.') : 0;
        if (codeset && *codeset == '.') {
            ++codeset;
            cd = iconv_open(to ? to : codeset, from ? from : codeset);
        }

        // 2. CODESET from lang if it contains a .CODESET part
        codeset = lang ? strchr(lang, '.') : 0;
        if (cd == (iconv_t) -1 && codeset && *codeset == '.') {
            ++codeset;
            cd = iconv_open(to ? to : codeset, from ? from : codeset);
        }

        // 3. ctype (maybe the locale is named "ISO-8859-1" or something)
        if (cd == (iconv_t) -1 && ctype && *ctype != 0 && strcmp (ctype, "C") != 0)
            cd = iconv_open(to ? to : ctype, from ? from : ctype);


        // 4. locale (ditto)
        if (cd == (iconv_t) -1 && lang && *lang != 0)
            cd = iconv_open(to ? to : lang, from ? from : lang);

        // 5. "@euro"
        if ((cd == (iconv_t) -1 && ctype && strstr(ctype, "@euro")) || (lang && strstr(lang, "@euro")))
            cd = iconv_open(to ? to : "ISO8859-15", from ? from : "ISO8859-15");

        delete [] ctype;
        delete [] lang;
    }

    return cd;
}
Пример #4
0
/* This function returns a newly allocated wide string containing the USB
   device string numbered by the index. The returned string must be freed
   by using free(). */
static wchar_t *get_usb_string(libusb_device_handle *dev, uint8_t idx)
{
	char buf[512];
	int len;
	wchar_t *str = NULL;

#ifndef __ANDROID__ /* we don't use iconv on Android */
	wchar_t wbuf[256];
	/* iconv variables */
	iconv_t ic;
	size_t inbytes;
	size_t outbytes;
	size_t res;
#ifdef __FreeBSD__
	const char *inptr;
#else
	char *inptr;
#endif
	char *outptr;
#endif

	/* Determine which language to use. */
	uint16_t lang;
	lang = get_usb_code_for_current_locale();
	if (!is_language_supported(dev, lang))
		lang = get_first_language(dev);

	/* Get the string from libusb. */
	len = libusb_get_string_descriptor(dev,
			idx,
			lang,
			(unsigned char*)buf,
			sizeof(buf));
	if (len < 0)
		return NULL;

#ifdef __ANDROID__

	/* Bionic does not have iconv support nor wcsdup() function, so it
	   has to be done manually.  The following code will only work for
	   code points that can be represented as a single UTF-16 character,
	   and will incorrectly convert any code points which require more
	   than one UTF-16 character.

	   Skip over the first character (2-bytes).  */
	len -= 2;
	str = malloc((len / 2 + 1) * sizeof(wchar_t));
	int i;
	for (i = 0; i < len / 2; i++) {
		str[i] = buf[i * 2 + 2] | (buf[i * 2 + 3] << 8);
	}
	str[len / 2] = 0x00000000;

#else

	/* buf does not need to be explicitly NULL-terminated because
	   it is only passed into iconv() which does not need it. */

	/* Initialize iconv. */
	ic = iconv_open("WCHAR_T", "UTF-16LE");
	if (ic == (iconv_t)-1) {
		LOG("iconv_open() failed\n");
		return NULL;
	}

	/* Convert to native wchar_t (UTF-32 on glibc/BSD systems).
	   Skip the first character (2-bytes). */
	inptr = buf+2;
	inbytes = len-2;
	outptr = (char*) wbuf;
	outbytes = sizeof(wbuf);
	res = iconv(ic, (char**)&inptr, &inbytes, &outptr, &outbytes);
	if (res == (size_t)-1) {
		LOG("iconv() failed\n");
		goto err;
	}

	/* Write the terminating NULL. */
	wbuf[sizeof(wbuf)/sizeof(wbuf[0])-1] = 0x00000000;
	if (outbytes >= sizeof(wbuf[0]))
		*((wchar_t*)outptr) = 0x00000000;

	/* Allocate and copy the string. */
	str = wcsdup(wbuf);

err:
	iconv_close(ic);

#endif

	return str;
}
Пример #5
0
void FontAtlas::conversionU16TOGB2312(const std::u16string& newChars, std::unordered_map<unsigned short, unsigned short>& newCharsMap)
{
    size_t strLen = newChars.length();
    auto gb2312StrSize = strLen * 2;
    auto gb2312Text = new (std::nothrow) char[gb2312StrSize];
    memset(gb2312Text, 0, gb2312StrSize);

    switch (_fontFreeType->getEncoding())
    {
    case FT_ENCODING_GB2312:
    {
#if CC_TARGET_PLATFORM == CC_PLATFORM_WIN32 || CC_TARGET_PLATFORM == CC_PLATFORM_WINRT
        WideCharToMultiByte(936, NULL, (LPCWCH)newChars.c_str(), strLen, (LPSTR)gb2312Text, gb2312StrSize, NULL, NULL);
#elif CC_TARGET_PLATFORM == CC_PLATFORM_ANDROID
        conversionEncodingJNI((char*)newChars.c_str(), gb2312StrSize, "UTF-16LE", gb2312Text, "GB2312");
#else
        if (_iconv == nullptr)
        {
            _iconv = iconv_open("gb2312", "utf-16le");
        }

        if (_iconv == (iconv_t)-1)
        {
            CCLOG("conversion from utf16 to gb2312 not available");
        }
        else
        {
            char* pin = (char*)newChars.c_str();
            char* pout = gb2312Text;
            size_t inLen = strLen * 2;
            size_t outLen = gb2312StrSize;

            iconv(_iconv, (char**)&pin, &inLen, &pout, &outLen);
        }
#endif
    }
        break;
    default:
        CCLOG("Unsupported encoding:%d", _fontFreeType->getEncoding());
        break;
    }

    unsigned short gb2312Code = 0;
    unsigned char* dst = (unsigned char*)&gb2312Code;
    unsigned short u16Code;
    for (size_t index = 0, gbIndex = 0; index < strLen; ++index)
    {
        u16Code = newChars[index];
        if (u16Code < 256)
        {
            newCharsMap[u16Code] = u16Code;
            gbIndex += 1;
        }
        else
        {
            dst[0] = gb2312Text[gbIndex + 1];
            dst[1] = gb2312Text[gbIndex];
            newCharsMap[u16Code] = gb2312Code;

            gbIndex += 2;
        }
    }

    delete [] gb2312Text;
}
Пример #6
0
static int iconv_erl_control(ErlDrvData drv_data,
			     unsigned int command,
			     char *buf, int len,
			     char **rbuf, int rlen)
{
   int i;
   int size;
   int index = 0;
   int avail;
   size_t inleft, outleft;
   ErlDrvBinary *b;
   char *from, *to, *string, *stmp, *rstring, *rtmp;
   iconv_t cd;
   int error = 0;

   ei_decode_version(buf, &index, &i);
   ei_decode_tuple_header(buf, &index, &i);
   ei_get_type(buf, &index, &i, &size);
   from = malloc(size + 1); 
   ei_decode_string(buf, &index, from);

   ei_get_type(buf, &index, &i, &size);
   to = malloc(size + 1); 
   ei_decode_string(buf, &index, to);
  
   ei_get_type(buf, &index, &i, &size);
   stmp = string = malloc(size + 1); 
   ei_decode_string(buf, &index, string);

   cd = iconv_open(to, from);

   if (cd == (iconv_t) -1) {
      cd = iconv_open("ascii", "ascii");
      if (cd == (iconv_t) -1) {
	 *rbuf = (char*)(b = driver_alloc_binary(size));
	 memcpy(b->orig_bytes, string, size);

	 free(from);
	 free(to);
	 free(string);

	 return size;
      }
   }
   
   outleft = avail = 4*size;
   inleft = size;
   rtmp = rstring = malloc(avail);
   while (inleft > 0) {
      if (iconv(cd, &stmp, &inleft, &rtmp, &outleft) == (size_t) -1)
      {
          error = 1;
          break;
      }
   }
   
   size = error ? 0 : rtmp - rstring;

   *rbuf = (char*)(b = driver_alloc_binary(size));
   memcpy(b->orig_bytes, rstring, size);

   free(from);
   free(to);
   free(string);
   free(rstring);
   iconv_close(cd);
   
   return size;
}
Пример #7
0
	//------------------------------------------------------------------------------
	int IGUIStringConv_iconv::Utf8ToWChar( const CGUIString& rSrc, CGUIStringW& rDst )
	{
		if( rSrc.empty())
		{
			rDst.clear();
			return 0;
		}

		//open iconv
		iconv_t cd = iconv_open ("UTF-16LE", "UTF-8");
		if( cd == (iconv_t)-1 )
		{
			throw CGUIException(
				"[MultiByteToWideChar]: failed to open iconv, errno is %d",
				errno);
			return -1;
		}

		//convert
		size_t	buf_size = rSrc.size()+1;
		size_t	inbytesleft = rSrc.size();
		size_t	outbytesleft = buf_size;
		char*	dst = (char*)(new wchar[buf_size]);
		char*	pOutBuf = NULL;
		char*	pInBuf = (char*)(rSrc.c_str());

		bool	bError = false;

		while(inbytesleft > 0) 
		{
			pOutBuf = dst;
			outbytesleft = buf_size*sizeof(wchar);

			size_t retbytes = iconv(cd, &pInBuf, &inbytesleft, &pOutBuf, &outbytesleft);

			if (dst != pOutBuf)  
			{
				// wchar is 4byte in mac, but iconv return a "utf-16" buff which is 2byte per code
				if (sizeof(wchar) == 4) 
				{
					for (int iChar = 0; iChar < (pOutBuf-dst)/2; iChar++)
					{
						unsigned short* pU16Char = (unsigned short*)&dst[2*iChar];
						rDst.push_back((wchar)*pU16Char);
					}
				}
				else if (sizeof(wchar) == 2) 
				{
					rDst.append((wchar*)dst, (pOutBuf-dst)/sizeof(wchar));
				}
			} 

			//check ret
			if( retbytes == size_t(-1) )
			{
				if( errno == E2BIG )
				{
					continue;
				}
				else
				{
					bError = true;
					break;
				}
			}
			else
			{
				//success
				break;
			}
		}

		delete[] dst;
		if( bError)
		{
			switch(errno)
			{
			case EILSEQ:
				throw CGUIException(
					"[MultiByteToWideChar]: failed to iconv, errno is EILSEQ");
				return -1;
			case EINVAL:
				throw CGUIException(
					"[MultiByteToWideChar]: failed to iconv, errno is EINVAL");
				return -1;
			default:
				throw CGUIException(
					"[MultiByteToWideChar]: failed to iconv, errno is %d",
					errno);
				return -1;
			}
		}

		//close iconv
		int ret = iconv_close(cd);
		if( ret == -1 )
		{
			throw CGUIException(
				"[MultiByteToWideChar]: failed to close iconv, errno is %d",
				errno);
			return -1;
		}

		return 0;
	}
Пример #8
0
int benthos_dc_manifest_parse(plugin_manifest_t * ptr, const char * path)
{
	int rv;
	struct plugin_manifest_t_ * manifest;
	struct stat finfo;
	xmlDoc * doc;
	xmlNode * root;
	iconv_t conv;

	if (! ptr || ! path)
		return EINVAL;

	/* Create the Encoding Converter */
	conv = iconv_open("ISO-8859-1", "UTF-8");
	if (conv == (iconv_t)(-1))
		return errno;

	/* Create the Manifest Object */
	manifest = new struct plugin_manifest_t_;
	if (! manifest)
	{
		iconv_close(conv);
		return ENOMEM;
	}

	/* Check that the File Exists */
	rv = stat(path, & finfo);
	if (rv != 0)
	{
		delete manifest;
		iconv_close(conv);
		return errno;
	}

	if (! S_ISREG(finfo.st_mode))
	{
		delete manifest;
		iconv_close(conv);
		return ENOENT;
	}

	/* Load the Manifest File */
	doc = xmlReadFile(path, 0, 0);
	if (doc == NULL)
	{
		delete manifest;
		xmlCleanupParser();
		iconv_close(conv);
		return MANFIEST_ERR_MALFORMED;
	}

	/* Load the Root Node */
	root = xmlDocGetRootElement(doc);
	if ((root == NULL) || (root->type != XML_ELEMENT_NODE))
	{
		delete manifest;
		xmlFreeDoc(doc);
		xmlCleanupParser();
		iconv_close(conv);
		return MANIFEST_ERR_NOROOT;
	}

	/* Check the Root Node */
	if (xmlStrcmp(root->name, BAD_CAST("plugin")) != 0)
	{
		delete manifest;
		xmlFreeDoc(doc);
		xmlCleanupParser();
		iconv_close(conv);
		return MANIFEST_ERR_NOTPLUGIN;
	}

	/* Parse the Manifest Entry */
	rv = parse_manifest(manifest, root, conv);
	if (rv != 0)
	{
		delete manifest;
		xmlFreeDoc(doc);
		xmlCleanupParser();
		iconv_close(conv);
		return rv;
	}

	/* Set Manifest Pointer */
	(* ptr) = manifest;

	/* Cleanup */
	xmlFreeDoc(doc);
	xmlCleanupParser();
	iconv_close(conv);

	return 0;
}
Пример #9
0
CAMLprim value ml_text_recode_string(value enc_src, value enc_dst, value str)
{
  CAMLparam3(str, enc_src, enc_dst);
  CAMLlocal1(result);

  iconv_t cd = iconv_open(String_val(enc_dst), String_val(enc_src));

  if (cd == (iconv_t)-1)
    caml_failwith("Encoding.recode_string: invalid encoding");

  /* Length of the output buffer. It is initialised to the length of
     the input string, which should be a good
     approximation: */
  size_t len = caml_string_length(str);

  /* Pointer to the beginning of the output buffer. The +1 is for the
     NULL terminating byte. */
  char *dst_buffer = malloc(len + 1);

  if (dst_buffer == NULL)
    caml_failwith("Encoding.recode_string: out of memory");

  /* iconv arguments */
  char *src_bytes = String_val(str);
  char *dst_bytes = dst_buffer;
  size_t src_remaining = len;
  size_t dst_remaining = len;

  while (src_remaining) {
    size_t count = iconv (cd, &src_bytes, &src_remaining, &dst_bytes, &dst_remaining);

    if (count == (size_t) -1) {
      switch (errno) {
      case EILSEQ:
        free(dst_buffer);
        iconv_close(cd);
        caml_failwith("Encoding.recode_string: invalid multibyte sequence found in the input");

      case EINVAL:
        free(dst_buffer);
        iconv_close(cd);
        caml_failwith("Encoding.recode_string: incomplete multibyte sequence found in the input");

      case E2BIG: {
        /* Ouput offest relative to the beginning of the destination
           buffer: */
        size_t offset = dst_bytes - dst_buffer;

        /* Try with a buffer 2 times bigger: */
        len *= 2;
        dst_buffer = realloc(dst_buffer, len + 1);
        if (dst_buffer == NULL)
          caml_failwith("Encoding.recode_string: out of memory");

        dst_bytes = dst_buffer + offset;
        dst_remaining += len;
        break;
      }

      default:
        free(dst_buffer);
        iconv_close(cd);
        caml_failwith("Encoding.recode_string: unknown error");
      }
    }
  };

  *dst_bytes = 0;
  result = caml_alloc_string(dst_bytes - dst_buffer);
  memcpy(String_val(result), dst_buffer, dst_bytes - dst_buffer);

  /* Clean-up */
  free(dst_buffer);
  iconv_close(cd);

  CAMLreturn(result);
}
Пример #10
0
int
conv_enc (SCR *sp, int option, const char *enc)
{
#if defined(USE_WIDECHAR) && defined(USE_ICONV)
    iconv_t id;
    char2wchar_t    *c2w;
    wchar2char_t    *w2c;

    switch (option) {
    case O_FILEENCODING:
        c2w = &sp->conv.file2int;
        w2c = &sp->conv.int2file;
        break;
    case O_INPUTENCODING:
        c2w = &sp->conv.input2int;
        w2c = NULL;
        break;
    default:
        c2w = NULL;
        w2c = NULL;
        break;
    }

    if (!*enc) {
        if (c2w) *c2w = raw2int;
        if (w2c) *w2c = int2raw;
        return 0;
    }

    if (!strcmp(enc, "WCHAR_T")) {
        if (c2w) *c2w = CHAR_T_char2int;
        if (w2c) *w2c = CHAR_T_int2char;
        return 0;
    }

    id = iconv_open(enc, nl_langinfo(CODESET));
    if (id == (iconv_t)-1)
        goto err;
    iconv_close(id);
    id = iconv_open(nl_langinfo(CODESET), enc);
    if (id == (iconv_t)-1)
        goto err;
    iconv_close(id);

    switch (option) {
    case O_FILEENCODING:
        *c2w = fe_char2int;
        *w2c = fe_int2char;
        break;
    case O_INPUTENCODING:
        *c2w = ie_char2int;
        break;
    }

    F_CLR(sp, SC_CONV_ERROR);
    F_SET(sp, SC_SCR_REFORMAT);

    return 0;
err:
    switch (option) {
    case O_FILEENCODING:
        msgq(sp, M_ERR,
             "321|File encoding conversion not supported");
        break;
    case O_INPUTENCODING:
        msgq(sp, M_ERR,
             "322|Input encoding conversion not supported");
        break;
    }
#endif
    return 1;
}
Пример #11
0
static ErlDrvSSizeT iconv_erl_control(ErlDrvData drv_data,
			     unsigned int command,
			     char *buf, ErlDrvSizeT len,
			     char **rbuf, ErlDrvSizeT rlen)
{
   int i;
   int size;
   int index = 0;
   int avail;
   size_t inleft, outleft;
   ErlDrvBinary *b;
   char *from, *to, *string, *stmp, *rstring, *rtmp;
   iconv_t cd;
   int invalid_utf8_as_latin1 = 0;

   ei_decode_version(buf, &index, &i);
   ei_decode_tuple_header(buf, &index, &i);
   ei_get_type(buf, &index, &i, &size);
   from = driver_alloc(size + 1); 
   ei_decode_string(buf, &index, from);

   ei_get_type(buf, &index, &i, &size);
   to = driver_alloc(size + 1); 
   ei_decode_string(buf, &index, to);
  
   ei_get_type(buf, &index, &i, &size);
   stmp = string = driver_alloc(size + 1); 
   ei_decode_string(buf, &index, string);

   /* Special mode: parse as UTF-8 if possible; otherwise assume it's
      Latin-1.  Makes no difference when encoding. */
   if (strcmp(from, "utf-8+latin-1") == 0) {
      from[5] = '\0';
      invalid_utf8_as_latin1 = 1;
   }
   if (strcmp(to, "utf-8+latin-1") == 0) {
      to[5] = '\0';
   }
   cd = iconv_open(to, from);

   if (cd == (iconv_t) -1) {
      cd = iconv_open("ascii", "ascii");
      if (cd == (iconv_t) -1) {
	 *rbuf = (char*)(b = driver_alloc_binary(size));
	 memcpy(b->orig_bytes, string, size);

	 driver_free(from);
	 driver_free(to);
	 driver_free(string);

	 return size;
      }
   }
   
   outleft = avail = 4*size;
   inleft = size;
   rtmp = rstring = driver_alloc(avail);
   while (inleft > 0) {
      if (iconv(cd, &stmp, &inleft, &rtmp, &outleft) == (size_t) -1) {
	 if (invalid_utf8_as_latin1 && (*stmp & 0x80) && outleft >= 2) {
	    /* Encode one byte of (assumed) Latin-1 into two bytes of UTF-8 */
	    *rtmp++ = 0xc0 | ((*stmp & 0xc0) >> 6);
	    *rtmp++ = 0x80 | (*stmp & 0x3f);
	    outleft -= 2;
	 }
	 stmp++;
	 inleft--;
      }
   }
Пример #12
0
static int
default_int2char(SCR *sp, const CHAR_T * str, ssize_t len, CONVWIN *cw,
                 size_t *tolen, const char **pdst, const char *enc)
{
    size_t i, j;
    int offset = 0;
    char **tostr = (char **)(void *)&cw->bp1;
    size_t  *blen = &cw->blen1;
    mbstate_t mbs;
    size_t n;
    ssize_t  nlen = len + MB_CUR_MAX;
    char *dst;
    size_t buflen;
    char	buffer[CONV_BUFFER_SIZE];
    iconv_t	id = (iconv_t)-1;

    /* convert first len bytes of buffer and append it to cw->bp
     * len is adjusted => 0
     * offset contains the offset in cw->bp and is adjusted
     * cw->bp is grown as required
     */
#ifdef USE_ICONV
#define CONVERT2(len, cw, offset)					\
    do {								\
	const char *bp = buffer;					\
	while (len != 0) {						\
	    size_t outleft = cw->blen1 - offset;			\
	    char *obp = (char *)cw->bp1 + offset;		    	\
	    if (cw->blen1 < offset + MB_CUR_MAX) {		    	\
		nlen += 256;						\
		BINC_RETC(NULL, cw->bp1, cw->blen1, nlen);		\
	    }						    		\
	    errno = 0;						    	\
	    if (iconv(id, &bp, &len, &obp, &outleft) == (size_t)-1 &&	\
		errno != E2BIG) 					\
		    HANDLE_ICONV_ERROR(obp, bp, outleft, len);		\
	    offset = cw->blen1 - outleft;			        \
	}							        \
    } while (0)
#else
#define CONVERT2(len, cw, offset)
#endif


    MEMSET(&mbs, 0, 1);
    BINC_RETC(NULL, *tostr, *blen, nlen);
    dst = *tostr;
    buflen = *blen;

#ifdef USE_ICONV
    if (strcmp(nl_langinfo(CODESET), enc)) {
        id = iconv_open(enc, nl_langinfo(CODESET));
        if (id == (iconv_t)-1)
            goto err;
        dst = buffer;
        buflen = CONV_BUFFER_SIZE;
    }
#endif

    for (i = 0, j = 0; i < (size_t)len; ++i) {
        n = wcrtomb(dst+j, str[i], &mbs);
        if (n == (size_t)-1)
            HANDLE_MBR_ERROR(n, mbs, dst[j], str[i]);
        j += n;
        if (buflen < j + MB_CUR_MAX) {
            if (id != (iconv_t)-1) {
                CONVERT2(j, cw, offset);
            } else {
                nlen += 256;
                BINC_RETC(NULL, *tostr, *blen, nlen);
                dst = *tostr;
                buflen = *blen;
            }
        }
    }

    n = wcrtomb(dst+j, L'\0', &mbs);
    j += n - 1;				/* don't count NUL at the end */
    *tolen = j;

    if (id != (iconv_t)-1) {
        CONVERT2(j, cw, offset);
        *tolen = offset;
    }

    *pdst = cw->bp1;

    return 0;
err:
    *tolen = j;

    *pdst = cw->bp1;

    return 1;
}
Пример #13
0
static int
default_char2int(SCR *sp, const char * str, ssize_t len, CONVWIN *cw,
                 size_t *tolen, const CHAR_T **dst, const char *enc)
{
    int j;
    size_t i = 0;
    CHAR_T **tostr = (CHAR_T **)(void *)&cw->bp1;
    size_t  *blen = &cw->blen1;
    mbstate_t mbs;
    size_t   n;
    ssize_t  nlen = len;
    const char *src = (const char *)str;
    iconv_t	id = (iconv_t)-1;
    char	buffer[CONV_BUFFER_SIZE];
    size_t	left = len;
    int		error = 1;

    MEMSET(&mbs, 0, 1);
    BINC_RETW(NULL, *tostr, *blen, nlen);

#ifdef USE_ICONV
    if (strcmp(nl_langinfo(CODESET), enc)) {
        id = iconv_open(nl_langinfo(CODESET), enc);
        if (id == (iconv_t)-1)
            goto err;
        CONVERT(str, left, src, len);
    }
#endif

    for (i = 0, j = 0; j < len; ) {
        n = mbrtowc((*tostr)+i, src+j, len-j, &mbs);
        /* NULL character converted */
        if (n == (size_t)-2) error = -(len-j);
        if (n == (size_t)-1 || n == (size_t)-2)
            HANDLE_MBR_ERROR(n, mbs, (*tostr)[i], src[j]);
        if (n == 0) n = 1;
        j += n;
        if (++i >= *blen) {
            nlen += 256;
            BINC_RETW(NULL, *tostr, *blen, nlen);
        }
        if (id != (iconv_t)-1 && j == len && left) {
            CONVERT(str, left, src, len);
            j = 0;
        }
    }
    *tolen = i;

    if (id != (iconv_t)-1)
        iconv_close(id);

    *dst = cw->bp1;

    return 0;
err:
    *tolen = i;
    if (id != (iconv_t)-1)
        iconv_close(id);
    *dst = cw->bp1;

    return error;
}
Пример #14
0
static void
do_conv(FILE *fp, const char *from, const char *to, int silent,
	int hide_invalid)
{
	char inbuf[INBUFSIZE], outbuf[OUTBUFSIZE], *out;
	const char *in;
	size_t inbytes, outbytes, invalids;
	ssize_t ret;
	iconv_t cd;
	u_int32_t flags = 0;

	if (hide_invalid)
		flags |= __ICONV_F_HIDE_INVALID;
	cd = iconv_open(to, from);
	if (cd == (iconv_t)-1)
		err(EXIT_FAILURE, "iconv_open(%s, %s)", to, from);

	invalids = 0;
	while ((inbytes = fread(inbuf, 1, INBUFSIZE, fp)) > 0) {
		in = inbuf;
		while (inbytes>0) {
			size_t inval;

			out = outbuf;
			outbytes = OUTBUFSIZE;
			ret = __iconv(cd, &in, &inbytes, &out, &outbytes,
				      flags, &inval);
			invalids += inval;
			if (ret == -1 && errno != E2BIG) {
				/*
				 * XXX: iconv(3) is bad interface.
				 *   invalid character count is lost here.
				 *   instead, we just provide __iconv function.
				 */
				if (errno != EINVAL || in == inbuf)
					err(EXIT_FAILURE, "iconv()");

				/* incomplete input character */
				memmove(inbuf, in, inbytes);
				ret = fread(inbuf+inbytes, 1,
					    INBUFSIZE-inbytes, fp);
				if (ret == 0) {
					if (feof(fp))
						errx(EXIT_FAILURE,
						     "iconv(): %s",
						     strerror(EINVAL));
					else
						err(EXIT_FAILURE, "fread()");
				}
				in = inbuf;
				inbytes += ret;
			}
			if (outbytes < OUTBUFSIZE)
				fwrite(outbuf, 1, OUTBUFSIZE-outbytes, stdout);
		}
	}
	/* reset the shift state of the output buffer */
	outbytes = OUTBUFSIZE;
	out = outbuf;
	ret = iconv(cd, NULL, NULL, &out, &outbytes);
	if (ret == -1)
		err(EXIT_FAILURE, "iconv()");
	if (outbytes < OUTBUFSIZE)
		fwrite(outbuf, 1, OUTBUFSIZE-outbytes, stdout);

	if (invalids > 0 && !silent)
		warnx("warning: invalid characters: %lu",
		      (unsigned long)invalids);

	iconv_close(cd);
}
Пример #15
0
static rc_uint_type
wind_WideCharToMultiByte (rc_uint_type cp, const unichar *u, char *mb, rc_uint_type mb_len)
{
  rc_uint_type ret = 0;
#if defined (_WIN32) || defined (__CYGWIN__)
  WINBOOL used_def = FALSE;

  ret = (rc_uint_type) WideCharToMultiByte (cp, 0, u, -1, mb, mb_len,
				      	    NULL, & used_def);
#elif defined (HAVE_ICONV)
  int first = 1;
  char tmp[32];
  char *p_tmp;
  const char *iconv_name = wind_iconv_cp (cp);

  if (!u || !iconv_name)
    return 0;
  iconv_t cd = iconv_open (iconv_name, "UTF-16LE");

  while (1)
    {
      int iret;
      const char *n_u = "";
      char *n_tmp = "";

      p_tmp = tmp;
      iret = iconv_onechar (cd, (ICONV_CONST char *) u, p_tmp, 32, &n_u, & n_tmp);
      if (first)
	{
	  first = 0;
	  continue;
	}
      if (!iret)
	{
	  size_t l_tmp = (size_t) (n_tmp - p_tmp);

	  if (mb)
	    {
	      if ((size_t) mb_len < l_tmp)
		break;
	      memcpy (mb, tmp, l_tmp);
	      mb += l_tmp;
	      mb_len -= l_tmp;
	    }
	  ret += l_tmp;
	}
      else
	break;
      if (u[0] == 0)
	break;
      u = (const unichar *) n_u;
    }
  iconv_close (cd);
#else
  if (cp)
    ret = 0;

  while (u[ret] != 0)
    ++ret;

  ++ret;

  if (mb)
    {
      while (*u != 0 && mb_len != 0)
	{
	  if (u[0] == (u[0] & 0x7f))
	    *mb++ = (char) u[0];
	  else
	    *mb++ = '_';
	  ++u; --mb_len;
	}
      if (mb_len != 0)
	*mb = 0;
    }
#endif
  return ret;
}
Пример #16
0
	bool ConvertCharset(const CString& sFrom, const CString& sTo, CString& sData)
	{
		if(sData.empty()) return true;

		DEBUG("charset: Trying to convert [" + sData.Escape_n(CString::EURL) + "] from [" + sFrom + "] to [" + sTo + "]...");

		iconv_t ic = iconv_open(sTo.c_str(), sFrom.c_str());
		if(ic == (iconv_t)-1) return false;

		size_t uLength = GetConversionLength(ic, sData);

		if(uLength == (size_t)-1)
		{
			// incompatible input encoding.
			iconv_close(ic);
			return false;
		}
		else if(uLength == (size_t)-2)
		{
			// internal error, preserve errno from GetConversionLength:
			int tmp_errno = errno;
			iconv_close(ic);
			errno = tmp_errno;
			return false;
		}
		else
		{
			// no error, so let's do the actual conversion.

			iconv(ic, NULL, NULL, NULL, NULL); // reset

			// state vars for iconv:
			size_t uResultBufSize = uLength + 1;
			char *pResult = new char[uResultBufSize];
			memset(pResult, 0, uResultBufSize);
			char *pResultWalker = pResult;
			const char* pIn = sData.c_str();
			size_t uInLen = sData.size();

			// let's fcking do it!
			size_t uResult = iconv(ic, (ICONV_CONST char**)&pIn, &uInLen, &pResultWalker, &uResultBufSize);
			bool bResult = (uResult != (size_t)-1);

			iconv_close(ic);

			if(bResult)
			{
				sData.assign(pResult, (uLength + 1) - uResultBufSize);

				DEBUG("charset: Converted: [" + sData.Escape_n(CString::EURL) + "] from [" + sFrom + "] to [" + sTo + "]!");
			}
			else
			{
				DEBUG("Conversion failed: [" << uResult << "]");
			}

			delete[] pResult;

			return bResult;
		}
	}
Пример #17
0
char *
str_iconv (const char *src, const char *from_codeset, const char *to_codeset)
{
  if (*src == '\0' || c_strcasecmp (from_codeset, to_codeset) == 0)
    {
      char *result = strdup (src);

      if (result == NULL)
        errno = ENOMEM;
      return result;
    }
  else
    {
#if HAVE_ICONV
      iconv_t cd;
      char *result;

      /* Avoid glibc-2.1 bug with EUC-KR.  */
# if ((__GLIBC__ == 2 && __GLIBC_MINOR__ <= 1) && !defined __UCLIBC__) \
     && !defined _LIBICONV_VERSION
      if (c_strcasecmp (from_codeset, "EUC-KR") == 0
          || c_strcasecmp (to_codeset, "EUC-KR") == 0)
        {
          errno = EINVAL;
          return NULL;
        }
# endif
      cd = iconv_open (to_codeset, from_codeset);
      if (cd == (iconv_t) -1)
        return NULL;

      result = str_cd_iconv (src, cd);

      if (result == NULL)
        {
          /* Close cd, but preserve the errno from str_cd_iconv.  */
          int saved_errno = errno;
          iconv_close (cd);
          errno = saved_errno;
        }
      else
        {
          if (iconv_close (cd) < 0)
            {
              /* Return NULL, but free the allocated memory, and while doing
                 that, preserve the errno from iconv_close.  */
              int saved_errno = errno;
              free (result);
              errno = saved_errno;
              return NULL;
            }
        }
      return result;
#else
      /* This is a different error code than if iconv_open existed but didn't
         support from_codeset and to_codeset, so that the caller can emit
         an error message such as
           "iconv() is not supported. Installing GNU libiconv and
            then reinstalling this package would fix this."  */
      errno = ENOSYS;
      return NULL;
#endif
    }
}
Пример #18
0
int main(int argc,char *argv[]){
   strcpy(fname,argv[1]);
   FILE *f=fopen(fname,"rb");
   if(read_header(f)){
      char ofname[0x400];
      strcpy(ofname,fname);
      char *ibuf;
      char *obuf;
      ibuf=header_buf+(lrc_offs-9);
      while(*ibuf==' '){
	 ibuf--;
      }
      *(ibuf+1)=0;
      size_t ol=0x200,il=(ibuf-(char *)header_buf)-0x16;
      if(il==lrc_offs-0x1F){
	 obuf=strrchr(ofname,'.');
	 char *p=obuf-1;
	 obuf+=5;
	 *obuf=0;
	 while(*p!='/'){
	    *(p+5)=*p;
	    p--;
	 }
	 p[1]='d';
	 p[2]='o';
	 p[3]='n';
	 p[4]='e';
	 p[5]='-';
	 
      }
      else{
	 ibuf=header_buf+0x18;
	 obuf=strrchr(ofname,'/');
	 strcpy(obuf,"/done-");
	 obuf+=6;
	 iconv_t cd=iconv_open("UTF-8","GBK");
	 iconv(cd,&ibuf,&il,&obuf,&ol);
	 iconv_close(cd);
	 obuf--;
      }
      fprintf(stderr,"INFO: %s\n",ofname);
      if(lrc_len){
	 char *lrc_str=malloc(lrc_len+0x100);
	 memset(lrc_str,0,lrc_len+0x100);
	 fseek(f,lrc_offs,SEEK_SET);
	 fread(lrc_str,1,lrc_len,f);
	 init_keys(lrc_offs);
	 decode_str(lrc_str,lrc_len);
	 strcpy(obuf,".LRC");
	 FILE *ff=fopen(ofname,"w+");
	 fwrite(lrc_str,1,lrc_len,ff);
	 fclose(ff);
	 free(lrc_str);
      }
      if(dat_len){
	 unsigned char *dat_str=malloc(dat_len+0x100);
	 memset(dat_str,0,dat_len+0x100);
	 fseek(f,dat_offs,SEEK_SET);
	 int read=fread(dat_str,1,dat_len,f);
	 init_keys(dat_offs);
	 decode_str(dat_str,dat_len);
	 int type_known=1;
	 if(strncmp(dat_str,"RIFF",4)==0&&strncmp(dat_str+8,"AVI LIST",8)==0){
	    strcpy(obuf,".AVI");
	 }
	 else if(strncmp(dat_str,"FWS",3)==0){
	    strcpy(obuf,".SWF");
	 }
	 else if(dat_str[0]==0xFF&&(dat_str[1]&0xE0)==0xE0){
	    strcpy(obuf,".MP3");
	 }
	 else{
	    int i;
	    fprintf(stderr,"ERR: Unknown header:");
	    for(i=0;i<10;i++){
	       fprintf(stderr," %02X",dat_str[i]);
	    }
	    fprintf(stderr,"\n");
	    strcpy(obuf,".DAT");
	    type_known=0;
	 }
	 if(type_known){
	    FILE *ff=fopen(ofname,"w+");
	    fwrite(dat_str,1,dat_len,ff);
	    fclose(ff);
	 }
	 else{
	    FILE *ff=fopen(ofname,"w+");
	    fwrite(dat_str,1,dat_len,ff);
	    fclose(ff);
	 }
	 free(dat_str);
      }
   }
   fclose(f);
}
Пример #19
0
	//------------------------------------------------------------------------------
	int IGUIStringConv_iconv::WCharToUtf8( const CGUIStringW& rSrc, CGUIString& rDst )
	{
		if( rSrc.empty())
		{
			rDst.clear();
			return 0;
		}

		//open iconv
		iconv_t cd = iconv_open ("UTF-8", "UTF-16LE");
		if( cd == (iconv_t)-1 )
		{
			throw CGUIException(
				"[WCharToUtf8]: failed to open iconv, errno is %d",
				errno);
			return -1;
		}

		//convert
		size_t	buf_size = rSrc.size()*4+1;
		size_t	inbytesleft = rSrc.size()*2;
		size_t	outbytesleft = buf_size;
		char*	dst = (char*)(new char[buf_size]);
		char*	pOutBuf = NULL;
		char*	pInBuf = (char*)rSrc.c_str();

		bool	bError = false;

		while(inbytesleft > 0) 
		{
			pOutBuf = dst;
			outbytesleft = buf_size;

			size_t retbytes = iconv(cd, &pInBuf, &inbytesleft, &pOutBuf, &outbytesleft);
			//int errno_save = errno;

			if (dst != pOutBuf)  
			{
				// we have something to write
				rDst.append(dst, (pOutBuf-dst));
			} 

			//check ret
			if( retbytes == size_t(-1) )
			{
				if( errno == E2BIG )
				{
					continue;
				}
				else
				{
					bError = true;
					break;
				}
			}
			else
			{
				//success
				break;
			}
		}

		delete[] dst;
		if( bError)
		{
			switch(errno)
			{
			case EILSEQ:
				throw CGUIException(
					"[WCharToUtf8]: failed to iconv, errno is EILSEQ");
				return -1;
			case EINVAL:
				throw CGUIException(
					"[WCharToUtf8]: failed to iconv, errno is EINVAL");
				return -1;
			default:
				throw CGUIException(
					"[WCharToUtf8]: failed to iconv, errno is %d",
					errno);
				return -1;
			}
		}

		//close iconv
		int ret = iconv_close(cd);
		if( ret == -1 )
		{
			throw CGUIException(
				"[WCharToUtf8]: failed to close iconv, errno is %d",
				errno);
			return -1;
		}

		return 0;
	}
Пример #20
0
/*
 * curl_easy_duphandle() is an external interface to allow duplication of a
 * given input easy handle. The returned handle will be a new working handle
 * with all options set exactly as the input source handle.
 */
CURL *curl_easy_duphandle(CURL *incurl)
{
  bool fail = TRUE;
  struct SessionHandle *data=(struct SessionHandle *)incurl;

  struct SessionHandle *outcurl = (struct SessionHandle *)
    calloc(sizeof(struct SessionHandle), 1);

  if(NULL == outcurl)
    return NULL; /* failure */

  do {

    /*
     * We setup a few buffers we need. We should probably make them
     * get setup on-demand in the code, as that would probably decrease
     * the likeliness of us forgetting to init a buffer here in the future.
     */
    outcurl->state.headerbuff=(char*)malloc(HEADERSIZE);
    if(!outcurl->state.headerbuff) {
      break;
    }
    outcurl->state.headersize=HEADERSIZE;

    /* copy all userdefined values */
    if (Curl_dupset(outcurl, data) != CURLE_OK)
      break;

    if(data->state.used_interface == Curl_if_multi)
      outcurl->state.connc = data->state.connc;
    else
      outcurl->state.connc = Curl_mk_connc(CONNCACHE_PRIVATE, -1);

    if(!outcurl->state.connc)
      break;

    outcurl->state.lastconnect = -1;

    outcurl->progress.flags    = data->progress.flags;
    outcurl->progress.callback = data->progress.callback;

#if !defined(CURL_DISABLE_HTTP) && !defined(CURL_DISABLE_COOKIES)
    if(data->cookies) {
      /* If cookies are enabled in the parent handle, we enable them
         in the clone as well! */
      outcurl->cookies = Curl_cookie_init(data,
                                            data->cookies->filename,
                                            outcurl->cookies,
                                            data->set.cookiesession);
      if(!outcurl->cookies) {
        break;
      }
    }
#endif   /* CURL_DISABLE_HTTP */

    /* duplicate all values in 'change' */

    if(data->change.url) {
      outcurl->change.url = strdup(data->change.url);
      if(!outcurl->change.url)
        break;
      outcurl->change.url_alloc = TRUE;
    }

    if(data->change.referer) {
      outcurl->change.referer = strdup(data->change.referer);
      if(!outcurl->change.referer)
        break;
      outcurl->change.referer_alloc = TRUE;
    }

#ifdef USE_ARES
    /* If we use ares, we setup a new ares channel for the new handle */
    if(ARES_SUCCESS != ares_init(&outcurl->state.areschannel))
      break;
#endif

#if defined(CURL_DOES_CONVERSIONS) && defined(HAVE_ICONV)
    outcurl->inbound_cd = iconv_open(CURL_ICONV_CODESET_OF_HOST,
                                     CURL_ICONV_CODESET_OF_NETWORK);
    outcurl->outbound_cd = iconv_open(CURL_ICONV_CODESET_OF_NETWORK,
                                      CURL_ICONV_CODESET_OF_HOST);
    outcurl->utf8_cd = iconv_open(CURL_ICONV_CODESET_OF_HOST,
                                  CURL_ICONV_CODESET_FOR_UTF8);
#endif

    Curl_easy_initHandleData(outcurl);

    outcurl->magic = CURLEASY_MAGIC_NUMBER;

    fail = FALSE; /* we reach this point and thus we are OK */

  } while(0);

  if(fail) {
    if(outcurl) {
      if(outcurl->state.connc &&
         (outcurl->state.connc->type == CONNCACHE_PRIVATE))
        Curl_rm_connc(outcurl->state.connc);
      if(outcurl->state.headerbuff)
        free(outcurl->state.headerbuff);
      if(outcurl->change.url)
        free(outcurl->change.url);
      if(outcurl->change.referer)
        free(outcurl->change.referer);
      Curl_freeset(outcurl);
      free(outcurl); /* free the memory again */
      outcurl = NULL;
    }
  }

  return outcurl;
}
Пример #21
0
iconv_t
rpl_iconv_open (const char *tocode, const char *fromcode)
#undef iconv_open
{
  char fromcode_upper[32];
  char tocode_upper[32];
  char *fromcode_upper_end;
  char *tocode_upper_end;

#if REPLACE_ICONV_UTF
  /* Special handling of conversion between UTF-8 and UTF-{16,32}{BE,LE}.
     Do this here, before calling the real iconv_open(), because  OSF/1 5.1
     iconv() to these encoding inserts a BOM, which is wrong.
     We do not need to handle conversion between arbitrary encodings and
     UTF-{16,32}{BE,LE}, because the 'striconveh' module implements two-step
     conversion throough UTF-8.
     The _ICONV_* constants are chosen to be disjoint from any iconv_t
     returned by the system's iconv_open() functions.  Recall that iconv_t
     is a scalar type.  */
  if (c_toupper (fromcode[0]) == 'U'
      && c_toupper (fromcode[1]) == 'T'
      && c_toupper (fromcode[2]) == 'F'
      && fromcode[3] == '-')
    {
      if (c_toupper (tocode[0]) == 'U'
	  && c_toupper (tocode[1]) == 'T'
	  && c_toupper (tocode[2]) == 'F'
	  && tocode[3] == '-')
	{
	  if (strcmp (fromcode + 4, "8") == 0)
	    {
	      if (c_strcasecmp (tocode + 4, "16BE") == 0)
		return _ICONV_UTF8_UTF16BE;
	      if (c_strcasecmp (tocode + 4, "16LE") == 0)
		return _ICONV_UTF8_UTF16LE;
	      if (c_strcasecmp (tocode + 4, "32BE") == 0)
		return _ICONV_UTF8_UTF32BE;
	      if (c_strcasecmp (tocode + 4, "32LE") == 0)
		return _ICONV_UTF8_UTF32LE;
	    }
	  else if (strcmp (tocode + 4, "8") == 0)
	    {
	      if (c_strcasecmp (fromcode + 4, "16BE") == 0)
		return _ICONV_UTF16BE_UTF8;
	      if (c_strcasecmp (fromcode + 4, "16LE") == 0)
		return _ICONV_UTF16LE_UTF8;
	      if (c_strcasecmp (fromcode + 4, "32BE") == 0)
		return _ICONV_UTF32BE_UTF8;
	      if (c_strcasecmp (fromcode + 4, "32LE") == 0)
		return _ICONV_UTF32LE_UTF8;
	    }
	}
    }
#endif

  /* Do *not* add special support for 8-bit encodings like ASCII or ISO-8859-1
     here.  This would lead to programs that work in some locales (such as the
     "C" or "en_US" locales) but do not work in East Asian locales.  It is
     better if programmers make their programs depend on GNU libiconv (except
     on glibc systems), e.g. by using the AM_ICONV macro and documenting the
     dependency in an INSTALL or DEPENDENCIES file.  */

  /* Try with the original names first.
     This covers the case when fromcode or tocode is a lowercase encoding name
     that is understood by the system's iconv_open but not listed in our
     mappings table.  */
  {
    iconv_t cd = iconv_open (tocode, fromcode);
    if (cd != (iconv_t)(-1))
      return cd;
  }

  /* Convert the encodings to upper case, because
       1. in the arguments of iconv_open() on AIX, HP-UX, and OSF/1 the case
	  matters,
       2. it makes searching in the table faster.  */
  {
    const char *p = fromcode;
    char *q = fromcode_upper;
    while ((*q = c_toupper (*p)) != '\0')
      {
	p++;
	q++;
	if (q == &fromcode_upper[SIZEOF (fromcode_upper)])
	  {
	    errno = EINVAL;
	    return (iconv_t)(-1);
	  }
      }
    fromcode_upper_end = q;
  }

  {
    const char *p = tocode;
    char *q = tocode_upper;
    while ((*q = c_toupper (*p)) != '\0')
      {
	p++;
	q++;
	if (q == &tocode_upper[SIZEOF (tocode_upper)])
	  {
	    errno = EINVAL;
	    return (iconv_t)(-1);
	  }
      }
    tocode_upper_end = q;
  }

#ifdef ICONV_FLAVOR
  /* Apply the mappings.  */
  {
    const struct mapping *m =
      mapping_lookup (fromcode_upper, fromcode_upper_end - fromcode_upper);

    fromcode = (m != NULL ? m->vendor_name : fromcode_upper);
  }
  {
    const struct mapping *m =
      mapping_lookup (tocode_upper, tocode_upper_end - tocode_upper);

    tocode = (m != NULL ? m->vendor_name : tocode_upper);
  }
#else
  fromcode = fromcode_upper;
  tocode = tocode_upper;
#endif

  return iconv_open (tocode, fromcode);
}
Пример #22
0
int qr_code_data_list_extract_text(const qr_code_data_list *_qrlist,
                                   zbar_image_scanner_t *iscn,
                                   zbar_image_t *img)
{
  iconv_t              sjis_cd;
  iconv_t              utf8_cd;
  iconv_t              latin1_cd;
  const qr_code_data  *qrdata;
  int                  nqrdata;
  unsigned char       *mark;
  int                  ntext;
  int                  i;
  qrdata=_qrlist->qrdata;
  nqrdata=_qrlist->nqrdata;
  mark=(unsigned char *)calloc(nqrdata,sizeof(*mark));
  ntext=0;
  /*This is the encoding the standard says is the default.*/
  //latin1_cd=iconv_open("UTF-8","ISO8859-1");
    latin1_cd=iconv_open("UTF-8","GB18030");
  /*But this one is often used, as well.*/
  sjis_cd=iconv_open("UTF-8","SJIS");
  /*This is a trivial conversion just to check validity without extra code.*/
  utf8_cd=iconv_open("UTF-8","UTF-8");
  for(i=0;i<nqrdata;i++)if(!mark[i]){
    const qr_code_data       *qrdataj;
    const qr_code_data_entry *entry;
    iconv_t                   enc_list[3];
    iconv_t                   eci_cd;
    int                       sa[16];
    int                       sa_size;
    char                     *sa_text;
    size_t                    sa_ntext;
    size_t                    sa_ctext;
    int                       fnc1;
    int                       eci;
    int                       err;
    int                       j;
    int                       k;
    zbar_symbol_t *syms = NULL, **sym = &syms;
    qr_point dir;
    int horiz;

    /*Step 0: Collect the other QR codes belonging to this S-A group.*/
    if(qrdata[i].sa_size){
      unsigned sa_parity;
      sa_size=qrdata[i].sa_size;
      sa_parity=qrdata[i].sa_parity;
      for(j=0;j<sa_size;j++)sa[j]=-1;
      for(j=i;j<nqrdata;j++)if(!mark[j]){
        /*TODO: We could also match version, ECC level, etc. if size and
           parity alone are too ambiguous.*/
        if(qrdata[j].sa_size==sa_size&&qrdata[j].sa_parity==sa_parity&&
         sa[qrdata[j].sa_index]<0){
          sa[qrdata[j].sa_index]=j;
          mark[j]=1;
        }
      }
      /*TODO: If the S-A group is complete, check the parity.*/
    }
    else{
      sa[0]=i;
      sa_size=1;
    }

    sa_ctext=0;
    fnc1=0;
    /*Step 1: Detect FNC1 markers and estimate the required buffer size.*/
    for(j=0;j<sa_size;j++)if(sa[j]>=0){
      qrdataj=qrdata+sa[j];
      for(k=0;k<qrdataj->nentries;k++){
        int shift;
        entry=qrdataj->entries+k;
        shift=0;
        switch(entry->mode){
          /*FNC1 applies to the entire code and ignores subsequent markers.*/
          case QR_MODE_FNC1_1ST:
          case QR_MODE_FNC1_2ND:fnc1=1;break;
          /*2 SJIS bytes will be at most 4 UTF-8 bytes.*/
          case QR_MODE_KANJI:shift++;
          /*We assume at most 4 UTF-8 bytes per input byte.
            I believe this is true for all the encodings we actually use.*/
          case QR_MODE_BYTE:shift++;
          default:{
            /*The remaining two modes are already valid UTF-8.*/
            if(QR_MODE_HAS_DATA(entry->mode)){
              sa_ctext+=entry->payload.data.len<<shift;
            }
          }break;
        }
      }
    }

    /*Step 2: Convert the entries.*/
    sa_text=(char *)malloc((sa_ctext+1)*sizeof(*sa_text));
    sa_ntext=0;
    eci=-1;
    enc_list[0]=sjis_cd;
    enc_list[1]=latin1_cd;
    enc_list[2]=utf8_cd;
    eci_cd=(iconv_t)-1;
    err=0;
    for(j = 0; j < sa_size && !err; j++, sym = &(*sym)->next) {
      *sym = _zbar_image_scanner_alloc_sym(iscn, ZBAR_QRCODE, 0);
      (*sym)->datalen = sa_ntext;
      if(sa[j]<0){
        /* generic placeholder for unfinished results */
        (*sym)->type = ZBAR_PARTIAL;

        /*Skip all contiguous missing segments.*/
        for(j++;j<sa_size&&sa[j]<0;j++);
        /*If there aren't any more, stop.*/
        if(j>=sa_size)break;

        /* mark break in data */
        sa_text[sa_ntext++]='\0';
        (*sym)->datalen = sa_ntext;

        /* advance to next symbol */
        sym = &(*sym)->next;
        *sym = _zbar_image_scanner_alloc_sym(iscn, ZBAR_QRCODE, 0);
      }

      qrdataj=qrdata+sa[j];
      /* expose bounding box */
      sym_add_point(*sym, qrdataj->bbox[0][0], qrdataj->bbox[0][1]);
      sym_add_point(*sym, qrdataj->bbox[2][0], qrdataj->bbox[2][1]);
      sym_add_point(*sym, qrdataj->bbox[3][0], qrdataj->bbox[3][1]);
      sym_add_point(*sym, qrdataj->bbox[1][0], qrdataj->bbox[1][1]);

      /* approx symbol "up" direction */
      dir[0] = (qrdataj->bbox[0][0] - qrdataj->bbox[2][0] +
                qrdataj->bbox[1][0] - qrdataj->bbox[3][0]);
      dir[1] = (qrdataj->bbox[2][1] - qrdataj->bbox[0][1] +
                qrdataj->bbox[3][1] - qrdataj->bbox[1][1]);
      horiz = abs(dir[0]) > abs(dir[1]);
      (*sym)->orient = horiz + 2 * (dir[1 - horiz] < 0);

      for(k=0;k<qrdataj->nentries&&!err;k++){
        size_t              inleft;
        size_t              outleft;
        char               *in;
        char               *out;
        entry=qrdataj->entries+k;
        switch(entry->mode){
          case QR_MODE_NUM:{
            if(sa_ctext-sa_ntext>=(size_t)entry->payload.data.len){
              memcpy(sa_text+sa_ntext,entry->payload.data.buf,
               entry->payload.data.len*sizeof(*sa_text));
              sa_ntext+=entry->payload.data.len;
            }
            else err=1;
          }break;
          case QR_MODE_ALNUM:{
            char *p;
            in=(char *)entry->payload.data.buf;
            inleft=entry->payload.data.len;
            /*FNC1 uses '%' as an escape character.*/
            if(fnc1)for(;;){
              size_t plen;
              char   c;
              p=memchr(in,'%',inleft*sizeof(*in));
              if(p==NULL)break;
              plen=p-in;
              if(sa_ctext-sa_ntext<plen+1)break;
              memcpy(sa_text+sa_ntext,in,plen*sizeof(*in));
              sa_ntext+=plen;
              /*Two '%'s is a literal '%'*/
              if(plen+1<inleft&&p[1]=='%'){
                c='%';
                plen++;
                p++;
              }
              /*One '%' is the ASCII group separator.*/
              else c=0x1D;
              sa_text[sa_ntext++]=c;
              inleft-=plen+1;
              in=p+1;
            }
            else p=NULL;
            if(p!=NULL||sa_ctext-sa_ntext<inleft)err=1;
            else{
              memcpy(sa_text+sa_ntext,in,inleft*sizeof(*sa_text));
              sa_ntext+=inleft;
            }
          }break;
          /*TODO: This will not handle a multi-byte sequence split between
             multiple data blocks.
            Does such a thing occur?
            Is it allowed?
            It requires copying buffers around to handle correctly.*/
          case QR_MODE_BYTE:{
            in=(char *)entry->payload.data.buf;
            inleft=entry->payload.data.len;
            out=sa_text+sa_ntext;
            outleft=sa_ctext-sa_ntext;
            /*If we have no specified encoding, attempt to auto-detect it.*/
            if(eci<0){
              int ei;
              /*First check for the UTF-8 BOM.*/
              if(inleft>=3&&
               in[0]==(char)0xEF&&in[1]==(char)0xBB&&in[2]==(char)0xBF){
                in+=3;
                inleft-=3;
                /*Actually try converting (to check validity).*/
                err=utf8_cd==(iconv_t)-1||
                 iconv(utf8_cd,&in,&inleft,&out,&outleft)==(size_t)-1;
                if(!err){
                  sa_ntext=out-sa_text;
                  enc_list_mtf(enc_list,utf8_cd);
                  continue;
                }
                in=(char *)entry->payload.data.buf;
                inleft=entry->payload.data.len;
                out=sa_text+sa_ntext;
                outleft=sa_ctext-sa_ntext;
              }
              /*If the text is 8-bit clean, prefer UTF-8 over SJIS, since SJIS
                 will corrupt the backslashes used for DoCoMo formats.*/
              else if(text_is_ascii((unsigned char *)in,inleft)){
                enc_list_mtf(enc_list,utf8_cd);
              }
              /*Try our list of encodings.*/
              for(ei=0;ei<3;ei++)if(enc_list[ei]!=(iconv_t)-1){
                /*According to the standard, ISO/IEC 8859-1 (one hyphen) is
                   supposed to be used, but reality is not always so.
                  It's got an invalid range that is used often with SJIS
                   and UTF-8, though, which makes detection easier.
                  However, iconv() does not properly reject characters in
                   those ranges, since ISO-8859-1 (two hyphens) defines a
                   number of seldom-used control code characters there.
                  So if we see any of those characters, move this
                   conversion to the end of the list.*/
                if(ei<2&&enc_list[ei]==latin1_cd&&
                 !text_is_latin1((unsigned char *)in,inleft)){
                  int ej;
                  for(ej=ei+1;ej<3;ej++)enc_list[ej-1]=enc_list[ej];
                  enc_list[2]=latin1_cd;
                }
                err=iconv(enc_list[ei],&in,&inleft,&out,&outleft)==(size_t)-1;
                if(!err){
                  sa_ntext=out-sa_text;
                  enc_list_mtf(enc_list,enc_list[ei]);
                  break;
                }
                in=(char *)entry->payload.data.buf;
                inleft=entry->payload.data.len;
                out=sa_text+sa_ntext;
                outleft=sa_ctext-sa_ntext;
              }
            }
            /*We were actually given a character set; use it.*/
            else{
              err=eci_cd==(iconv_t)-1||
               iconv(eci_cd,&in,&inleft,&out,&outleft)==(size_t)-1;
              if(!err)sa_ntext=out-sa_text;
            }
          }break;
          /*Kanji mode always uses SJIS.*/
          case QR_MODE_KANJI:{
            in=(char *)entry->payload.data.buf;
            inleft=entry->payload.data.len;
            out=sa_text+sa_ntext;
            outleft=sa_ctext-sa_ntext;
            err=sjis_cd==(iconv_t)-1||
             iconv(sjis_cd,&in,&inleft,&out,&outleft)==(size_t)-1;
            if(!err)sa_ntext=out-sa_text;
          }break;
          /*Check to see if a character set was specified.*/
          case QR_MODE_ECI:{
            const char *enc;
            char        buf[16];
            unsigned    cur_eci;
            cur_eci=entry->payload.eci;
            if(cur_eci<=QR_ECI_ISO8859_16&&cur_eci!=14){
              if(cur_eci!=QR_ECI_GLI0&&cur_eci!=QR_ECI_CP437){
                sprintf(buf,"ISO8859-%i",QR_MAXI(cur_eci,3)-2);
                enc=buf;
              }
              /*Note that CP437 requires an iconv compiled with
                 --enable-extra-encodings, and thus may not be available.*/
              else enc="CP437";
            }
            else if(cur_eci==QR_ECI_SJIS)enc="SJIS";
            /*Don't know what this ECI code specifies, but not an encoding that
               we recognize.*/
            else continue;
            eci=cur_eci;
            eci_cd=iconv_open("UTF-8",enc);
          }break;
          /*Silence stupid compiler warnings.*/
          default:break;
        }
      }
      /*If eci should be reset between codes, do so.*/
      if(eci<=QR_ECI_GLI1){
        eci=-1;
        if(eci_cd!=(iconv_t)-1)iconv_close(eci_cd);
      }
    }
    if(eci_cd!=(iconv_t)-1)iconv_close(eci_cd);
    if(!err){
      zbar_symbol_t *sa_sym;
      sa_text[sa_ntext++]='\0';
      if(sa_ctext+1>sa_ntext){
        sa_text=(char *)realloc(sa_text,sa_ntext*sizeof(*sa_text));
      }

      if(sa_size == 1)
          sa_sym = syms;
      else {
          /* cheap out w/axis aligned bbox for now */
          int xmin = img->width, xmax = -2;
          int ymin = img->height, ymax = -2;

          /* create "virtual" container symbol for composite result */
          sa_sym = _zbar_image_scanner_alloc_sym(iscn, ZBAR_QRCODE, 0);
          sa_sym->syms = _zbar_symbol_set_create();
          sa_sym->syms->head = syms;

          /* fixup data references */
          for(; syms; syms = syms->next) {
              int next;
              _zbar_symbol_refcnt(syms, 1);
              if(syms->type == ZBAR_PARTIAL)
                  sa_sym->type = ZBAR_PARTIAL;
              else
                  for(j = 0; j < syms->npts; j++) {
                      int u = syms->pts[j].x;
                      if(xmin >= u) xmin = u - 1;
                      if(xmax <= u) xmax = u + 1;
                      u = syms->pts[j].y;
                      if(ymin >= u) ymin = u - 1;
                      if(ymax <= u) ymax = u + 1;
                  }
              syms->data = sa_text + syms->datalen;
              next = (syms->next) ? syms->next->datalen : sa_ntext;
              assert(next > syms->datalen);
              syms->datalen = next - syms->datalen - 1;
          }
          if(xmax >= -1) {
              sym_add_point(sa_sym, xmin, ymin);
              sym_add_point(sa_sym, xmin, ymax);
              sym_add_point(sa_sym, xmax, ymax);
              sym_add_point(sa_sym, xmax, ymin);
          }
      }
      sa_sym->data = sa_text;
      sa_sym->data_alloc = sa_ntext;
      sa_sym->datalen = sa_ntext - 1;

      _zbar_image_scanner_add_sym(iscn, sa_sym);
    }
    else {
        _zbar_image_scanner_recycle_syms(iscn, syms);
        free(sa_text);
    }
  }
  if(utf8_cd!=(iconv_t)-1)iconv_close(utf8_cd);
  if(sjis_cd!=(iconv_t)-1)iconv_close(sjis_cd);
  if(latin1_cd!=(iconv_t)-1)iconv_close(latin1_cd);
  free(mark);
  return ntext;
}
Пример #23
0
int
main (int argc, char *argv[])
{
  int fd;
  struct stat st;
  int result;
  char *inmem;
  char *outmem;
  size_t inlen;
  size_t outlen;

#ifdef HAVE_MCHECK_H
  mtrace ();
#endif

  if (!argv[1])
    exit (1);

  /* Make the content of the file available in memory.  */
  fd = open (argv[1], O_RDONLY);
  if (fd == -1)
    error (EXIT_FAILURE, errno, "cannot open %s", basename (argv[1]));

  if (fstat (fd, &st) != 0)
    error (EXIT_FAILURE, errno, "cannot stat %s", basename (argv[1]));
  memlen = st.st_size;

  mem = (char *) malloc (memlen + 1);
  if (mem == NULL)
    error (EXIT_FAILURE, errno, "while allocating buffer");

  if ((size_t) read (fd, mem, memlen) != memlen)
    error (EXIT_FAILURE, 0, "cannot read entire file");
  mem[memlen] = '\0';

  close (fd);

  /* We have to convert a few things from Latin-1 to UTF-8.  */
  cd = iconv_open ("UTF-8", "ISO-8859-1");
  if (cd == (iconv_t) -1)
    error (EXIT_FAILURE, errno, "cannot get conversion descriptor");

  /* For the second test we have to convert the file content to UTF-8.
     Since the text is mostly ASCII it should be enough to allocate
     twice as much memory for the UTF-8 text than for the Latin-1
     text.  */
  umem = (char *) calloc (2, memlen);
  if (umem == NULL)
    error (EXIT_FAILURE, errno, "while allocating buffer");

  inmem = mem;
  inlen = memlen;
  outmem = umem;
  outlen = 2 * memlen - 1;
  iconv (cd, &inmem, &inlen, &outmem, &outlen);
  umemlen = outmem - umem;
  if (inlen != 0)
    error (EXIT_FAILURE, errno, "cannot convert buffer");

#ifdef DEBUG
  re_set_syntax (RE_DEBUG);
#endif

  /* Run the actual tests.  All tests are run in a single-byte and a
     multi-byte locale.  */
  result = test_expr ("[הבאגיטךםלמסצףעפ�תש�]", 2, 2);
  result |= test_expr ("G.ran", 2, 3);
  result |= test_expr ("G.\\{1\\}ran", 2, 3);
  result |= test_expr ("G.*ran", 3, 44);
  result |= test_expr ("[הבאג]", 0, 0);
  result |= test_expr ("Uddeborg", 2, 2);
  result |= test_expr (".Uddeborg", 2, 2);

  /* Free the resources.  */
  free (umem);
  iconv_close (cd);
  free (mem);

  return result;
}
Пример #24
0
ORG_LABCRYPTO_ABETTOR_result
ORG_LABCRYPTO_ABETTOR__unicode__utf8_to_utf16(
  ORG_LABCRYPTO_ABETTOR_string utf8,
  ORG_LABCRYPTO_ABETTOR_string_ptr utf16,
  ORG_LABCRYPTO_ABETTOR_length_ptr utf16_len
) {
  ORG_LABCRYPTO_ABETTOR_uint32 i = 0;
  iconv_t cd;
  char *inbuf, *outbuf;
  size_t inbytesleft, outbytesleft, nchars, utf16_buf_len;

#if _WIN32
  cd = iconv_open("UTF-16LE", "UTF-8");
#else
	cd = iconv_open("UTF16LE", "UTF8");
#endif
  if (cd == (iconv_t) - 1) {
    printf("iconv_open failed: %d\n", errno);
    return -1;
  }
  inbytesleft = strlen(utf8);
  if (inbytesleft == 0) {
	  printf("!%s: empty string\n", FUNCTION_MACRO);
    iconv_close(cd);
    return -1;
  }
  inbuf = utf8;
  utf16_buf_len = 2 * inbytesleft; 
  *utf16 = malloc(utf16_buf_len);
  if (!*utf16) {
	  printf("!%s: malloc failed\n", FUNCTION_MACRO);
    iconv_close(cd);
    return -1;
  }
  outbytesleft = utf16_buf_len;
  outbuf = *utf16;    
  nchars = iconv(cd, &inbuf, &inbytesleft, &outbuf, &outbytesleft);
  while (nchars == (size_t)-1 && errno == E2BIG) {
      char *ptr;
      size_t increase = 10;                   // increase length a bit
      size_t len;
      utf16_buf_len += increase;
      outbytesleft += increase;
      ptr = realloc(*utf16, utf16_buf_len);
      if (!ptr) {
        printf("!%s: realloc failed\n", FUNCTION_MACRO);
        free(*utf16);
        iconv_close(cd);
        return -1;
      }
      len = outbuf - *utf16;
      *utf16 = ptr;
      outbuf = *utf16 + len;
      nchars = iconv(cd, &inbuf, &inbytesleft, &outbuf, &outbytesleft);
  }
  if (nchars == (size_t)-1) {
	  printf("!%s: iconv failed: %d\n", FUNCTION_MACRO, errno);
    free(*utf16);
    iconv_close(cd);
    return -1;
  }
  iconv_close(cd);
  *utf16_len = utf16_buf_len - outbytesleft;
  for (; i < *utf16_len; i += 2) {
    char temp = (*utf16)[i];
    (*utf16)[i] = (*utf16)[i + 1];
    (*utf16)[i + 1] = temp;
  }
  return 0;
}
Пример #25
0
// make our proposed ZIP-file chunk map
ngx_int_t
ngx_http_zip_generate_pieces(ngx_http_request_t *r, ngx_http_zip_ctx_t *ctx)
{
    ngx_uint_t i, piece_i;
    off_t offset = 0;
    time_t unix_time = 0;
    ngx_uint_t dos_time = 0;
    ngx_http_zip_file_t  *file;
    ngx_http_zip_piece_t *header_piece, *file_piece, *trailer_piece, *cd_piece;
    ngx_http_variable_value_t  *vv;

    if ((vv = ngx_palloc(r->pool, sizeof(ngx_http_variable_value_t))) == NULL) 
        return NGX_ERROR;

    ctx->unicode_path = 0;
#ifdef NGX_ZIP_HAVE_ICONV
    iconv_t *iconv_cd = NULL;
#endif

    // Let's try to find special header that contains separator string.
    // What for this strange separator string you ask?
    // Sometimes there might be a problem converting UTF-8 to zips native
    // charset(CP866), because it's not 1:1 conversion. So my solution is to
    // developers provide their own version of converted filename and pass it
    // to mod_zip along with UTF-8 filename which will go straight to Unicode
    // path extra field (thanks to tony2001). So separator is a solution that doesn't
    // break current format. And allows passing file name in both formats as one string.
    //
    // Normally we pass:
    // CRC32 <size> <path> <filename>\n
    // ...
    // * <filename> passed to archive as filename w/o conversion
    // * UFT-8 flag for filename is set
    //
    // tony2001's X-Archive-Charset: <charset> way:
    // CRC32 <size> <path> <filename>\n
    // ...
    // * <filename> is accepted to be UTF-8 string
    // * <filename>, converted to <charset> and passed to archive as filename
    // * <filename> passed to Unicode path extra field
    // * UFT-8 flag for filename is not set
    //
    // My X-Archive-Name-Sep: <sep> solution:
    // CRC32 <size> <path> <native-filename><sep><utf8-filename>\n
    // ...
    // * <native-filename> passed to archive as filename w/o conversion
    // * <utf8-filename> passed to Unicode path extra field
    // * UFT-8 flag for filename is not set
    //
    // You just need to provide separator that won't interfere with file names. I suggest using '/'
    // as it is ASCII character and forbidden on most (if not all) platforms as a part of filename.
    //
    // Empty separator string means no UTF-8 version provided. Usefull when we need to pass only
    // names encoded in native charset. It's equal to 'X-Archive-Charset: native;'.
    // Note: Currently it is impossible after '[PATCH] Support for UTF-8 file names.'(4f61592b)
    // because UFT-8 flag (zip_utf8_flag) is set default for templates.

    if(ngx_http_upstream_header_variable(r, vv, (uintptr_t)(&ngx_http_zip_header_name_separator)) == NGX_OK && !vv->not_found) {
        ctx->native_charset = 1;
        if(vv->len)
            ctx->unicode_path = 1;            
    } else {
#ifdef NGX_ZIP_HAVE_ICONV
        if (ngx_http_upstream_header_variable(r, vv, (uintptr_t)(&ngx_http_zip_header_charset_name)) == NGX_OK
                && !vv->not_found && ngx_strncmp(vv->data, "utf8", sizeof("utf8") - 1) != 0) {

            if(ngx_strncmp(vv->data, "native", sizeof("native") - 1))
            {
                char encoding[ICONV_CSNMAXLEN];
                snprintf(encoding, sizeof(encoding), "%s//TRANSLIT//IGNORE", vv->data);

                iconv_cd = iconv_open((const char *)encoding, "utf-8");
                if (iconv_cd == (iconv_t)(-1)) {
                    ngx_log_error(NGX_LOG_WARN, r->connection->log, errno,
                                  "mod_zip: iconv_open('%s', 'utf-8') failed",
                                  vv->data);
                    iconv_cd = NULL;
                }
                else
                {
                    ctx->unicode_path = 1;
                    ctx->native_charset = 1;
                }
            }
            else
                ctx->native_charset = 1;
        }
#endif
    }

    // pieces: for each file: header, data, footer (if needed) -> 2 or 3 per file
    // plus file footer (CD + [zip64 end + zip64 locator +] end of cd) in one chunk
    ctx->pieces_n = ctx->files.nelts * (2 + (!!ctx->missing_crc32)) + 1;

    if ((ctx->pieces = ngx_palloc(r->pool, sizeof(ngx_http_zip_piece_t) * ctx->pieces_n)) == NULL) 
        return NGX_ERROR;
    
    ctx->cd_size = 0;
    unix_time = time(NULL);
    dos_time = ngx_dos_time(unix_time);
    for (piece_i = i = 0; i < ctx->files.nelts; i++) {
        file = &((ngx_http_zip_file_t *)ctx->files.elts)[i];
        file->offset = offset;
        file->unix_time = unix_time;
        file->dos_time = dos_time;

        if(ctx->unicode_path) {
#ifdef NGX_ZIP_HAVE_ICONV
            if (iconv_cd) {
                size_t inlen = file->filename.len, outlen, outleft;
                u_char *p, *in;

                //inbuf
                file->filename_utf8.data = ngx_pnalloc(r->pool, file->filename.len + 1);
                ngx_memcpy(file->filename_utf8.data, file->filename.data, file->filename.len);
                file->filename_utf8.len = file->filename.len;
                file->filename_utf8.data[file->filename.len] = '\0';

                //outbuf
                outlen = outleft = inlen * sizeof(int) + 15;
                file->filename.data = ngx_pnalloc(r->pool, outlen + 1);

                in = file->filename_utf8.data;
                p = file->filename.data;

                //reset state
                iconv(iconv_cd, NULL, NULL, NULL, NULL);

                //convert the string
                iconv(iconv_cd, (char **)&in, &inlen, (char **)&p, &outleft);
                //XXX if (res == (size_t)-1) { ? }

                file->filename.len = outlen - outleft;

                file->filename_utf8_crc32 = ngx_crc32_long(file->filename_utf8.data, file->filename_utf8.len);
            }
#endif
              else if(vv->len) {
                const char * sep = ngx_http_zip_strnrstr((const char*)file->filename.data, file->filename.len,
                                                         (const char*)vv->data, vv->len);
                if(sep) {
                    size_t utf8_len = file->filename.len - vv->len - (size_t)(sep - (const char *)file->filename.data);
                    file->filename_utf8.data = ngx_pnalloc(r->pool, utf8_len);
                    file->filename_utf8.len = utf8_len;
                    ngx_memcpy(file->filename_utf8.data, sep + vv->len, utf8_len);

                    file->filename.len -= utf8_len + vv->len;
                    file->filename_utf8_crc32 = ngx_crc32_long(file->filename_utf8.data, file->filename_utf8.len);
                } /* else { } */    // Separator not found. Okay, no extra field for this one then.
            }
        }

        if(offset >= (off_t) NGX_MAX_UINT32_VALUE)
            ctx->zip64_used = file->need_zip64_offset = 1;
        if(file->size >= (off_t) NGX_MAX_UINT32_VALUE) 
            ctx->zip64_used = file->need_zip64 = 1;

        ctx->cd_size += sizeof(ngx_zip_central_directory_file_header_t) + file->filename.len + sizeof(ngx_zip_extra_field_central_t) 
            + (file->need_zip64_offset ? 
                    (file->need_zip64 ? sizeof(ngx_zip_extra_field_zip64_sizes_offset_t) : sizeof(ngx_zip_extra_field_zip64_offset_only_t)) :
                    (file->need_zip64 ? sizeof(ngx_zip_extra_field_zip64_sizes_only_t) : 0) +
                    (ctx->unicode_path && file->filename_utf8.len ? (sizeof(ngx_zip_extra_field_unicode_path_t) + file->filename_utf8.len): 0)
              );

        header_piece = &ctx->pieces[piece_i++];
        header_piece->type = zip_header_piece;
        header_piece->file = file;
        header_piece->range.start = offset;
        header_piece->range.end = offset += sizeof(ngx_zip_local_file_header_t)
            + file->filename.len + sizeof(ngx_zip_extra_field_local_t) + (file->need_zip64? sizeof(ngx_zip_extra_field_zip64_sizes_only_t):0)
            + (ctx->unicode_path && file->filename_utf8.len ? (sizeof(ngx_zip_extra_field_unicode_path_t) + file->filename_utf8.len): 0);

        file_piece = &ctx->pieces[piece_i++];
        file_piece->type = zip_file_piece;
        file_piece->file = file;
        file_piece->range.start = offset;
        file_piece->range.end = offset += file->size; //!note: (sizeless chunks): we need file size here / or mark it and modify ranges after

        if (file->missing_crc32) { // if incomplete header -> add footer with that info to file
            trailer_piece = &ctx->pieces[piece_i++];
            trailer_piece->type = zip_trailer_piece;
            trailer_piece->file = file;
            trailer_piece->range.start = offset;
            trailer_piece->range.end = offset += file->need_zip64? sizeof(ngx_zip_data_descriptor_zip64_t) : sizeof(ngx_zip_data_descriptor_t);
            //!!TODO: if we want Ranges support - here we know it is impossible for this set
            //? check conf/some state and abort?
        }
    }

#ifdef NGX_ZIP_HAVE_ICONV
    if (iconv_cd) {
        iconv_close(iconv_cd);
    }
#endif

    ctx->zip64_used |= offset >= (off_t) NGX_MAX_UINT32_VALUE || ctx->files.nelts >= NGX_MAX_UINT16_VALUE;

    ctx->cd_size += sizeof(ngx_zip_end_of_central_directory_record_t);
    if (ctx->zip64_used)
        ctx->cd_size += sizeof(ngx_zip_zip64_end_of_central_directory_record_t) + sizeof(ngx_zip_zip64_end_of_central_directory_locator_t);


    cd_piece = &ctx->pieces[piece_i++];
    cd_piece->type = zip_central_directory_piece;
    cd_piece->range.start = offset;
    cd_piece->range.end = offset += ctx->cd_size;

    ctx->pieces_n = piece_i; //!! nasty hack (truncating allocated array without reallocation)

    ctx->archive_size = offset;

    return NGX_OK;
}
Пример #26
0
int git_path_iconv_init_precompose(git_path_iconv_t *ic)
{
    git_buf_init(&ic->buf, 0);
    ic->map = iconv_open(GIT_PATH_REPO_ENCODING, GIT_PATH_NATIVE_ENCODING);
    return 0;
}
Пример #27
0
static void
printSelBuf(FILE * fout, Atom sel_type, unsigned char *sel_buf, size_t sel_len)
{
#ifdef HAVE_ICONV
    Atom html = XInternAtom(dpy, "text/html", True);
#endif

    if (fverb == OVERBOSE) {	/* print in verbose mode only */
	char *atom_name = XGetAtomName(dpy, sel_type);
	fprintf(stderr, "Type is %s.\n", atom_name);
	XFree(atom_name);
    }

    if (sel_type == XA_INTEGER) {
	/* if the buffer contains integers, print them */
	long *long_buf = (long *) sel_buf;
	size_t long_len = sel_len / sizeof(long);
	while (long_len--)
	    fprintf(fout, "%ld\n", *long_buf++);
	return;
    }

    if (sel_type == XA_ATOM) {
	/* if the buffer contains atoms, print their names */
	Atom *atom_buf = (Atom *) sel_buf;
	size_t atom_len = sel_len / sizeof(Atom);
	while (atom_len--) {
	    char *atom_name = XGetAtomName(dpy, *atom_buf++);
	    fprintf(fout, "%s\n", atom_name);
	    XFree(atom_name);
	}
	return;
    }

#ifdef HAVE_ICONV
    if (html != None && sel_type == html) {
	/* if the buffer contains UCS-2 (UTF-16), convert to
	 * UTF-8.  Mozilla-based browsers do this for the
	 * text/html target.
	 */
	iconv_t cd;
	char *sel_charset = NULL;
	if (sel_buf[0] == 0xFF && sel_buf[1] == 0xFE)
	    sel_charset = "UTF-16LE";
	else if (sel_buf[0] == 0xFE && sel_buf[1] == 0xFF)
	    sel_charset = "UTF-16BE";

	if (sel_charset != NULL && (cd = iconv_open("UTF-8", sel_charset)) != (iconv_t) - 1) {
	    char *out_buf_start = malloc(sel_len), *in_buf = (char *) sel_buf + 2,
		*out_buf = out_buf_start;
	    size_t in_bytesleft = sel_len - 2, out_bytesleft = sel_len;

	    while (iconv(cd, &in_buf, &in_bytesleft, &out_buf, &out_bytesleft) == -1
		   && errno == E2BIG) {
		fwrite(out_buf_start, sizeof(char), sel_len - out_bytesleft, fout);
		out_buf = out_buf_start;
		out_bytesleft = sel_len;
	    }
	    if (out_buf != out_buf_start)
		fwrite(out_buf_start, sizeof(char), sel_len - out_bytesleft, fout);

	    free(out_buf_start);
	    iconv_close(cd);
	    return;
	}
    }
#endif

    /* otherwise, print the raw buffer out */
    fwrite(sel_buf, sizeof(char), sel_len, fout);
}
Пример #28
0
static rc_uint_type
wind_MultiByteToWideChar (rc_uint_type cp, const char *mb,
			  unichar *u, rc_uint_type u_len)
{
  rc_uint_type ret = 0;

#if defined (_WIN32) || defined (__CYGWIN__)
  rc_uint_type conv_flags = MB_PRECOMPOSED;

  /* MB_PRECOMPOSED is not allowed for UTF-7 or UTF-8.
     MultiByteToWideChar will set the last error to
     ERROR_INVALID_FLAGS if we do. */
  if (cp == CP_UTF8 || cp == CP_UTF7)
    conv_flags = 0;

  ret = (rc_uint_type) MultiByteToWideChar (cp, conv_flags,
					    mb, -1, u, u_len);
  /* Convert to bytes. */
  ret *= sizeof (unichar);

#elif defined (HAVE_ICONV)
  int first = 1;
  char tmp[32];
  char *p_tmp;
  const char *iconv_name = wind_iconv_cp (cp);

  if (!mb || !iconv_name)
    return 0;
  iconv_t cd = iconv_open ("UTF-16LE", iconv_name);

  while (1)
    {
      int iret;
      const char *n_mb = "";
      char *n_tmp = "";

      p_tmp = tmp;
      iret = iconv_onechar (cd, (ICONV_CONST char *) mb, p_tmp, 32, & n_mb, & n_tmp);
      if (first)
	{
	  first = 0;
	  continue;
	}
      if (!iret)
	{
	  size_t l_tmp = (size_t) (n_tmp - p_tmp);

	  if (u)
	    {
	      if ((size_t) u_len < l_tmp)
		break;
	      memcpy (u, tmp, l_tmp);
	      u += l_tmp/2;
	      u_len -= l_tmp;
	    }
	  ret += l_tmp;
	}
      else
	break;
      if (tmp[0] == 0 && tmp[1] == 0)
	break;
      mb = n_mb;
    }
  iconv_close (cd);
#else
  if (cp)
    ret = 0;
  ret = strlen (mb) + 1;
  ret *= sizeof (unichar);
  if (u != NULL && u_len != 0)
    {
      do
	{
	  *u++ = ((unichar) *mb) & 0xff;
	  --u_len; mb++;
	}
      while (u_len != 0 && mb[-1] != 0);
    }
  if (u != NULL && u_len != 0)
    *u = 0;
#endif
  return ret;
}
Пример #29
0
void
test(const char *from, const char *fromstr, int fromsize, const char *to, const char *tostr, int tosize, int errcode, int bufsize, int line)
{
    char outbuf[BUFSIZ];
    char *pin;
    char *pout;
    size_t inbytesleft;
    size_t outbytesleft;
    iconv_t cd;
    size_t r;
#ifdef USE_LIBICONV_DLL
    char dllpath[_MAX_PATH];
#endif

    cd = iconv_open(to, from);
    if (cd == (iconv_t)(-1))
    {
        printf("%s -> %s: NG: INVALID ENCODING NAME: line=%d\n", from, to, line);
        exit(1);
    }

#ifdef USE_LIBICONV_DLL
    if (((rec_iconv_t *)cd)->hlibiconv != NULL)
        GetModuleFileNameA(((rec_iconv_t *)cd)->hlibiconv, dllpath, sizeof(dllpath));

    if (use_dll && ((rec_iconv_t *)cd)->hlibiconv == NULL)
    {
        printf("%s: %s -> %s: NG: FAILED TO USE DLL: line=%d\n", dllpath, from, to, line);
        exit(1);
    }
    else if (!use_dll && ((rec_iconv_t *)cd)->hlibiconv != NULL)
    {
        printf("%s: %s -> %s: NG: DLL IS LOADED UNEXPECTEDLY: line=%d\n", dllpath, from, to, line);
        exit(1);
    }
#endif

    errno = 0;

    pin = (char *)fromstr;
    pout = outbuf;
    inbytesleft = fromsize;
    outbytesleft = bufsize;
    r = iconv(cd, &pin, &inbytesleft, &pout, &outbytesleft);
    if (r != (size_t)(-1))
        r = iconv(cd, NULL, NULL, &pout, &outbytesleft);
    *pout = 0;

#ifdef USE_LIBICONV_DLL
    if (use_dll)
        printf("%s: ", dllpath);
#endif
    printf("%s(%s) -> ", from, tohex(fromstr, fromsize));
    printf("%s(%s%s%s): ", to, tohex(tostr, tosize),
            errcode == 0 ? "" : ":",
            errcode == 0 ? "" : errstr(errcode));
    if (strcmp(outbuf, tostr) == 0 && errno == errcode)
        printf("OK\n");
    else
    {
        printf("RESULT(%s:%s): ", tohex(outbuf, sizeof(outbuf) - outbytesleft),
                errstr(errno));
        printf("NG: line=%d\n", line);
        exit(1);
    }
}
Пример #30
0
int my_xmlStrncopy(char ** out, const char * in, int len)
{
	if(in) {
		size_t lin=0;
		size_t lout=0;
		int l1=0;
		int l2=0;
		int retval=1;
		char *inbuf;
		char *inbuf2;
		char *outbuf;
		char *outbuf2;
		
		lin=strlen(in);
		l2=xmlUTF8Strlen((xmlChar*)in);
		
		if(l2<0) lout=l1;
		else if (len>0 && len<l2) lout=len;
		else lout=l2;
		
		inbuf=inbuf2=(char *)malloc((lin+1)*sizeof(char));
		outbuf=outbuf2=(char *)malloc((lout+1)*sizeof(char));

		memcpy(inbuf,in,lin);

		l1=lin;
		l2=lout;

#ifndef LINUX
		if(my_UTF8Toisolat1(&outbuf2,&lout,(const char **)&inbuf2,&lin)<0) {
#else
		if(my_UTF8Toisolat1(&outbuf2,&lout,&inbuf2,&lin)<0) {
#endif
			retval=-1;
		}

		free(inbuf);

		outbuf[l2]=0;

		if(*out) {
			memcpy(*out,outbuf,l2+1);
			free(outbuf);
		} else {
			*out=outbuf;
		}

		return retval<0?-1:l2;
	} else return -1;
}

#ifndef LINUX
int my_UTF8Toisolat1(char **dest, size_t * lu, const char **src, size_t * l)
#else
int my_UTF8Toisolat1(char **dest, size_t * lu, char **src, size_t * l)
#endif
{
	iconv_t t=iconv_open("ISO_8859-1","UTF-8");

	iconv(t, src, l, dest, lu);

	iconv_close(t);
	return 1;
}