Exemplo n.º 1
0
static int appendGServiceArrayCount()
{

	int size=(g_services_counts+DEFAULT_SERVICE_SIZE)*sizeof(struct TGService *);
	struct TGService ** _ppservices=(struct TGService **)malloc(size);
	logI(TAG," malloc service array from %d to %d", (long) & _ppservices[0],(long)&_ppservices[g_services_counts+DEFAULT_SERVICE_SIZE]);
	if(_ppservices==NULL)
	{
		return -1;
	}

	if(g_services==NULL)
	{
		logI(TAG," initilize service array space");
		g_services=_ppservices;
	}
	else
	{
		memcpy(_ppservices,g_services,g_services_counts*sizeof(struct TGService *));
		free(g_services);
		g_services=_ppservices;
	}

	g_services_counts+=DEFAULT_SERVICE_SIZE;

	return 0;
}
Exemplo n.º 2
0
int main(int argc,char ** argv)
{
	//set log level first
	setenv("LOG_LEVEL","2",1);
	char ** ppHead=argv;
	while(ppHead!=NULL && *ppHead!=NULL)
	{
		if(strcmp(*ppHead,"-h")==0)
		{
			printHelp();
			exit(0);
		}
		ppHead++;
	}
	int ret=init_context(argc,argv);
	logI("MAIN","================init context complete===============\n");
	if(ret==-1)
	{
		release();
		printHelp();
		exit(1);
			
	}
	
	init_plugin(argc,argv);
	logI("MAIN","================init plugins complete===============\n");

	startup();
	
	return 0;
}
Exemplo n.º 3
0
static int readCommonOem()
{
    logI("readCommonOem ln=%d",__LINE__);
    static int isRead=0;
    if(isRead==1)
        return 0;
logI("readCommonOem ln=%d",__LINE__);
    sortOemItemDres();
    isRead=1;
    FILE* fp;
    fp = fopen(gOemItemDres[CAMERA_OEM_COMMON].path, "rb");

    if(fp==0)
    {
logI("readCommonOem ln=%d",__LINE__);
        gIsOemExist=0;
        fillDefaultOemComm(&gCamCommon);
        return 0;
    }
    else
        gIsOemExist=1;
logI("readCommonOem ln=%d",__LINE__);
    int r;
    int err=0;
    r = fread(&gCamCommon, 1, sizeof(OEM_CAMERA_COMMON), fp);
    if(r!=sizeof(OEM_CAMERA_COMMON))
        err=e_OemErr_FileErr;
    fclose(fp);
    return err;
}
Exemplo n.º 4
0
void init()
{

/**	int size=sizeof(TGClient*) * DEFAULT_MAX_CLIENTS;
	clients_ar_size=DEFAULT_MAX_CLIENTS;
	g_clients=(TGClient **) malloc(size);
	memset(g_clients,0,size);
	
**/
	//init client array
	appendClient();
	logI(TAG," server clients initialiezd");

	// init context
	int size=sizeof(TGContext);
	g_context=(TGContext *)malloc(size);
	memset(g_context,0,size);
	logI(TAG," server context initialized");
	
	size=sizeof(TGServer);
	g_context->pServer=(TGServer *)malloc(size);
	memset(g_context->pServer,0,size);
	// init default value
	g_context->pServer->port=DEFAULT_LISTEN_PORT;
	g_context->pServer->maxClients=DEFAULT_MAX_CLIENTS;
	logI(TAG," server info initialized");
}
static int closeFlash(void)
{
    int i;
	int j;
	int k;
	logI("closeFlash ln=%d",__LINE__);
	for(i=0;i<e_Max_Sensor_Dev_Num;i++)
	{
	    //logI("closeFlash ln=%d %d",__LINE__,i);
    	for(j=0;j<e_Max_Strobe_Num_Per_Dev;j++)
    	{
    	    //logI("closeFlash ln=%d %d",__LINE__,j);
        	for(k=0;k<e_Max_Part_Num_Per_Dev;k++)
        	{
        	    //logI("closeFlash ln=%d %d %d",__LINE__,k, (int)g_pFlashInitFunc[i][j][k]);
        		if(g_pFlashInitFunc[i][j][k]!=0)
        		{
        		    logI("closeFlash i,j,k %d %d %d", i, j, k);
            		g_pFlashInitFunc[i][j][k]->flashlight_ioctl(FLASH_IOC_SET_ONOFF, 0);
        		}
        	}
        }
    }
	return 0;
}
Exemplo n.º 6
0
int OemCamDrv::isOemAvailable()
{
    logI("isOemAvailable ln=%d",__LINE__);
    Mutex::Autolock _l(gLock);
    int type;
    type = cust_getCamParaType();
    if(type == e_CamParaTypeOem)
    {
        int err;
        err = readCommonOem();
        if(gIsOemExist==0 || err!=0)
        {
            logI("isOemAvailable ln=%d isAvailable=%d",__LINE__,0);
            return 0;
        }
        else
        {
            logI("isOemAvailable ln=%d isAvailable=%d",__LINE__,1);
            return 1;
        }
    }
    else
    {
        logI("isOemAvailable ln=%d isAvailable=%d",__LINE__,0);
        return 0;
    }
};
Exemplo n.º 7
0
// when client connection is established
// this function is called by client process
// Note: this function never is called in main process
void initAllServices()
{
	if(g_services!=NULL)
	{
		struct TGService ** ppHead=g_services;
		struct TGService * pS=NULL;
		while((pS=*ppHead++)!=NULL)
		{
			logI(TAG," start to initialize service:%s parameters:%s",pS->serviceName,pS->parameters);
			pS->do_init(pS->parameters);
			logI(TAG," finish initializeing service:%s",pS->serviceName);
		}
	}
}
Exemplo n.º 8
0
void bat_oc_protection_powerlimit(BATTERY_OC_LEVEL level)
{
    logI("bat_oc_protection_powerlimit %d (%d %d %d)\n", level, BATTERY_OC_LEVEL_0, BATTERY_OC_LEVEL_1,__LINE__);
    logI("bat_oc_protection_powerlimit %d (%d %d %d)\n", level, BATTERY_OC_LEVEL_0, BATTERY_OC_LEVEL_1,__LINE__);
    if (level == BATTERY_OC_LEVEL_1){
        // battery OC trigger CPU Limit to under 4 X 0.8G
        closeFlash();
        gLowPowerOc=BATTERY_OC_LEVEL_1;
    }
    else{
        //unlimit cpu and gpu
        gLowPowerOc=BATTERY_OC_LEVEL_0;
    }
}
Exemplo n.º 9
0
// when client connection is closed
// this function is called by client process
// Note: this function never is called in main process
void releaseAllServices()
{
	if(g_services!=NULL)
	{
		struct TGService ** ppHead=g_services;
		struct TGService * pS=NULL;
		while((pS=*ppHead++)!=NULL)
		{
			logI(TAG," start to release service:%s",pS->serviceName);
			pS->do_release(pS->pGlobalData);	
			logI(TAG," finish releaseing service:%s",pS->serviceName);
		}
	}
}
Exemplo n.º 10
0
int FlashPlineTool::searchAePlineIndex(int* ind, strAETable* pAE, int exp, int afe, int isp)
{
    int i;
    int minErr;
    int sz;
    int bestInd=0;
    double expLevTar;
    expLevTar = (double)exp*afe*isp/(1024*1024);
    minErr=expLevTar;
    sz = (int)pAE->u4TotalIndex;
    for(i=0; i<sz; i++)
    {
        int expLev;
        int exp;
        int afe;
        int isp;
        double dif;
        exp = pAE->pCurrentTable->sPlineTable[i].u4Eposuretime;
        afe = pAE->pCurrentTable->sPlineTable[i].u4AfeGain;
        isp = pAE->pCurrentTable->sPlineTable[i].u4IspGain;
        expLev = (double)exp*afe*isp/(1024*1024);
        dif=expLev-expLevTar;
        if(dif<0)
            dif=-dif;
        if(minErr>dif)
        {
            minErr=dif;
            bestInd=i;
        }
    }
    logI("bestMatchIndex: %d", bestInd);
    *ind = bestInd;
    return 0;
}
Exemplo n.º 11
0
int StrobeGlobalDriver::uninit(int sensorDev, int strobeId)
{
    logI("uninit dev=%d id=%d", sensorDev, strobeId);
	Mutex::Autolock lock(mLock);
	closekd_nolock();
	return 0;
}
MINT32 default_flashlight_ioctl(unsigned int cmd, unsigned long arg) {
    int i4RetValue = 0;
    int iFlashType = (int)FLASHLIGHT_NONE;
    kdStrobeDrvArg kdArg;
	unsigned long copyRet;
    copyRet = copy_from_user(&kdArg , (void *)arg , sizeof(kdStrobeDrvArg));


    switch(cmd)
    {
        case FLASHLIGHTIOC_G_FLASHTYPE:
            iFlashType = FLASHLIGHT_NONE;
            kdArg.arg = iFlashType;
            if(copy_to_user((void __user *) arg , (void*)&kdArg , sizeof(kdStrobeDrvArg)))
			{
				logE("[FLASHLIGHTIOC_G_FLASHTYPE] ioctl copy to user failed ~");
				return -EFAULT;
			}
            break;
    	default :
    		logI("[default_flashlight_ioctl] ~");
    		break;
    }
    return i4RetValue;
}
Exemplo n.º 13
0
static void releaseClient(TGClient * pClient)
{
	if(pClient!=NULL)
	{
		if(pClient->sockfd>=0)
		{
			logI(TAG," shut down client connection:%s",pClient->clientIP);
#ifdef LINUX
			shutdown(pClient->sockfd,SHUT_RDWR);
#elif WIN32
			close(pClient->sockfd);
#endif
		}
		
		if(pClient->readPipe>=0)
		{
			close(pClient->readPipe);
		}
		if(pClient->writePipe>=0)
		{
			close(pClient->writePipe);
		}
		if(pClient->clientIP!=NULL)
		{
			free(pClient->clientIP);
		}
		memset(pClient,0,sizeof(TGClient));
		free(pClient);
	}
}
static long my_ioctl_compat(struct file *filep, unsigned int cmd, unsigned long arg)
{
    logI("flash my_ioctl_compat2 line=%d cmd=%d arg=%ld \n",__LINE__,cmd,arg);
	int err;
	//int copyRet;
	kdStrobeDrvArg* pUObj;
	pUObj = compat_ptr(arg);

    /*
	kdStrobeDrvArg* pUObj;
	pUObj = compat_ptr(arg);
	kdStrobeDrvArg obj;
	copyRet = copy_from_user(&obj , (void *)pUObj , sizeof(kdStrobeDrvArg));
    logI("strobe arg %d %d %d\n", obj.sensorDev, obj.strobeId, obj.arg);
    obj.arg = 23411;
    copy_to_user((void __user *) arg , (void*)&obj , sizeof(kdStrobeDrvArg));
    */




	//data = compat_alloc_user_space(sizeof(*data));
	//if (sys_data == NULL)
		//    return -EFAULT;
    //err = compat_arg_struct_user32_to_kernel(data32, data);
    //arg2 = (unsigned long)data32;
    err = flashlight_ioctl_core(filep, cmd, pUObj);

    return err;

}
Exemplo n.º 15
0
bool ida_iatt_combine(struct iatt * dst, struct iatt * src1,
                      struct iatt * src2)
{
    size_t blksize, blocks1, blocks2;

    if (src1->ia_blksize == src2->ia_blksize)
    {
        blksize = src1->ia_blksize;
        blocks1 = src1->ia_blocks;
        blocks2 = src2->ia_blocks;
    }
    else if (src1->ia_blksize < src2->ia_blksize)
    {
        blksize = src2->ia_blksize;
        blocks2 = src2->ia_blocks;
        blocks1 = (src1->ia_blocks * src1->ia_blksize + blksize - 1) / blksize;
    }
    else
    {
        blksize = src1->ia_blksize;
        blocks1 = src1->ia_blocks;
        blocks2 = (src2->ia_blocks * src2->ia_blksize + blksize - 1) / blksize;
    }

    if ((src1->ia_ino != src2->ia_ino) ||
//        ((src1->ia_ino != 1) && (src1->ia_nlink != src2->ia_nlink)) ||
        (src1->ia_uid != src2->ia_uid) ||
        (src1->ia_gid != src2->ia_gid) ||
        (src1->ia_rdev != src2->ia_rdev) ||
        (st_mode_from_ia(src1->ia_prot, src1->ia_type) !=
         st_mode_from_ia(src2->ia_prot, src2->ia_type)) ||
// Only check size for regular files. Directories can be identical in contents
// but have different sizes.
        ((src1->ia_type == IA_IFREG) && (src1->ia_size != src2->ia_size)) ||
        (uuid_compare(src1->ia_gfid, src2->ia_gfid) != 0))
    {
        logI("IDA: iatt combine failed (%lu, %u, %u, %u, %lu, %lu, %X), "
             "(%lu, %u, %u, %u, %lu, %lu, %X)",
             src1->ia_ino, src1->ia_nlink, src1->ia_uid, src1->ia_gid,
             src1->ia_rdev, src1->ia_size, st_mode_from_ia(src1->ia_prot, src1->ia_type),
             src2->ia_ino, src2->ia_nlink, src2->ia_uid, src2->ia_gid,
             src2->ia_rdev, src2->ia_size, st_mode_from_ia(src2->ia_prot, src2->ia_type));
        return false;
    }

