msm: kgsl: queue timestamp expired work more often
There are a some workloads where interrupts do not always get generated, and as a result the timestamp work was not triggered often enough. Queue timestamp expired work from adreno_waittimestamp(), when the timestamp expires while we are not waiting. It is possible in this case that no interrupt fired because no processes were waiting. Queue timestamp expired work when freememontimestamp is called, which reduces the amount of memory built up by applications that use this api often.
This commit is contained in:
parent
5c1047c767
commit
f6acf3ab9f
@ -1182,13 +1182,21 @@ static int adreno_waittimestamp(struct kgsl_device *device,
|
||||
msecs_first = (msecs <= 100) ? ((msecs + 4) / 5) : 100;
|
||||
msecs_part = (msecs - msecs_first + 3) / 4;
|
||||
for (retries = 0; retries < 5; retries++) {
|
||||
if (!kgsl_check_timestamp(device, timestamp)) {
|
||||
if (kgsl_check_timestamp(device, timestamp)) {
|
||||
/* if the timestamp happens while we're not
|
||||
* waiting, there's a chance that an interrupt
|
||||
* will not be generated and thus the timestamp
|
||||
* work needs to be queued.
|
||||
*/
|
||||
queue_work(device->work_queue, &device->ts_expired_ws);
|
||||
status = 0;
|
||||
goto done;
|
||||
}
|
||||
adreno_poke(device);
|
||||
// the QSD8X50 don't support io_fraction ?? // SecureCRT 2012-06-20
|
||||
// io_cnt = (io_cnt + 1) % 100;
|
||||
// if (io_cnt <
|
||||
// pwr->pwrlevels[pwr->active_pwrlevel].
|
||||
// io_fraction)
|
||||
// pwr->pwrlevels[pwr->active_pwrlevel].o_fraction)
|
||||
// io = 0;
|
||||
mutex_unlock(&device->mutex);
|
||||
/* We need to make sure that the process is
|
||||
@ -1212,28 +1220,19 @@ static int adreno_waittimestamp(struct kgsl_device *device,
|
||||
}
|
||||
/*this wait timed out*/
|
||||
}
|
||||
}
|
||||
if (!kgsl_check_timestamp(device, timestamp)) {
|
||||
status = -ETIMEDOUT;
|
||||
KGSL_DRV_ERR(device,
|
||||
"Device hang detected while waiting "
|
||||
"for timestamp: %x, last "
|
||||
"submitted(rb->timestamp): %x, wptr: "
|
||||
"%x\n", timestamp,
|
||||
adreno_dev->ringbuffer.timestamp,
|
||||
"Device hang detected while waiting for timestamp: %x,"
|
||||
"last submitted(rb->timestamp): %x, wptr: %x\n",
|
||||
timestamp, adreno_dev->ringbuffer.timestamp,
|
||||
adreno_dev->ringbuffer.wptr);
|
||||
if (!adreno_dump_and_recover(device)) {
|
||||
/* wait for idle after recovery as the
|
||||
* timestamp that this process wanted
|
||||
* to wait on may be invalid */
|
||||
if (!adreno_idle(device,
|
||||
KGSL_TIMEOUT_DEFAULT))
|
||||
status = 0;
|
||||
}
|
||||
} else {
|
||||
if (!adreno_idle(device, KGSL_TIMEOUT_DEFAULT))
|
||||
status = 0;
|
||||
}
|
||||
|
||||
done:
|
||||
return (int)status;
|
||||
}
|
||||
|
@ -99,7 +99,8 @@ static int kgsl_add_event(struct kgsl_device *device, u32 ts,
|
||||
|
||||
if (n == &device->events)
|
||||
list_add_tail(&event->list, &device->events);
|
||||
|
||||
|
||||
queue_work(device->work_queue, &device->ts_expired_ws);
|
||||
return 0;
|
||||
}
|
||||
#endif
|
||||
|
Loading…
x
Reference in New Issue
Block a user