FREObject updateData(FREContext ctx, void* funcData, uint32_t argc, FREObject argv[])
	{

		int numMessages = messageQueue.size();
		
		//printf("Update data, num messages : %i",numMessages);
		FREObject result = NULL;

		try
		{
			
			FRENewObject((const uint8_t *)"Vector.<benkuper.nativeExtensions.MIDIMessage>",0,NULL,&result,NULL);

			FRESetArrayLength(result,numMessages);

			for(int i=0;i<numMessages;i++)
			{
			
				FRESetArrayElementAt(result,i,messageToFre(messageQueue[i]));
			}

			
		}catch(std::exception e)
		{
			printf("### Error updating data : %s\n",e.what());
		}
		
		messageQueue.clear();

		return result;
	}
FREObject FREArray(uint32_t length) {
	FREObject array;
	FRENewObject((const uint8_t*)"Array", 0, NULL, &array, NULL);
	FRESetArrayLength(array, length);

	return array;
}
 virtual void setWorldTransform(const btTransform &worldTrans) {
     printShit("Should set transform...");
     FREObject raw, trans;
     FRENewObject((uint8_t*)"Vector.<Number>", 0, NULL, &raw, NULL);
     FRESetArrayLength(raw, 16);
     
     btScalar data[16];
     worldTrans.getOpenGLMatrix(data);
     printShit("Data: ");
     print16scalars(data);
     for (int i=0; i < 16; i++) {
         FREObject val;
         printResult(FRENewObjectFromDouble(double(data[i]), &val), "Make double", false);
         printResult(FRESetArrayElementAt(raw, i, val), "Set arr elem", false);
     }
     printResult(FRENewObject((uint8_t*)"flash.geom.Matrix3D", 0, NULL, &trans, NULL), "New Mat3D", false);
     printResult(FRESetObjectProperty(trans, (uint8_t*)"rawData", raw, NULL), "Set rawData", false);
     printResult(FRESetObjectProperty(skin, (uint8_t*)"transform", trans, NULL), "Set transform", false);
 }
	FREObject listInputDevices(FREContext ctx, void* funcData, uint32_t argc, FREObject argv[])
	{
		FREObject result = NULL;
		FRENewObject((const uint8_t *)"Vector.<benkuper.nativeExtensions.MIDIDeviceIn>",0,NULL,&result,NULL);

	    unsigned int nPorts = midiin->getPortCount();

		//printf("Native MIDI :: listInputDevices > %i devices detected :\n",nPorts);

		FRESetArrayLength(result,nPorts);
		
		// Check inputs.
		std::string portName;

		for ( unsigned int i=0; i<nPorts; i++ ) {
			try {
				portName = midiin->getPortName(i);
			}
			catch ( RtMidiError &error ) {
				error.printMessage();
				// return NULL;
			}

			//std::cout << "  Input Port #" << i+1 << ": " << portName << '\n';
			//printf("[%i] %s\n",i,portName.c_str());

			FREObject args[1];
			FREObject portFRE = NULL;
			FRENewObjectFromUTF8(portName.size(),(const uint8_t*)portName.c_str(),&portFRE);
			args[0] = portFRE;

			FREObject curPort = NULL;
			FREObject exc = NULL;
			FREResult fre =  FRENewObject((const uint8_t *)"benkuper.nativeExtensions.MIDIDeviceIn",1,args,&curPort,&exc);
			//printf("FREResult = %i",fre);

			FRESetArrayElementAt(result,i,curPort);
		}

		return result;

	}