    *dst = *src1;

    dst->ia_blksize = blksize;
    dst->ia_blocks = blocks1 + blocks2;

    ida_iatt_time_merge(&dst->ia_atime, &dst->ia_atime_nsec, src2->ia_atime,
                        src2->ia_atime_nsec);
    ida_iatt_time_merge(&dst->ia_mtime, &dst->ia_mtime_nsec, src2->ia_mtime,
                        src2->ia_mtime_nsec);
    ida_iatt_time_merge(&dst->ia_ctime, &dst->ia_ctime_nsec, src2->ia_ctime,
                        src2->ia_ctime_nsec);

    return true;
}
static int flashlight_release(struct inode *inode, struct file *file)
{
    logI("[flashlight_release] E ~");

	checkAndRelease();

    return 0;
}
Exemplo n.º 17
0
// when server is starting up 
// server call this function for initialize all service 
void createAllServices()
{
	int count=0;
	if(g_services!=NULL)
	{	
		struct TGService ** ppHead=g_services;
		struct TGService * pS=NULL;
		while((pS=*ppHead++)!=NULL)
		{
			logI(TAG," start to creat service:%s",pS->serviceName);
			void * pData=pS->do_create(pS->parameters);	
			pS->pGlobalData=pData;
			logI(TAG," finish creating service:%s",pS->serviceName);
			count++;
		}
	}
}
static void bat_per_protection_powerlimit_flashlight(BATTERY_PERCENT_LEVEL level)
{
    logI("bat_per_protection_powerlimit_flashlight %d (%d %d %d)\n", level, BATTERY_PERCENT_LEVEL_0, BATTERY_PERCENT_LEVEL_1,__LINE__);
    logI("bat_per_protection_powerlimit_flashlight %d (%d %d %d)\n", level, BATTERY_PERCENT_LEVEL_0, BATTERY_PERCENT_LEVEL_1,__LINE__);
    if (level == BATTERY_PERCENT_LEVEL_0)
    {
        gLowPowerPer=BATTERY_PERCENT_LEVEL_0;
    }
    else if(level == BATTERY_PERCENT_LEVEL_1)
    {
        decFlash();
        gLowPowerPer=BATTERY_PERCENT_LEVEL_1;
    }
    else
    {
        //unlimit cpu and gpu
    }
}
Exemplo n.º 19
0
static void addService(struct TGService * pSer)
{
	if(pSer==NULL)
	{
		return;
	}
	//FIXME linked list or array?
	if(g_services==NULL)
	{
		logI(TAG," create new space for service array");
		appendGServiceArrayCount();
		g_services[0]=pSer;
		return;
	}
	else
	{
		int i=0;
		for(i=0;i<g_services_counts;i++)
		{
			struct TGService * pS=g_services[i];
			if(pS==NULL)
			{
				g_services[i]=pSer;
				logI(TAG,"load library: id:%d name:%s",pSer->sID,pSer->serviceName);
				return;
			}
		}
		
		//if still not return, means the array is full.
		// we need append space,
		if(appendGServiceArrayCount()==0)
		{
			g_services[i]=pSer;
			logI(TAG,"load library: id:%d name:%s",pSer->sID,pSer->serviceName);
		}
		else
		{
			logE(TAG,"can not push service in to array. cause by: malloc space error");
		}
	}
}
static int flashlight_open(struct inode *inode, struct file *file)
{
	int i4RetValue = 0;
	static int bInited=0;
	if(bInited==0)
	{
		globalInit();
		bInited=1;
	}
    logI("[flashlight_open] E ~");
    return i4RetValue;
}
Exemplo n.º 21
0
int StrobeGlobalDriver::init(int sensorDev, int strobeId)
{
    logI("init dev=%d id=%d", sensorDev, strobeId);
    Mutex::Autolock lock(mLock);
    openkd_nolock();
	int err;
	err = sendCommand_nolock(FLASHLIGHTIOC_X_SET_DRIVER, sensorDev, strobeId, 0);
	if(err!=0)
	{
        logE("FLASHLIGHTIOC_X_SET_DRIVER kd_err=%d", err);
		return StrobeDrv::STROBE_UNKNOWN_ERROR;
    }
	return 0;
}
Exemplo n.º 22
0
int StrobeGlobalDriver::sendCommand_nolock(int cmd, int sensorDev, int strobeId, int arg)
{
    logI("sendCommand_nolock()");
	if (mStrobeHandle <= 0)
	{
	    logE("sendCommand() mStrobeHandle <= 0 ~");
	    return StrobeDrv::STROBE_UNKNOWN_ERROR;
	}
	kdStrobeDrvArg stbArg;
    stbArg.sensorDev=sensorDev;
    stbArg.strobeId = strobeId;
    stbArg.arg=arg;
    return ioctl(mStrobeHandle, cmd, &stbArg);
}
static void Lbat_protection_powerlimit_flash(LOW_BATTERY_LEVEL level)
{
    logI("Lbat_protection_powerlimit_flash %d (%d %d %d %d)\n", level, LOW_BATTERY_LEVEL_0, LOW_BATTERY_LEVEL_1, LOW_BATTERY_LEVEL_2,__LINE__);
    logI("Lbat_protection_powerlimit_flash %d (%d %d %d %d)\n", level, LOW_BATTERY_LEVEL_0, LOW_BATTERY_LEVEL_1, LOW_BATTERY_LEVEL_2,__LINE__);
    if (level == LOW_BATTERY_LEVEL_0)
    {
        gLowPowerVbat=LOW_BATTERY_LEVEL_0;
    }
    else if (level == LOW_BATTERY_LEVEL_1)
    {
        decFlash();
        gLowPowerVbat=LOW_BATTERY_LEVEL_1;

    }
    else if(level == LOW_BATTERY_LEVEL_2)
    {
        decFlash();
        gLowPowerVbat=LOW_BATTERY_LEVEL_2;
    }
    else
    {
        //unlimit cpu and gpu
    }
}
Exemplo n.º 24
0
static void appendClient()
{
	int newClientCounts=clients_ar_size+DEFAULT_MAX_CLIENTS;
	int size=sizeof(TGClient*) * newClientCounts;
	TGClient ** ppNew=(TGClient **) malloc(size);
	memset(ppNew,0,size);
	logI(TAG,"append client poll:%d old size:%d address from:%d to:%d",newClientCounts,clients_ar_size,(long )&ppNew[0],(long)&ppNew[newClientCounts-1]);
	if(g_clients!=NULL)
	{

		memcpy(ppNew,g_clients,clients_ar_size*sizeof(TGClient *));
		free(g_clients);
	}
	g_clients=ppNew;
	clients_ar_size=newClientCounts;
}
Exemplo n.º 25
0
int StrobeGlobalDriver::openkd_nolock()
{
    if(mUsers==0)
	{
		mStrobeHandle = open(STROBE_DEV_NAME, O_RDWR);
		logI("open flash driver kd=%d", mStrobeHandle);
	}

	if (mStrobeHandle <= 0)
    {
        logE("error openkd_nolock %s: %s", STROBE_DEV_NAME, strerror(errno));
		return StrobeDrv::STROBE_UNKNOWN_ERROR;
    }
	android_atomic_inc(&mUsers);
	return 0;
}
Exemplo n.º 26
0
void loadService(const char * path)
{
	if(path==NULL || strlen(path)==0)
	{
		logN(TAG ,LOG_LEVEL_WARNING," path is empty");
		return;
	}

	logI(TAG," prepare to load service from library:%s",path);
	
	void * dlHandler=NULL;
	char * errmsg;
#ifdef LINUX
	dlHandler=dlopen(path,RTLD_NOW);
	if(dlHandler==NULL)
	{
		errmsg=dlerror();
		logN("SERVICE",LOG_LEVEL_WARNING," can not open library:%s %s",path,errmsg);
		return;
	}
#elif WIN32
#endif
	
	struct TGService * pService=NULL;
	if(checkLib(dlHandler,&pService)==0)
	{
		logD(TAG,"check lib successfully");
		//FIXME use system seportor
		char * pLibName=NULL;
		getLibName(path,&pLibName);
		if(pLibName==NULL)
		{
			pLibName=(char *)malloc(sizeof(5));	
			memset(pLibName,0,10);
			sprintf(pLibName,"%d",pService->sID);
		}
		
		pService->serviceName=pLibName;
		addService(pService);
	}
	else
	{
		logW(TAG,"check library error");
	}

}
int	checkAndRelease(void)
{
	int i;
	int j;
	int k;
	for(i=0;i<e_Max_Sensor_Dev_Num;i++)
	for(j=0;j<e_Max_Strobe_Num_Per_Dev;j++)
	for(k=0;k<e_Max_Part_Num_Per_Dev;k++)
	{
		if(g_pFlashInitFunc[i][j][k]!=0)
		{
		    logI("checkAndRelease %d %d %d", i, j, k);
			g_pFlashInitFunc[i][j][k]->flashlight_release(0);
			g_pFlashInitFunc[i][j][k]=0;
		}
	}
	return 0;
}
Exemplo n.º 28
0
// check library 
// check some functions  exist in library or not
// if it doesn't exist in library return -1 
// else if it's correct return 0 and fill functions address into ppService
static int checkLib(void * dlHandler,struct TGService ** ppService)
{
	static int sID=0;
	struct TGService * pService=(struct TGService *) malloc(sizeof(struct TGService));
	memset(pService,0,sizeof(struct TGService));

	SERVICE_CREATE_FUNCTION fpC=NULL;
	SERVICE_INIT_FUNCTION fpI=NULL;
	SERVICE_DO_REQUEST_FUNCTION fpDo=NULL;
	SERVICE_RELEASE_FUNCTION fpR=NULL;
	SERVICE_DESTROY_FUNCTION fpD=NULL;
	
#ifdef LINUX
	fpC=dlsym(dlHandler,SERVICE_CREATE_FUNCTION_NAME);
	fpI=dlsym(dlHandler,SERVICE_INIT_FUNCTION_NAME);
	fpDo=dlsym(dlHandler,SERVICE_DO_REQUEST_FUNCTION_NAME);
	fpR=dlsym(dlHandler,SERVICE_RELEASE_FUNCTION_NAME);
	fpD=dlsym(dlHandler,SERVICE_DESTROY_FUNCTION_NAME);
#elif WIN32
#endif

	int flag;
	if(fpC!=NULL && fpI!=NULL && fpDo!=NULL && fpR!=NULL && fpD!=NULL)
	{
		pService->sID=sID++;	
		pService->do_create=fpC;
		pService->do_init=fpI;
		pService->do_request=fpDo;
		pService->do_release=fpR;
		pService->do_destroy=fpD;
		flag=0;
		*ppService=pService;
		logI(TAG," checked successfully flag:%d create:%s init:%s request:%s release:%s desotry:%s",flag,(long)&fpC,(long)&fpI,(long)&fpDo,(long)&fpR,(long)&fpD);
	}
	else
	{
		flag=-1;
		logE(TAG," checked library error:%s %s %s %s %s",fpC,fpI,fpDo,fpR,fpD);
		free(pService);
	}
	

	return flag;
}
//==============================
// functions
//==============================
int globalInit(void)
{
	int i;
	int j;
	int k;
	logI("globalInit");
	for(i=0;i<e_Max_Sensor_Dev_Num;i++)
	for(j=0;j<e_Max_Strobe_Num_Per_Dev;j++)
	{
	    gLowBatDuty[i][j]=-1;
		g_strobePartId[i][j]=1;
		for(k=0;k<e_Max_Part_Num_Per_Dev;k++)
		{
			g_pFlashInitFunc[i][j][k]=0;
		}

	}
	return 0;
}
Exemplo n.º 30
0
int StrobeGlobalDriver::closekd_nolock()
{
	if(mUsers<=0)
	{
		logW("closekd_nolock user<=0");
		return 0;
	}
	if(mUsers == 1)
	{
		if (mStrobeHandle > 0)
		{
		    logI("close flash driver kd=%d", mStrobeHandle);
			close(mStrobeHandle);
		}
		mStrobeHandle = -1;
	}
	android_atomic_dec(&mUsers);
    return 0;
}