src/hidapi/android/hid.cpp
changeset 12346 b4c98c84a0b2
parent 12308 4e3b4ddb8787
child 12765 80586f864508
equal deleted inserted replaced
12345:50e1cca28b39 12346:b4c98c84a0b2
    12 #include <errno.h>	// For ETIMEDOUT and ECONNRESET
    12 #include <errno.h>	// For ETIMEDOUT and ECONNRESET
    13 #include <stdlib.h> // For malloc() and free()
    13 #include <stdlib.h> // For malloc() and free()
    14 #include <string.h>	// For memcpy()
    14 #include <string.h>	// For memcpy()
    15 
    15 
    16 #define TAG "hidapi"
    16 #define TAG "hidapi"
       
    17 
       
    18 // Have error log always available
       
    19 #define LOGE(...) __android_log_print(ANDROID_LOG_ERROR, TAG, __VA_ARGS__)
       
    20 
    17 #ifdef DEBUG
    21 #ifdef DEBUG
    18 #define LOGV(...) __android_log_print(ANDROID_LOG_VERBOSE, TAG, __VA_ARGS__)
    22 #define LOGV(...) __android_log_print(ANDROID_LOG_VERBOSE, TAG, __VA_ARGS__)
    19 #define LOGD(...) __android_log_print(ANDROID_LOG_DEBUG, TAG, __VA_ARGS__)
    23 #define LOGD(...) __android_log_print(ANDROID_LOG_DEBUG, TAG, __VA_ARGS__)
    20 #else
    24 #else
    21 #define LOGV(...)
    25 #define LOGV(...)
   396 	hid_device *GetDevice()
   400 	hid_device *GetDevice()
   397 	{
   401 	{
   398 		return m_pDevice;
   402 		return m_pDevice;
   399 	}
   403 	}
   400 
   404 
       
   405 	void ExceptionCheck( JNIEnv *env, const char *pszMethodName )
       
   406 	{
       
   407 		if ( env->ExceptionCheck() )
       
   408 		{
       
   409 			// Get our exception
       
   410 			jthrowable jExcept = env->ExceptionOccurred();
       
   411 
       
   412 			// Clear the exception so we can call JNI again
       
   413 			env->ExceptionClear();
       
   414 
       
   415 			// Get our exception message
       
   416 			jclass jExceptClass = env->GetObjectClass( jExcept );
       
   417 			jmethodID jMessageMethod = env->GetMethodID( jExceptClass, "getMessage", "()Ljava/lang/String;" );
       
   418 			jstring jMessage = (jstring)( env->CallObjectMethod( jExcept, jMessageMethod ) );
       
   419 			const char *pszMessage = env->GetStringUTFChars( jMessage, NULL );
       
   420 
       
   421 			// ...and log it.
       
   422 			LOGE( "CHIDDevice::%s threw an exception: %s", pszMethodName, pszMessage );
       
   423 
       
   424 			// Cleanup
       
   425 			env->ReleaseStringUTFChars( jMessage, pszMessage );
       
   426 			env->DeleteLocalRef( jMessage );
       
   427 			env->DeleteLocalRef( jExceptClass );
       
   428 			env->DeleteLocalRef( jExcept );
       
   429 		}
       
   430 	}
       
   431 
   401 	bool BOpen()
   432 	bool BOpen()
   402 	{
   433 	{
   403 		// Make sure thread is attached to JVM/env
   434 		// Make sure thread is attached to JVM/env
   404 		JNIEnv *env;
   435 		JNIEnv *env;
   405 		g_JVM->AttachCurrentThread( &env, NULL );
   436 		g_JVM->AttachCurrentThread( &env, NULL );
   406 		pthread_setspecific( g_ThreadKey, (void*)env );
   437 		pthread_setspecific( g_ThreadKey, (void*)env );
   407 
   438 
   408 		m_bIsWaitingForOpen = false;
   439 		m_bIsWaitingForOpen = false;
   409 		m_bOpenResult = env->CallBooleanMethod( g_HIDDeviceManagerCallbackHandler, g_midHIDDeviceManagerOpen, m_nId );
   440 		m_bOpenResult = env->CallBooleanMethod( g_HIDDeviceManagerCallbackHandler, g_midHIDDeviceManagerOpen, m_nId );
       
   441 		ExceptionCheck( env, "BOpen" );
   410 
   442 
   411 		if ( m_bIsWaitingForOpen )
   443 		if ( m_bIsWaitingForOpen )
   412 		{
   444 		{
   413 			hid_mutex_guard cvl( &m_cvLock );
   445 			hid_mutex_guard cvl( &m_cvLock );
   414 
   446 
   513 		g_JVM->AttachCurrentThread( &env, NULL );
   545 		g_JVM->AttachCurrentThread( &env, NULL );
   514 		pthread_setspecific( g_ThreadKey, (void*)env );
   546 		pthread_setspecific( g_ThreadKey, (void*)env );
   515 
   547 
   516 		jbyteArray pBuf = NewByteArray( env, pData, nDataLen );
   548 		jbyteArray pBuf = NewByteArray( env, pData, nDataLen );
   517 		int nRet = env->CallIntMethod( g_HIDDeviceManagerCallbackHandler, g_midHIDDeviceManagerSendOutputReport, m_nId, pBuf );
   549 		int nRet = env->CallIntMethod( g_HIDDeviceManagerCallbackHandler, g_midHIDDeviceManagerSendOutputReport, m_nId, pBuf );
       
   550 		ExceptionCheck( env, "SendOutputReport" );
       
   551 
   518 		env->DeleteLocalRef( pBuf );
   552 		env->DeleteLocalRef( pBuf );
   519 		return nRet;
   553 		return nRet;
   520 	}
   554 	}
   521 
   555 
   522 	int SendFeatureReport( const unsigned char *pData, size_t nDataLen )
   556 	int SendFeatureReport( const unsigned char *pData, size_t nDataLen )
   526 		g_JVM->AttachCurrentThread( &env, NULL );
   560 		g_JVM->AttachCurrentThread( &env, NULL );
   527 		pthread_setspecific( g_ThreadKey, (void*)env );
   561 		pthread_setspecific( g_ThreadKey, (void*)env );
   528 
   562 
   529 		jbyteArray pBuf = NewByteArray( env, pData, nDataLen );
   563 		jbyteArray pBuf = NewByteArray( env, pData, nDataLen );
   530 		int nRet = env->CallIntMethod( g_HIDDeviceManagerCallbackHandler, g_midHIDDeviceManagerSendFeatureReport, m_nId, pBuf );
   564 		int nRet = env->CallIntMethod( g_HIDDeviceManagerCallbackHandler, g_midHIDDeviceManagerSendFeatureReport, m_nId, pBuf );
       
   565 		ExceptionCheck( env, "SendFeatureReport" );
   531 		env->DeleteLocalRef( pBuf );
   566 		env->DeleteLocalRef( pBuf );
   532 		return nRet;
   567 		return nRet;
   533 	}
   568 	}
   534 
   569 
   535 	void ProcessFeatureReport( const uint8_t *pBuf, size_t nBufSize )
   570 	void ProcessFeatureReport( const uint8_t *pBuf, size_t nBufSize )
   562 			m_bIsWaitingForFeatureReport = true;
   597 			m_bIsWaitingForFeatureReport = true;
   563 		}
   598 		}
   564 
   599 
   565 		jbyteArray pBuf = NewByteArray( env, pData, nDataLen );
   600 		jbyteArray pBuf = NewByteArray( env, pData, nDataLen );
   566 		int nRet = env->CallBooleanMethod( g_HIDDeviceManagerCallbackHandler, g_midHIDDeviceManagerGetFeatureReport, m_nId, pBuf ) ? 0 : -1;
   601 		int nRet = env->CallBooleanMethod( g_HIDDeviceManagerCallbackHandler, g_midHIDDeviceManagerGetFeatureReport, m_nId, pBuf ) ? 0 : -1;
       
   602 		ExceptionCheck( env, "GetFeatureReport" );
   567 		env->DeleteLocalRef( pBuf );
   603 		env->DeleteLocalRef( pBuf );
   568 		if ( nRet < 0 )
   604 		if ( nRet < 0 )
   569 		{
   605 		{
   570 			LOGV( "GetFeatureReport failed" );
   606 			LOGV( "GetFeatureReport failed" );
   571 			m_bIsWaitingForFeatureReport = false;
   607 			m_bIsWaitingForFeatureReport = false;
   620 		JNIEnv *env;
   656 		JNIEnv *env;
   621 		g_JVM->AttachCurrentThread( &env, NULL );
   657 		g_JVM->AttachCurrentThread( &env, NULL );
   622 		pthread_setspecific( g_ThreadKey, (void*)env );
   658 		pthread_setspecific( g_ThreadKey, (void*)env );
   623 
   659 
   624 		env->CallVoidMethod( g_HIDDeviceManagerCallbackHandler, g_midHIDDeviceManagerClose, m_nId );
   660 		env->CallVoidMethod( g_HIDDeviceManagerCallbackHandler, g_midHIDDeviceManagerClose, m_nId );
   625 
   661 		ExceptionCheck( env, "Close" );
       
   662 	
   626 		hid_mutex_guard dataLock( &m_dataLock );
   663 		hid_mutex_guard dataLock( &m_dataLock );
   627 		m_vecData.clear();
   664 		m_vecData.clear();
   628 
   665 
   629 		// Clean and release pending feature report reads
   666 		// Clean and release pending feature report reads
   630 		hid_mutex_guard cvLock( &m_cvLock );
   667 		hid_mutex_guard cvLock( &m_cvLock );