Commit 00bea608 authored by Mark Stevens's avatar Mark Stevens
Browse files

update from duco/rk312x_20160510 on rockchip-5.1.0_r5 branches

parent 796aaf7f
......@@ -647,6 +647,38 @@ static void run_dexopt(int zip_fd, int odex_fd, const char* input_file_name,
ALOGE("execl(%s) failed: %s\n", DEX_OPT_BIN, strerror(errno));
}
static int split_count(const char *str)
{
char *ctx;
int count = 0;
char buf[PROPERTY_VALUE_MAX];
strncpy(buf, str, sizeof(buf));
char *pBuf = buf;
while(strtok_r(pBuf, " ", &ctx) != NULL) {
count++;
pBuf = NULL;
}
return count;
}
static int split(char *buf, char **argv)
{
char *ctx;
int count = 0;
char *tok;
char *pBuf = buf;
while((tok = strtok_r(pBuf, " ", &ctx)) != NULL) {
argv[count++] = tok;
pBuf = NULL;
}
return count;
}
static void run_patchoat(int input_fd, int oat_fd, const char* input_file_name,
const char* output_file_name, const char *pkgname, const char *instruction_set)
{
......@@ -719,7 +751,8 @@ static void run_dex2oat(int zip_fd, int oat_fd, const char* input_file_name,
dex2oat_isa_features, NULL) > 0;
char dex2oat_flags[PROPERTY_VALUE_MAX];
bool have_dex2oat_flags = property_get("dalvik.vm.dex2oat-flags", dex2oat_flags, NULL) > 0;
int dex2oat_flags_count = property_get("dalvik.vm.dex2oat-flags",
dex2oat_flags, NULL) <= 0 ? 0 : split_count(dex2oat_flags);
ALOGV("dalvik.vm.dex2oat-flags=%s\n", dex2oat_flags);
// If we booting without the real /data, don't spend time compiling.
......@@ -803,7 +836,7 @@ static void run_dex2oat(int zip_fd, int oat_fd, const char* input_file_name,
+ (have_dex2oat_Xms_flag ? 2 : 0)
+ (have_dex2oat_Xmx_flag ? 2 : 0)
+ (have_dex2oat_compiler_filter_flag ? 1 : 0)
+ (have_dex2oat_flags ? 1 : 0)
+ dex2oat_flags_count
+ (have_dex2oat_swap_fd ? 1 : 0)];
int i = 0;
argv[i++] = (char*)DEX2OAT_BIN;
......@@ -832,8 +865,8 @@ static void run_dex2oat(int zip_fd, int oat_fd, const char* input_file_name,
if (have_dex2oat_compiler_filter_flag) {
argv[i++] = dex2oat_compiler_filter_arg;
}
if (have_dex2oat_flags) {
argv[i++] = dex2oat_flags;
if (dex2oat_flags_count) {
i += split(dex2oat_flags, argv + i);
}
if (have_dex2oat_swap_fd) {
argv[i++] = dex2oat_swap_fd;
......@@ -842,7 +875,7 @@ static void run_dex2oat(int zip_fd, int oat_fd, const char* input_file_name,
argv[i] = NULL;
execv(DEX2OAT_BIN, (char* const *)argv);
ALOGE("execl(%s) failed: %s\n", DEX2OAT_BIN, strerror(errno));
ALOGE("execv(%s) failed: %s\n", DEX2OAT_BIN, strerror(errno));
}
static int wait_child(pid_t pid)
......
<?xml version="1.0" encoding="utf-8"?>
<!--$_FOR_ROCKCHIP_RBOX_$-->
<!--$_rbox_$_modify_$_chenzhi_20120309: add for pppoe-->
<!-- Copyright (C) 2009 The Android Open Source Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
<!-- This is the standard set of features for devices that support pppoe. -->
<permissions>
<feature name="android.software.pppoe" />
</permissions>
......@@ -302,6 +302,11 @@ enum {
AKEYCODE_TV_CONTENTS_MENU = 256,
AKEYCODE_TV_MEDIA_CONTEXT_MENU = 257,
AKEYCODE_TV_TIMER_PROGRAMMING = 258,
AKEYCODE_TV_KEYMOUSE_LEFT = 260,
AKEYCODE_TV_KEYMOUSE_RIGHT = 261,
AKEYCODE_TV_KEYMOUSE_UP = 262,
AKEYCODE_TV_KEYMOUSE_DOWN = 263,
AKEYCODE_TV_KEYMOUSE_MODE_SWITCH = 264,
AKEYCODE_HELP = 259
// NOTE: If you add a new keycode here you must also add it to several other files.
......
......@@ -60,6 +60,9 @@ class BufferItem : public Flattenable<BufferItem> {
// mCrop is the current crop rectangle for this buffer slot.
Rect mCrop;
// mDirtyRect is the dirty rectangle for this buffer slot.
Rect mDirtyRect;
// mTransform is the current transform flags for this buffer slot.
// refer to NATIVE_WINDOW_TRANSFORM_* in <window.h>
uint32_t mTransform;
......
......@@ -76,6 +76,8 @@ public:
// when a new frame becomes available.
void setFrameAvailableListener(const wp<FrameAvailableListener>& listener);
int32_t getAlreadyStereo();
private:
ConsumerBase(const ConsumerBase&);
void operator=(const ConsumerBase&);
......@@ -233,6 +235,8 @@ protected:
//
// This mutex is intended to be locked by derived classes.
mutable Mutex mMutex;
int32_t mAlreadyStereo;
};
// ----------------------------------------------------------------------------
......
......@@ -176,6 +176,9 @@ public:
// getCurrentCrop returns the cropping rectangle of the current buffer.
Rect getCurrentCrop() const;
// getDirtyRegion returns the dirty rect associated with the current buffer.
Rect getCurrentDirtyRect() const;
// getCurrentTransform returns the transform of the current buffer.
uint32_t getCurrentTransform() const;
......@@ -369,6 +372,10 @@ private:
// It gets set each time updateTexImage is called.
Rect mCurrentCrop;
//mCurrentDirtyRect is the dirty rectangle associated with the current
//buffer.
Rect mCurrentDirtyRect;
// mCurrentTransform is the transform identifier for the current texture. It
// gets set each time updateTexImage is called.
uint32_t mCurrentTransform;
......
......@@ -67,6 +67,9 @@ public:
// mCrop is the current crop rectangle for this buffer slot.
Rect mCrop;
// mDirtyRect is the dirty rectangle for this buffer slot.
Rect mDirtyRect;
// mTransform is the current transform flags for this buffer slot.
// refer to NATIVE_WINDOW_TRANSFORM_* in <window.h>
uint32_t mTransform;
......
......@@ -281,6 +281,14 @@ public:
: timestamp(timestamp), isAutoTimestamp(isAutoTimestamp), crop(crop),
scalingMode(scalingMode), transform(transform), stickyTransform(sticky),
async(async), fence(fence) { }
inline QueueBufferInput(int64_t timestamp, bool isAutoTimestamp,
const Rect& crop, const Rect& dirtyRect, int scalingMode, uint32_t transform, bool async,
const sp<Fence>& fence, uint32_t sticky = 0)
: timestamp(timestamp), isAutoTimestamp(isAutoTimestamp), crop(crop),
dirtyRect(dirtyRect),scalingMode(scalingMode), transform(transform), stickyTransform(sticky),
async(async), fence(fence) { }
inline void deflate(int64_t* outTimestamp, bool* outIsAutoTimestamp,
Rect* outCrop, int* outScalingMode, uint32_t* outTransform,
bool* outAsync, sp<Fence>* outFence,
......@@ -297,6 +305,24 @@ public:
}
}
inline void deflate(int64_t* outTimestamp, bool* outIsAutoTimestamp,
Rect* outCrop, Rect* outDirtyRect, int* outScalingMode, uint32_t* outTransform,
bool* outAsync, sp<Fence>* outFence,
uint32_t* outStickyTransform = NULL) const {
*outTimestamp = timestamp;
*outIsAutoTimestamp = bool(isAutoTimestamp);
*outCrop = crop;
*outDirtyRect = dirtyRect;
*outScalingMode = scalingMode;
*outTransform = transform;
*outAsync = bool(async);
*outFence = fence;
if (outStickyTransform != NULL) {
*outStickyTransform = stickyTransform;
}
}
// Flattenable protocol
size_t getFlattenedSize() const;
size_t getFdCount() const;
......@@ -307,6 +333,7 @@ public:
int64_t timestamp;
int isAutoTimestamp;
Rect crop;
Rect dirtyRect;
int scalingMode;
uint32_t transform;
uint32_t stickyTransform;
......
......@@ -101,6 +101,10 @@ public:
*/
void allocateBuffers();
/* sets dirty rectangle of the buffer that gets queued next for the
* Surface */
status_t setDirtyRect(const Rect* dirtyRect);
protected:
virtual ~Surface();
......@@ -226,6 +230,10 @@ private:
// that gets queued. It is set by calling setCrop.
Rect mCrop;
// mDirtyRect is the dirty rectangle set for the next buffer that gets
// queued. It is set by calling setDirtyRect.
Rect mDirtyRect;
// mScalingMode is the scaling mode that will be used for the next
// buffers that get queued. It is set by calling setScalingMode.
int mScalingMode;
......
......@@ -110,6 +110,11 @@ enum {
*/
#define MAX_POINTERS 16
/*
* Maximum number of samples supported per motion event.
*/
#define MAX_SAMPLES UINT16_MAX
/*
* Maximum pointer id value supported in a motion event.
* Smallest pointer id is 0.
......@@ -208,7 +213,7 @@ struct PointerCoords {
void scale(float scale);
void applyOffset(float xOffset, float yOffset);
void transfromCoordinate(float posX, float posY, float scaleX, float scaleY);
inline float getX() const {
return getAxisValue(AMOTION_EVENT_AXIS_X);
}
......@@ -543,7 +548,7 @@ public:
void offsetLocation(float xOffset, float yOffset);
void scale(float scaleFactor);
void transformCoordinate(float posX, float posY, float scaleX, float scaleY);
// Apply 3x3 perspective matrix transformation.
// Matrix is in row-major form and compatible with SkMatrix.
void transform(const float matrix[9]);
......
......@@ -298,6 +298,11 @@ static const InputEventLabel KEYCODES[] = {
DEFINE_KEYCODE(TV_CONTENTS_MENU),
DEFINE_KEYCODE(TV_MEDIA_CONTEXT_MENU),
DEFINE_KEYCODE(TV_TIMER_PROGRAMMING),
DEFINE_KEYCODE(TV_KEYMOUSE_LEFT),
DEFINE_KEYCODE(TV_KEYMOUSE_RIGHT),
DEFINE_KEYCODE(TV_KEYMOUSE_UP),
DEFINE_KEYCODE(TV_KEYMOUSE_DOWN),
DEFINE_KEYCODE(TV_KEYMOUSE_MODE_SWITCH),
DEFINE_KEYCODE(HELP),
{ NULL, 0 }
......
......@@ -28,8 +28,11 @@ enum {
USER_ACTIVITY_EVENT_OTHER = 0,
USER_ACTIVITY_EVENT_BUTTON = 1,
USER_ACTIVITY_EVENT_TOUCH = 2,
//------modify begin for button & keyboard backlight by cx@rock-chips.com------
USER_ACTIVITY_EVENT_CAPACITIVE_BUTTON = 3,
USER_ACTIVITY_EVENT_LAST = USER_ACTIVITY_EVENT_TOUCH, // Last valid event code.
USER_ACTIVITY_EVENT_LAST = USER_ACTIVITY_EVENT_CAPACITIVE_BUTTON, // Last valid event code.
//------modify end------
};
}; // namespace android
......
......@@ -25,13 +25,18 @@
namespace android {
/**
* display_info_t, 用于在 sf 和 surface_composer_client 之间传递 特定 display 的信息.
*/
struct DisplayInfo {
uint32_t w;
uint32_t h;
float xdpi;
float ydpi;
float fps;
/** 具体 dpi 数值和 160(mdpi) 的比值. */
float density;
/** client 要求的 display 的 orientations. */
uint8_t orientation;
bool secure;
nsecs_t appVsyncOffset;
......
......@@ -34,6 +34,7 @@ BufferItem::BufferItem() :
mAcquireCalled(false),
mTransformToDisplayInverse(false) {
mCrop.makeInvalid();
mDirtyRect.makeInvalid();
}
BufferItem::~BufferItem() {}
......@@ -43,6 +44,7 @@ BufferItem::operator IGraphicBufferConsumer::BufferItem() const {
bufferItem.mGraphicBuffer = mGraphicBuffer;
bufferItem.mFence = mFence;
bufferItem.mCrop = mCrop;
bufferItem.mDirtyRect = mDirtyRect;
bufferItem.mTransform = mTransform;
bufferItem.mScalingMode = mScalingMode;
bufferItem.mTimestamp = mTimestamp;
......@@ -57,6 +59,7 @@ BufferItem::operator IGraphicBufferConsumer::BufferItem() const {
size_t BufferItem::getPodSize() const {
size_t c = sizeof(mCrop) +
sizeof(mDirtyRect) +
sizeof(mTransform) +
sizeof(mScalingMode) +
sizeof(mTimestamp) +
......@@ -127,6 +130,7 @@ status_t BufferItem::flatten(
}
FlattenableUtils::write(buffer, size, mCrop);
FlattenableUtils::write(buffer, size, mDirtyRect);
FlattenableUtils::write(buffer, size, mTransform);
FlattenableUtils::write(buffer, size, mScalingMode);
FlattenableUtils::write(buffer, size, mTimestamp);
......@@ -169,6 +173,7 @@ status_t BufferItem::unflatten(
}
FlattenableUtils::read(buffer, size, mCrop);
FlattenableUtils::read(buffer, size, mDirtyRect);
FlattenableUtils::read(buffer, size, mTransform);
FlattenableUtils::read(buffer, size, mScalingMode);
FlattenableUtils::read(buffer, size, mTimestamp);
......
......@@ -517,12 +517,14 @@ status_t BufferQueueProducer::queueBuffer(int slot,
int64_t timestamp;
bool isAutoTimestamp;
Rect crop;
Rect dirtyRect;
int scalingMode;
uint32_t transform;
uint32_t stickyTransform;
bool async;
sp<Fence> fence;
input.deflate(&timestamp, &isAutoTimestamp, &crop, &scalingMode, &transform,
input.deflate(&timestamp, &isAutoTimestamp, &crop, &dirtyRect, &scalingMode, &transform,
&async, &fence, &stickyTransform);
if (fence == NULL) {
......@@ -530,7 +532,7 @@ status_t BufferQueueProducer::queueBuffer(int slot,
return BAD_VALUE;
}
switch (scalingMode) {
switch (scalingMode & 0xff) {
case NATIVE_WINDOW_SCALING_MODE_FREEZE:
case NATIVE_WINDOW_SCALING_MODE_SCALE_TO_WINDOW:
case NATIVE_WINDOW_SCALING_MODE_SCALE_CROP:
......@@ -603,6 +605,7 @@ status_t BufferQueueProducer::queueBuffer(int slot,
item.mAcquireCalled = mSlots[slot].mAcquireCalled;
item.mGraphicBuffer = mSlots[slot].mGraphicBuffer;
item.mCrop = crop;
item.mDirtyRect = dirtyRect;
item.mTransform = transform & ~NATIVE_WINDOW_TRANSFORM_INVERSE_DISPLAY;
item.mTransformToDisplayInverse =
bool(transform & NATIVE_WINDOW_TRANSFORM_INVERSE_DISPLAY);
......
......@@ -55,7 +55,8 @@ static int32_t createProcessUniqueId() {
ConsumerBase::ConsumerBase(const sp<IGraphicBufferConsumer>& bufferQueue, bool controlledByApp) :
mAbandoned(false),
mConsumer(bufferQueue) {
mConsumer(bufferQueue),
mAlreadyStereo(0) {
// Choose a name using the PID and a process-unique ID.
mName = String8::format("unnamed-%d-%d", getpid(), createProcessUniqueId());
......@@ -196,9 +197,16 @@ status_t ConsumerBase::acquireBufferLocked(BufferQueue::BufferItem *item,
CB_LOGV("acquireBufferLocked: -> slot=%d/%" PRIu64,
item->mBuf, item->mFrameNumber);
mAlreadyStereo = (item->mScalingMode & 0x300) >> 8;
item->mScalingMode = item->mScalingMode & ~0x300;
return OK;
}
int32_t ConsumerBase::getAlreadyStereo() {
//ALOGD("djw: gui: mAlreadyStereo =%d",mAlreadyStereo);
return mAlreadyStereo;
}
status_t ConsumerBase::addReleaseFence(int slot,
const sp<GraphicBuffer> graphicBuffer, const sp<Fence>& fence) {
Mutex::Autolock lock(mMutex);
......
......@@ -141,6 +141,7 @@ GLConsumer::GLConsumer(const sp<IGraphicBufferConsumer>& bq, uint32_t tex,
sizeof(mCurrentTransformMatrix));
mConsumer->setConsumerUsageBits(DEFAULT_USAGE_FLAGS);
mCurrentDirtyRect.clear();
}
GLConsumer::GLConsumer(const sp<IGraphicBufferConsumer>& bq, uint32_t texTarget,
......@@ -437,6 +438,7 @@ status_t GLConsumer::updateAndReleaseLocked(const BufferQueue::BufferItem& item)
mCurrentTimestamp = item.mTimestamp;
mCurrentFence = item.mFence;
mCurrentFrameNumber = item.mFrameNumber;
mCurrentDirtyRect = item.mDirtyRect;
computeCurrentTransformMatrixLocked();
......@@ -983,6 +985,11 @@ status_t GLConsumer::doGLFenceWaitLocked() const {
return NO_ERROR;
}
Rect GLConsumer::getCurrentDirtyRect() const {
Mutex::Autolock lock(mMutex);
return mCurrentDirtyRect;
}
void GLConsumer::freeBufferLocked(int slotIndex) {
ST_LOGV("freeBufferLocked: slotIndex=%d", slotIndex);
if (slotIndex == mCurrentTexture) {
......
......@@ -444,7 +444,7 @@ status_t BnGraphicBufferConsumer::onTransact(
CHECK_INTERFACE(IGraphicBufferConsumer, data, reply);
sp<GraphicBuffer> buffer = new GraphicBuffer();
data.read(*buffer.get());
int slot;
int slot = -1;
int result = attachBuffer(&slot, buffer);
reply->writeInt32(slot);
reply->writeInt32(result);
......
......@@ -304,7 +304,7 @@ status_t BnGraphicBufferProducer::onTransact(
uint32_t h = data.readInt32();
uint32_t format = data.readInt32();
uint32_t usage = data.readInt32();
int buf;
int buf = 0;
sp<Fence> fence;
int result = dequeueBuffer(&buf, &fence, async, w, h, format, usage);
reply->writeInt32(buf);
......@@ -344,7 +344,7 @@ status_t BnGraphicBufferProducer::onTransact(
CHECK_INTERFACE(IGraphicBufferProducer, data, reply);
sp<GraphicBuffer> buffer = new GraphicBuffer();
data.read(*buffer.get());
int slot;
int slot = 0;
int result = attachBuffer(&slot, buffer);
reply->writeInt32(slot);
reply->writeInt32(result);
......@@ -357,6 +357,7 @@ status_t BnGraphicBufferProducer::onTransact(
QueueBufferOutput* const output =
reinterpret_cast<QueueBufferOutput *>(
reply->writeInplace(sizeof(QueueBufferOutput)));
memset(output, 0, sizeof(QueueBufferOutput));
status_t result = queueBuffer(buf, input, output);
reply->writeInt32(result);
return NO_ERROR;
......@@ -371,7 +372,7 @@ status_t BnGraphicBufferProducer::onTransact(
} break;
case QUERY: {
CHECK_INTERFACE(IGraphicBufferProducer, data, reply);
int value;
int value = 0;
int what = data.readInt32();
int res = query(what, &value);
reply->writeInt32(value);
......@@ -433,6 +434,7 @@ size_t IGraphicBufferProducer::QueueBufferInput::getFlattenedSize() const {
return sizeof(timestamp)
+ sizeof(isAutoTimestamp)
+ sizeof(crop)
+ sizeof(dirtyRect)
+ sizeof(scalingMode)
+ sizeof(transform)
+ sizeof(stickyTransform)
......@@ -453,6 +455,7 @@ status_t IGraphicBufferProducer::QueueBufferInput::flatten(
FlattenableUtils::write(buffer, size, timestamp);
FlattenableUtils::write(buffer, size, isAutoTimestamp);
FlattenableUtils::write(buffer, size, crop);
FlattenableUtils::write(buffer, size, dirtyRect);
FlattenableUtils::write(buffer, size, scalingMode);
FlattenableUtils::write(buffer, size, transform);
FlattenableUtils::write(buffer, size, stickyTransform);
......@@ -467,6 +470,7 @@ status_t IGraphicBufferProducer::QueueBufferInput::unflatten(
sizeof(timestamp)
+ sizeof(isAutoTimestamp)
+ sizeof(crop)
+ sizeof(dirtyRect)
+ sizeof(scalingMode)
+ sizeof(transform)
+ sizeof(stickyTransform)
......@@ -479,6 +483,7 @@ status_t IGraphicBufferProducer::QueueBufferInput::unflatten(
FlattenableUtils::read(buffer, size, timestamp);
FlattenableUtils::read(buffer, size, isAutoTimestamp);
FlattenableUtils::read(buffer, size, crop);
FlattenableUtils::read(buffer, size, dirtyRect);
FlattenableUtils::read(buffer, size, scalingMode);
FlattenableUtils::read(buffer, size, transform);
FlattenableUtils::read(buffer, size, stickyTransform);
......
......@@ -36,6 +36,7 @@
#include <private/gui/ComposerService.h>
#include <hardware/rga.h>
namespace android {
Surface::Surface(
......@@ -65,6 +66,7 @@ Surface::Surface(
mReqUsage = 0;
mTimestamp = NATIVE_WINDOW_TIMESTAMP_AUTO;
mCrop.clear();
mDirtyRect.clear();
mScalingMode = NATIVE_WINDOW_SCALING_MODE_FREEZE;
mTransform = 0;
mStickyTransform = 0;
......@@ -126,9 +128,12 @@ int Surface::hook_queueBuffer(ANativeWindow* window,
int Surface::hook_dequeueBuffer_DEPRECATED(ANativeWindow* window,
ANativeWindowBuffer** buffer) {
Surface* c = getSelf(window);
ANativeWindowBuffer* buf;
ANativeWindowBuffer* buf = NULL;
int fenceFd = -1;
int result = c->dequeueBuffer(&buf, &fenceFd);
if (result != NO_ERROR) return result;
sp<Fence> fence(new Fence(fenceFd));
int waitResult = fence->waitForever("dequeueBuffer_DEPRECATED");
if (waitResult != OK) {
......@@ -172,6 +177,12 @@ int Surface::hook_perform(ANativeWindow* window, int operation, ...) {
return c->perform(operation, args);
}
status_t Surface::setDirtyRect(const Rect* dirtyRect) {
Mutex::Autolock lock(mMutex);
mDirtyRect = *dirtyRect;
return NO_ERROR;
}
int Surface::setSwapInterval(int interval) {
ATRACE_CALL();
// EGL specification states:
......@@ -315,10 +326,17 @@ int Surface::queueBuffer(android_native_buffer_t* buffer, int fenceFd) {
Rect crop;
mCrop.intersect(Rect(buffer->width, buffer->height), &crop);
Rect dirtyRect = mDirtyRect;
if(dirtyRect.isEmpty()) {
int drWidth = mUserWidth ? mUserWidth : mDefaultWidth;
int drHeight = mUserHeight ? mUserHeight : mDefaultHeight;
dirtyRect = Rect(drWidth, drHeight);
}
sp<Fence> fence(fenceFd >= 0 ? new Fence(fenceFd) : Fence::NO_FENCE);
IGraphicBufferProducer::QueueBufferOutput output;
IGraphicBufferProducer::QueueBufferInput input(timestamp, isAutoTimestamp,
crop, mScalingMode, mTransform ^ mStickyTransform, mSwapIntervalZero,
crop, dirtyRect, mScalingMode, mTransform ^ mStickyTransform, mSwapIntervalZero,
fence, mStickyTransform);
status_t err = mGraphicBufferProducer->queueBuffer(i, input, &output);
if (err != OK) {
......@@ -335,7 +353,7 @@ int Surface::queueBuffer(android_native_buffer_t* buffer, int fenceFd) {
}
mConsumerRunningBehind = (numPendingBuffers >= 2);
mDirtyRect.clear();
return err;
}
......@@ -695,13 +713,24 @@ int Surface::setScalingMode(int mode)
case NATIVE_WINDOW_SCALING_MODE_SCALE_TO_WINDOW:
case NATIVE_WINDOW_SCALING_MODE_SCALE_CROP:
break;
case 300: // close stereo
case 301: // left-right
case 302: // up-bottom
break;
default:
ALOGE("unknown scaling mode: %d", mode);
return BAD_VALUE;
}
Mutex::Autolock lock(mMutex);
mScalingMode = mode;
if(300==mode || 301==mode || 302==mode) {
if(300==mode) mScalingMode &= ~0x300;
if(301==mode) mScalingMode |= 0x100;
if(302==mode) mScalingMode |= 0x200;
} else {
mScalingMode &= ~0xff;
mScalingMode |= mode;
}
return NO_ERROR;
}
......@@ -739,6 +768,32 @@ void Surface::freeAllBuffers() {
// ----------------------------------------------------------------------
// the lock/unlock APIs must be used from the same thread
static int fd_rga=-1;
int hwChangeRgaFormat( int fmt )
{
switch (fmt)
{
case HAL_PIXEL_FORMAT_RGB_565:
return RK_FORMAT_RGB_565;
case HAL_PIXEL_FORMAT_RGB_888:
return RK_FORMAT_RGB_888;
case HAL_PIXEL_FORMAT_RGBA_8888:
return RK_FORMAT_RGBA_8888;
case HAL_PIXEL_FORMAT_RGBX_8888:
return RK_FORMAT_RGBX_8888;
case HAL_PIXEL_FORMAT_BGRA_8888:
return RK_FORMAT_BGRA_8888;
case HAL_PIXEL_FORMAT_YCrCb_NV12:
return RK_FORMAT_YCbCr_420_SP;
case HAL_PIXEL_FORMAT_YCrCb_NV12_VIDEO:
return RK_FORMAT_YCbCr_420_SP;
default:
return -1;
}
}
#ifndef USE_RGA_COPYBLT
static status_t copyBlt(
const sp<GraphicBuffer>& dst,
......@@ -756,6 +811,7 @@ static status_t copyBlt(
err = dst->lock(GRALLOC_USAGE_SW_WRITE_OFTEN, reg.bounds(), (void**)&dst_bits);
ALOGE_IF(err, "error locking dst buffer %s", strerror(-err));
#ifndef USE_LCDC_COMPOSER
Region::const_iterator head(reg.begin());
Region::const_iterator tail(reg.end());
if (head != tail && src_bits && dst_bits) {
......@@ -782,6 +838,313 @@ static status_t copyBlt(
}
}
#else
int32_t vir_w = 0, vir_h = 0;
Region::const_iterator head_(reg.begin());
Region::const_iterator tail_(reg.end());
if (head_ != tail_ && src_bits && dst_bits) {
while (head_ != tail_) {
const Rect& r(*head_++);
ssize_t h_ = r.height();
if (h_ <= 0) continue;
int32_t tmp_w = r.right;
int32_t tmp_h = r.bottom;
vir_w = (vir_w >= tmp_w) ? vir_w : tmp_w;
vir_h = (vir_h >= tmp_h) ? vir_h : tmp_h;
}
}
head_ = reg.begin();
if (head_ != tail_ && src_bits && dst_bits) {
//const size_t bpp = bytesPerPixel(src->format);
bool needsync = false;
struct rga_req Rga_Request;
if(fd_rga < 0){
property_set("sys.gui.version", "1.04");
fd_rga = open("/dev/rga",O_RDWR,0);
if(fd_rga < 0){
ALOGE(" rga open err");
goto ERROR;
}
}
while (head_ != tail_) {
if(needsync){
if(ioctl(fd_rga, RGA_BLIT_ASYNC, &Rga_Request) != 0){
ALOGE(" rga ioctl RGA_BLIT_ASYNC err !!!!!! fd_rga = %d", fd_rga);
goto ERROR;
}
}
const Rect& r(*head_++);
ssize_t h = r.height();
if (h <= 0) continue;
memset(&Rga_Request,0x0,sizeof(Rga_Request));
//set src info
Rga_Request.src.yrgb_addr = (int)src_bits; //(int)s;
Rga_Request.src.uv_addr = 0;
Rga_Request.src.v_addr = Rga_Request.src.uv_addr;
Rga_Request.src.vir_w = src->stride;
Rga_Request.src.vir_h = vir_h;
Rga_Request.src.format = hwChangeRgaFormat(src->format); // RK_FORMAT_RGBA_8888
Rga_Request.src.act_w = r.width();
Rga_Request.src.act_h = r.height();
Rga_Request.src.x_offset = r.left;
Rga_Request.src.y_offset = r.top;
//set dst info
Rga_Request.dst.yrgb_addr = (int)dst_bits; //(int)d;
Rga_Request.dst.uv_addr = 0;
Rga_Request.dst.v_addr = Rga_Request.dst.uv_addr;
Rga_Request.dst.vir_w = dst->stride;
Rga_Request.dst.vir_h = vir_h;
Rga_Request.dst.act_w = r.width();
Rga_Request.dst.act_h = r.height();
Rga_Request.clip.xmin = 0;
Rga_Request.clip.xmax = Rga_Request.dst.vir_w - 1;
Rga_Request.clip.ymin = 0;
Rga_Request.clip.ymax = Rga_Request.dst.vir_h - 1;
Rga_Request.dst.x_offset = r.left;
Rga_Request.dst.y_offset = r.top;
Rga_Request.sina = 0;
Rga_Request.cosa = 0x10000;
Rga_Request.dst.format = Rga_Request.src.format; // RK_FORMAT_RGBA_8888
Rga_Request.alpha_rop_flag |= (1 << 5);
Rga_Request.mmu_info.mmu_en = 1;
Rga_Request.mmu_info.mmu_flag = ((2 & 0x3) << 4) | 1;
needsync = true;
}
if(needsync){
if(ioctl(fd_rga, RGA_BLIT_ASYNC, &Rga_Request) != 0){
ALOGE(" %s(%d): RGA_BLIT_ASYNC Failed err !!!!!! fd_rga = %d ", __FUNCTION__, __LINE__, fd_rga);
ALOGE(" src info: yrgb_addr=%x, uv_addr=%x,v_addr=%x,"
"vir_w=%d,vir_h=%d,format=%d,"
"act_x_y_w_h [%d,%d,%d,%d] ",
Rga_Request.src.yrgb_addr, Rga_Request.src.uv_addr ,Rga_Request.src.v_addr,
Rga_Request.src.vir_w ,Rga_Request.src.vir_h ,Rga_Request.src.format ,
Rga_Request.src.x_offset ,
Rga_Request.src.y_offset,
Rga_Request.src.act_w ,
Rga_Request.src.act_h
);
ALOGE(" dst info: yrgb_addr=%x, uv_addr=%x,v_addr=%x,"
"vir_w=%d,vir_h=%d,format=%d,"
"clip[%d,%d,%d,%d], "
"act_x_y_w_h [%d,%d,%d,%d] ",
Rga_Request.dst.yrgb_addr, Rga_Request.dst.uv_addr ,Rga_Request.dst.v_addr,
Rga_Request.dst.vir_w ,Rga_Request.dst.vir_h ,Rga_Request.dst.format,
Rga_Request.clip.xmin,
Rga_Request.clip.xmax,
Rga_Request.clip.ymin,
Rga_Request.clip.ymax,
Rga_Request.dst.x_offset ,
Rga_Request.dst.y_offset,
Rga_Request.dst.act_w ,
Rga_Request.dst.act_h
);
goto ERROR;
}
}
}
ERROR:
#endif
if (src_bits)
src->unlock();
if (dst_bits)
dst->unlock();
return err;
}
#else
/*
* RgaCopybltThread add by yzq, because RGA_BLIT_ASYNC would use 3ms,
* use thread let the work noblock main thread.
*/
class RgaCopybltThread : public Thread {
static const int MAX_REQ = 5;
struct rga_req mRga_Request[MAX_REQ];
int req_pend;
public:
RgaCopybltThread():Thread(false) {
req_pend = 0;
if(fd_rga<0){
property_set("sys.gui.version", "1.05");
fd_rga = open("/dev/rga",O_RDWR,0);
if(fd_rga < 0){
ALOGE(" rga open err");
}
}
}
virtual ~RgaCopybltThread() {
}
bool threadLoop() {
while(req_pend){
int tmp_pend = req_pend;
int i=0;
for(i=0;i<MAX_REQ;i++){
if(( tmp_pend>>i ) & 0x1){
if(ioctl(fd_rga, RGA_BLIT_ASYNC, &mRga_Request[i]) != 0){
ALOGE(" rga ioctl RGA_BLIT_ASYNC err !!!!!! fd_rga = %d", fd_rga);
}
req_pend &= ~(1<<i);
}
}
}
return false;
}
bool setRgaReq(struct rga_req *req){
int i=0;
if(fd_rga < 0){
ALOGE("can't not setRgaReq,fd_rga = %d",fd_rga);
return false;
}
for(i=0;i<MAX_REQ;i++){
if(!((req_pend>>i) & 0x1)){
req_pend |= (1<<i);
memcpy(&mRga_Request[i],req,sizeof(struct rga_req));
break;
}
}
if(i==MAX_REQ){
if(ioctl(fd_rga, RGA_BLIT_ASYNC, req) != 0){
ALOGE(" rga ioctl RGA_BLIT_ASYNC err !!!!!! fd_rga = %d", fd_rga);
}
}
run();
return true;
}
};
static status_t copyBlt(
const sp<GraphicBuffer>& dst,
const sp<GraphicBuffer>& src,
const Region& reg)
{
// src and dst with, height and format must be identical. no verification
// is done here.
status_t err;
bool ioctl_fail = false;
uint8_t const * src_bits = NULL;
err = src->lock(GRALLOC_USAGE_SW_READ_OFTEN, reg.bounds(), (void**)&src_bits);
ALOGE_IF(err, "error locking src buffer %s", strerror(-err));
uint8_t* dst_bits = NULL;
err = dst->lock(GRALLOC_USAGE_SW_WRITE_OFTEN, reg.bounds(), (void**)&dst_bits);
ALOGE_IF(err, "error locking dst buffer %s", strerror(-err));
int32_t vir_w = 0, vir_h = 0;
Region::const_iterator head_(reg.begin());
Region::const_iterator tail_(reg.end());
if (head_ != tail_ && src_bits && dst_bits) {
while (head_ != tail_) {
const Rect& r(*head_++);
ssize_t h_ = r.height();
if (h_ <= 0) continue;
int32_t tmp_w = r.right;
int32_t tmp_h = r.bottom;
vir_w = (vir_w >= tmp_w) ? vir_w : tmp_w;
vir_h = (vir_h >= tmp_h) ? vir_h : tmp_h;
}
}
static sp<RgaCopybltThread> rgaCopyblt_t(new RgaCopybltThread());
head_ = reg.begin();
if (head_ != tail_ && src_bits && dst_bits) {
//const size_t bpp = bytesPerPixel(src->format);
bool needsync = false;
struct rga_req Rga_Request;
while (head_ != tail_) {
if(needsync){
if(!rgaCopyblt_t->setRgaReq(&Rga_Request))
goto ERROR;
}
const Rect& r(*head_++);
ssize_t h = r.height();
if (h <= 0) continue;
memset(&Rga_Request,0x0,sizeof(Rga_Request));
//set src info
Rga_Request.src.yrgb_addr = 0; //(int)s;
Rga_Request.src.uv_addr = (int)src_bits;
Rga_Request.src.v_addr = Rga_Request.src.uv_addr;
Rga_Request.src.vir_w = src->stride;
Rga_Request.src.vir_h = vir_h;
Rga_Request.src.format = hwChangeRgaFormat(src->format); // RK_FORMAT_RGBA_8888
Rga_Request.src.act_w = r.width();
Rga_Request.src.act_h = r.height();
Rga_Request.src.x_offset = r.left;
Rga_Request.src.y_offset = r.top;
//set dst info
Rga_Request.dst.yrgb_addr = 0; //(int)d;
Rga_Request.dst.uv_addr = (int)dst_bits;
Rga_Request.dst.v_addr = Rga_Request.dst.uv_addr;
Rga_Request.dst.vir_w = dst->stride;
Rga_Request.dst.vir_h = vir_h;
Rga_Request.dst.act_w = r.width();
Rga_Request.dst.act_h = r.height();
Rga_Request.clip.xmin = 0;
Rga_Request.clip.xmax = Rga_Request.dst.vir_w - 1;
Rga_Request.clip.ymin = 0;
Rga_Request.clip.ymax = Rga_Request.dst.vir_h - 1;
Rga_Request.dst.x_offset = r.left;
Rga_Request.dst.y_offset = r.top;
Rga_Request.sina = 0;
Rga_Request.cosa = 0x10000;
Rga_Request.dst.format = Rga_Request.src.format; // RK_FORMAT_RGBA_8888
Rga_Request.alpha_rop_flag |= (1 << 5);
Rga_Request.mmu_info.mmu_en = 1;
Rga_Request.mmu_info.mmu_flag = ((2 & 0x3) << 4) | 1;
Rga_Request.mmu_info.mmu_flag |= ((1<<31) | (1 << 8) | (1<<10));
needsync = true;
}
if(needsync){
if(!rgaCopyblt_t->setRgaReq(&Rga_Request))
goto ERROR;
}
}
ERROR:
if(ioctl_fail){
Region::const_iterator head(reg.begin());
Region::const_iterator tail(reg.end());
if (head != tail && src_bits && dst_bits) {
const size_t bpp = bytesPerPixel(src->format);
const size_t dbpr = dst->stride * bpp;
const size_t sbpr = src->stride * bpp;
while (head != tail) {
const Rect& r(*head++);
ssize_t h = r.height();
if (h <= 0) continue;
size_t size = r.width() * bpp;
uint8_t const * s = src_bits + (r.left + src->stride * r.top) * bpp;
uint8_t * d = dst_bits + (r.left + dst->stride * r.top) * bpp;
if (dbpr==sbpr && size==sbpr) {
size *= h;
h = 1;
}
do {
memcpy(d, s, size);
d += dbpr;
s += sbpr;
} while (--h > 0);
}
}
}
if (src_bits)
src->unlock();
......@@ -790,6 +1153,7 @@ static status_t copyBlt(
return err;
}
#endif //endifdef USE_RGA_COPYBLT just use in rk32xx
// ----------------------------------------------------------------------------
......@@ -820,6 +1184,31 @@ status_t Surface::lock(
Region newDirtyRegion;
if (inOutDirtyBounds) {
#ifdef USE_LCDC_COMPOSER
int32_t tmp_l = inOutDirtyBounds->left;
int32_t tmp_r = inOutDirtyBounds->right;
int32_t tmp_t = inOutDirtyBounds->top;
int32_t tmp_b = inOutDirtyBounds->bottom;
if(mTransform == 4){
inOutDirtyBounds->left = tmp_t;
inOutDirtyBounds->right = tmp_b;
inOutDirtyBounds->top = backBuffer->height - tmp_r;
inOutDirtyBounds->bottom = backBuffer->height - tmp_l;
}
if(mTransform == 3){
inOutDirtyBounds->left = backBuffer->width - tmp_r;
inOutDirtyBounds->right = backBuffer->width - tmp_l;
inOutDirtyBounds->top = backBuffer->height - tmp_b;
inOutDirtyBounds->bottom = backBuffer->height - tmp_t;
}
if(mTransform == 7){
inOutDirtyBounds->left = backBuffer->width - tmp_b;
inOutDirtyBounds->right = backBuffer->width - tmp_t;;
inOutDirtyBounds->top = tmp_l;
inOutDirtyBounds->bottom = tmp_r;
}
#endif
newDirtyRegion.set(static_cast<Rect const&>(*inOutDirtyBounds));
newDirtyRegion.andSelf(bounds);
} else {
......@@ -827,6 +1216,7 @@ status_t Surface::lock(
}
// figure out if we can copy the frontbuffer back
int backBufferSlot(getSlotFromBufferLocked(backBuffer.get()));
const sp<GraphicBuffer>& frontBuffer(mPostedBuffer);
const bool canCopyBack = (frontBuffer != 0 &&
backBuffer->width == frontBuffer->width &&
......@@ -834,15 +1224,23 @@ status_t Surface::lock(
backBuffer->format == frontBuffer->format);
if (canCopyBack) {
// copy the area that is invalid and not repainted this round
const Region copyback(mDirtyRegion.subtract(newDirtyRegion));
Mutex::Autolock lock(mMutex);
Region oldDirtyRegion;
if(mSlots[backBufferSlot].dirtyRegion.isEmpty()) {
oldDirtyRegion.set(bounds);
} else {
for(int i = 0 ; i < NUM_BUFFER_SLOTS; i++ ) {
if(i != backBufferSlot && !mSlots[i].dirtyRegion.isEmpty())
oldDirtyRegion.orSelf(mSlots[i].dirtyRegion);
}
}
const Region copyback(oldDirtyRegion.subtract(newDirtyRegion));
if (!copyback.isEmpty())
copyBlt(backBuffer, frontBuffer, copyback);
} else {
// if we can't copy-back anything, modify the user's dirty
// region to make sure they redraw the whole buffer
newDirtyRegion.set(bounds);
mDirtyRegion.clear();
Mutex::Autolock lock(mMutex);
for (size_t i=0 ; i<NUM_BUFFER_SLOTS ; i++) {
mSlots[i].dirtyRegion.clear();
......@@ -852,15 +1250,9 @@ status_t Surface::lock(
{ // scope for the lock
Mutex::Autolock lock(mMutex);
int backBufferSlot(getSlotFromBufferLocked(backBuffer.get()));
if (backBufferSlot >= 0) {
Region& dirtyRegion(mSlots[backBufferSlot].dirtyRegion);
mDirtyRegion.subtract(dirtyRegion);
dirtyRegion = newDirtyRegion;
}
mSlots[backBufferSlot].dirtyRegion = newDirtyRegion;
}
mDirtyRegion.orSelf(newDirtyRegion);
if (inOutDirtyBounds) {
*inOutDirtyBounds = newDirtyRegion.getBounds();
}
......@@ -904,6 +1296,13 @@ status_t Surface::unlockAndPost()
mPostedBuffer = mLockedBuffer;
mLockedBuffer = 0;
#if (defined USE_LCDC_COMPOSER) || (defined USE_RGA_COPYBLT)
if(fd_rga != -1){
if(ioctl(fd_rga, RGA_FLUSH, NULL) != 0) {
ALOGE("unlockAndPost RGA_FLUSH err, fd_rga: %d, err: %d ", fd_rga, err);
}
}
#endif
return err;
}
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment