Beispiel #1
0
NvBool NvOdmOsSemaphoreWaitTimeout(NvOdmOsSemaphoreHandle semaphore,
    NvU32 msec)
{
    NvError err;

    err = NvOsSemaphoreWaitTimeout((NvOsSemaphoreHandle)semaphore, msec);
    if (err == NvError_Timeout)
    {
        return NV_FALSE;
    }

    return NV_TRUE;
}
Beispiel #2
0
void NvBatteryEventHandlerThread(void *args)
{
	NvU8	BatteryState = 0, BatteryEvent = 0;
	NvBool  suspend_flag;

	for (;;) {
        NvOsSemaphoreWaitTimeout(batt_dev->hOdmSemaphore, 
		                         batt_dev->batt_status_poll_period);
		
		if (batt_dev->exitThread)
			break;

		if (!batt_dev->hOdmBattDev)
			continue;
        
        NvOsMutexLock(batt_dev->hBattEventMutex);
	    suspend_flag = batt_dev->inSuspend;
        NvOsMutexUnlock(batt_dev->hBattEventMutex);
		if (suspend_flag)
			continue;

	    pr_info("\tBATTERY: polling battery information! --->>>\n");
		
		NvOdmBatteryGetBatteryStatus(batt_dev->hOdmBattDev,
			NvOdmBatteryInst_Main,
			&BatteryState);

		NvOdmBatteryGetEvent(batt_dev->hOdmBattDev, &BatteryEvent);

		if ((BatteryState == NVODM_BATTERY_STATUS_UNKNOWN) ||
			(BatteryEvent == NvOdmBatteryEventType_Num)) {
			/* Do nothing */
		} else {
			if (BatteryEvent & NvOdmBatteryEventType_RemainingCapacityAlarm) {
				if (BatteryState == (NVODM_BATTERY_STATUS_CRITICAL |
					NVODM_BATTERY_STATUS_VERY_CRITICAL |
					NVODM_BATTERY_STATUS_DISCHARGING)) {
					pr_info("nvec_battery:calling kernel_power_off...\n");
					kernel_power_off();
				}
			} else {
				/* Update the battery and power supply info for other events */
				power_supply_changed(&tegra_power_supplies[NvCharger_Type_Battery]);
				//power_supply_changed(&tegra_power_supplies[NvCharger_Type_USB]); //
				power_supply_changed(&tegra_power_supplies[NvCharger_Type_AC]);
			}
		}
	}
}
/*
 * Always use one EcPrivThread-global clock/time for timeout calculations
 */
static void
NvEcPrivThread( void * args )
{
    NvEcPrivState   *ec = (NvEcPrivState *)args;
    NvU32           t, timeout = NV_WAIT_INFINITE;
    NvU32           tStatus = 0;
    NvError         wait = NvSuccess;
    NvError         e;

    while( !ec->exitThread )
    {
    #if ENABLE_TIMEOUT
        if ( timeout )
            wait = NvOsSemaphoreWaitTimeout( ec->sema, timeout );
    #else
        NvOsSemaphoreWait( ec->sema );
        wait = NvSuccess;
    #endif
        
    #if ENABLE_FAKE_TIMEOUT_TEST
        t = ec->lastTime + 0x200;
    #else
        t = NvOsGetTimeMS();
    #endif
        ec->timeDiff = t - ec->lastTime;
        ec->lastTime = t;      // update last timer value
        
        if ( !timeout || (wait == NvError_Timeout) )
        {
            // timeout case
            NvEcPrivProcessTimeout( ec );
        }
        
        // look for any pending packets
        tStatus = NvEcTransportQueryStatus( ec->transport );
        
        e = NvSuccess;

        /* 
         * SEND_COMPLETE event must be processed before RESPONSE_RECEIVE_COMPLETE 
         * event as SEND_COMPLETE event schedules timeout for RESPONSE_RECEIVE event.
         */
        if ( tStatus & (NVEC_TRANSPORT_STATUS_SEND_COMPLETE |
                         NVEC_TRANSPORT_STATUS_SEND_ERROR) )
        {
            NvEcPrivProcessPostSendRequest( ec,
                (tStatus & NVEC_TRANSPORT_STATUS_SEND_COMPLETE) ?
                    NvSuccess : NvError_I2cWriteFailed );
        }

        if ( tStatus & (NVEC_TRANSPORT_STATUS_RESPONSE_RECEIVE_ERROR |
                    NVEC_TRANSPORT_STATUS_RESPONSE_RECEIVE_COMPLETE) )
        {
            e = (tStatus & NVEC_TRANSPORT_STATUS_RESPONSE_RECEIVE_COMPLETE) ?
                    NvSuccess : NvError_I2cReadFailed;
            e = NvEcPrivProcessReceiveResponse( ec, e );
            // return ignored.  Could be spurious response.
        }
        if ( tStatus & (NVEC_TRANSPORT_STATUS_EVENT_RECEIVE_ERROR |
                    NVEC_TRANSPORT_STATUS_EVENT_RECEIVE_COMPLETE) )
        {
            e = (tStatus & NVEC_TRANSPORT_STATUS_EVENT_RECEIVE_COMPLETE) ?
                    NvSuccess : NvError_I2cReadFailed;
            e = NvEcPrivProcessReceiveEvent( ec, e );
                // return ignored.  Could be spurious event.
        }

	if ( tStatus & NVEC_TRANSPORT_STATUS_EVENT_PACKET_MAX_NACK ) {
		// signal the ping thread to send a ping command since max
		// number of nacks have been sent to the EC
		if (ec->hPingSema) {
			NvOsSemaphoreSignal(ec->hPingSema);
		}
	}

        // send request whenever possible 
        if ( (ec->timeout[NVEC_IDX_REQUEST] == NV_WAIT_INFINITE) && 
             (ec->EnterLowPowerState == NV_FALSE) )
            NvEcPrivProcessSendRequest( ec );
    #if ENABLE_TIMEOUT
        timeout = NvEcPrivUpdateActualTimeout( ec ); 
    #endif
        
        if (ec->EnterLowPowerState)
        {
            // This code assumes that EC is already in kept in sleep mode by
            // either shim or top level code. And there will not be any activity
            // going on SM bus.
            if (ec->timeout[NVEC_IDX_REQUEST] != NV_WAIT_INFINITE)
            {
                NvOsDebugPrintf("\r\nNvEc has active requests during suspend. "
                    "It shouldn't have. check it.");
            }
            
            // No active request is pending. Enter into low power state.
            // Signal power suspend API to enter into suspend mode.
            NvOsSemaphoreSignal(ec->LowPowerEntrySema);
            // Wait till power resume API signals resume operation.
            NvOsSemaphoreWait(ec->LowPowerExitSema);
            // Update the timeouts for the active responses, which are scheduled 
            // to receive before system entering into suspend.
#if ENABLE_TIMEOUT
            NvEcPrivResetActiveRequestResponseTimeouts( ec );
            timeout = NvEcPrivUpdateActualTimeout( ec );
#endif // ENABLE_TIMEOUT
        }
    }
}