FREObject getBytesAsArray(FREContext ctx, void* funcData, uint32_t argc, FREObject argv[])
{
	FREObject result;

	FRENewObject((const uint8_t*) "Array", 0, NULL, &result, NULL);
	FRESetArrayLength(result, bufferSize - 1);

	FREObject myChar;
	int i;

	pthread_mutex_lock(&safety);
	for (i = 0; i < bufferSize; i++)
	{
		FRENewObjectFromUTF8(1, (unsigned char *)buffer + i, &myChar);
		FRESetArrayElementAt(result, i, myChar);
	}

	bufferSize = 0;
	sentEvent = 0;
	pthread_mutex_unlock(&safety);

	return result;
}
FREObject getSuggestions(FREContext ctx, void* funcData, uint32_t argc, FREObject argv[]) {
	const uint8_t *locale = 0;
	const uint8_t *inpWord = 0;
	uint32_t len = -1;
	FREObject retObj=0;
	FREObject oneSuggestion=0;

	U16Char_t* inpWordU16 = NULL;
	std::string  inpWordDictEncoded;
	bool isConversionUnSuccesful=false;
	char * oneSuggestionEncoded=NULL;
	U16Char_t * oneSuggestionU16=NULL;
	std::string oneSuggestionU8;

	//assign memory to retobj
	FRENewObject((const uint8_t*)"Array", 0, NULL, &retObj, 0);

	//get first argument
	if(FREGetObjectAsUTF8(argv[1], &len, &locale) != FRE_OK)
	return retObj;
	len = 0;
	
	//get second argument
	if(FREGetObjectAsUTF8(argv[0], &len, &inpWord) != FRE_OK)
	return retObj;
	
	//get the hunspell object from cache
	Hunspell * hunspellObject=getHunspellObject(std::string((char *)locale));
		
	if(!hunspellObject) return retObj;
	
	//convert input utf8 to u16 string
	inpWordU16 = EncConv::convCharStrToU16Str((char *)inpWord, "UTF-8");

	//get dictionary encoding
	HUNSPELL_GET_ENCODING getEncAdd=(HUNSPELL_GET_ENCODING) GetProcAddress(hinstLib, "hunspell_get_dic_encoding");
	char * m_MainEncoding= (getEncAdd)(hunspellObject);

	//convert u16 to dictionary encoding
	inpWordDictEncoded=EncConv::convU16StrToCharStr(inpWordU16,m_MainEncoding);

	if(inpWordDictEncoded.length()==0)
	{
		isConversionUnSuccesful = true;
	}

	//get suggestAddress &freelistAddress
	HUNSPELL_SUGGEST suggestAdd= (HUNSPELL_SUGGEST) GetProcAddress(hinstLib, "hunspell_suggest");
	HUNSPELL_FREE_LIST freeListAdd= (HUNSPELL_FREE_LIST) GetProcAddress(hinstLib, "hunspell_free_list");
	
	char** suggList = NULL;
	int numSugg = 0;

	//Try getting suggestions with encoded word else try with UTF8
	if(suggestAdd && !isConversionUnSuccesful)
	{
		numSugg = (suggestAdd)(hunspellObject,(char *) (inpWordDictEncoded.c_str()),&suggList);
	}
	else
	{
		numSugg = (suggestAdd)(hunspellObject,(char *) (inpWord),&suggList);
	}
	

	if(numSugg)
				{
					FRESetArrayLength( retObj, numSugg );
					
					for(int iCount=0; iCount <numSugg; iCount++)
					{
						oneSuggestionEncoded=suggList[iCount];
						oneSuggestionU16=EncConv::convCharStrToU16Str(oneSuggestionEncoded, m_MainEncoding);
						oneSuggestionU8= EncConv::convU16StrToCharStr(oneSuggestionU16, "UTF-8");
						FRENewObjectFromUTF8((uint32_t)(oneSuggestionU8.length()),(const uint8_t*)(oneSuggestionU8.c_str()), &oneSuggestion);
						FRESetArrayElementAt(retObj, iCount, oneSuggestion);
						EncConv::releaseU16Str(oneSuggestionU16);
					}
					(freeListAdd)(hunspellObject, &suggList,numSugg);
					
				}
	EncConv::releaseU16Str(inpWordU16);
	return retObj;
}