Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit cb6b9041 authored by Mathias Agopian's avatar Mathias Agopian
Browse files

fixed some issues with the software renderer when surfaces are made current.

there was several issues:
- when a surface was made non-current, the last frame wasn't shown and the buffer could stay locked
- when a surface was made current the 2nd time, it would not dequeue a new buffer

now, queue/dequeue are done when the surface is made current.

for this to work, a new query() hook had to be added on android_native_window_t, it allows to retrieve some attributes of a window (currently only width and height).
parent 69bdcb9b
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -62,6 +62,7 @@ private:
    static int dequeueBuffer(android_native_window_t* window, android_native_buffer_t** buffer);
    static int lockBuffer(android_native_window_t* window, android_native_buffer_t* buffer);
    static int queueBuffer(android_native_window_t* window, android_native_buffer_t* buffer);
    static int query(android_native_window_t* window, int what, int* value);
    
    framebuffer_device_t* fbDev;
    alloc_device_t* grDev;
+6 −0
Original line number Diff line number Diff line
@@ -115,6 +115,8 @@ private:
    sp<ISurface>                mSurface;
    SurfaceID                   mToken;
    uint32_t                    mIdentity;
    uint32_t                    mWidth;
    uint32_t                    mHeight;
    PixelFormat                 mFormat;
    uint32_t                    mFlags;
    mutable Mutex               mLock;
@@ -192,10 +194,12 @@ private:
    static int dequeueBuffer(android_native_window_t* window, android_native_buffer_t** buffer);
    static int lockBuffer(android_native_window_t* window, android_native_buffer_t* buffer);
    static int queueBuffer(android_native_window_t* window, android_native_buffer_t* buffer);
    static int query(android_native_window_t* window, int what, int* value);

    int dequeueBuffer(android_native_buffer_t** buffer);
    int lockBuffer(android_native_buffer_t* buffer);
    int queueBuffer(android_native_buffer_t* buffer);
    int query(int what, int* value);

    status_t dequeueBuffer(sp<SurfaceBuffer>* buffer);
    status_t lockBuffer(const sp<SurfaceBuffer>& buffer);
@@ -209,6 +213,8 @@ private:
    sp<SurfaceBuffer>           mLockedBuffer;
    SurfaceID                   mToken;
    uint32_t                    mIdentity;
    uint32_t                    mWidth;
    uint32_t                    mHeight;
    PixelFormat                 mFormat;
    uint32_t                    mFlags;
    mutable Region              mDirtyRegion;
+14 −1
Original line number Diff line number Diff line
@@ -60,6 +60,12 @@ struct android_native_base_t

// ---------------------------------------------------------------------------

/* attributes queriable with query() */
enum {
    NATIVE_WINDOW_WIDTH     = 0,
    NATIVE_WINDOW_HEIGHT    = 1
};

struct android_native_window_t 
{
#ifdef __cplusplus
@@ -129,8 +135,15 @@ struct android_native_window_t
    int     (*queueBuffer)(struct android_native_window_t* window,
                struct android_native_buffer_t* buffer);

    /*
     * hook used to retrieve information about the native window.
     * 
     * Returns 0 on success or -errno on error.
     */
    int     (*query)(struct android_native_window_t* window,
            int what, int* value);
    
    void* reserved_proc[5];
    void* reserved_proc[4];
};

// ---------------------------------------------------------------------------
+18 −0
Original line number Diff line number Diff line
@@ -124,6 +124,7 @@ FramebufferNativeWindow::FramebufferNativeWindow()
    android_native_window_t::dequeueBuffer = dequeueBuffer;
    android_native_window_t::lockBuffer = lockBuffer;
    android_native_window_t::queueBuffer = queueBuffer;
    android_native_window_t::query = query;
}

FramebufferNativeWindow::~FramebufferNativeWindow() {
@@ -198,6 +199,23 @@ int FramebufferNativeWindow::queueBuffer(android_native_window_t* window,
    return res;
}

int FramebufferNativeWindow::query(android_native_window_t* window,
        int what, int* value) 
{
    FramebufferNativeWindow* self = getSelf(window);
    Mutex::Autolock _l(self->mutex);
    framebuffer_device_t* fb = self->fbDev;
    switch (what) {
        case NATIVE_WINDOW_WIDTH:
            *value = fb->width;
            return NO_ERROR;
        case NATIVE_WINDOW_HEIGHT:
            *value = fb->height;
            return NO_ERROR;
    }
    return BAD_VALUE;
}

// ----------------------------------------------------------------------------
}; // namespace android
// ----------------------------------------------------------------------------
+34 −1
Original line number Diff line number Diff line
@@ -180,7 +180,7 @@ SurfaceControl::SurfaceControl(
        uint32_t w, uint32_t h, PixelFormat format, uint32_t flags)
    : mClient(client), mSurface(surface),
      mToken(data.token), mIdentity(data.identity),
      mFormat(format), mFlags(flags)
      mWidth(w), mHeight(h), mFormat(format), mFlags(flags)
{
}
        
@@ -338,6 +338,8 @@ status_t SurfaceControl::writeSurfaceToParcel(
    uint32_t format = 0;
    SurfaceID token = -1;
    uint32_t identity = 0;
    uint32_t width = 0;
    uint32_t height = 0;
    sp<SurfaceComposerClient> client;
    sp<ISurface> sur;
    if (SurfaceControl::isValid(control)) {
@@ -345,6 +347,8 @@ status_t SurfaceControl::writeSurfaceToParcel(
        identity = control->mIdentity;
        client   = control->mClient;
        sur      = control->mSurface;
        width    = control->mWidth;
        height   = control->mHeight;
        format   = control->mFormat;
        flags    = control->mFlags;
    }
@@ -352,6 +356,8 @@ status_t SurfaceControl::writeSurfaceToParcel(
    parcel->writeStrongBinder(sur!=0     ? sur->asBinder()      : NULL);
    parcel->writeInt32(token);
    parcel->writeInt32(identity);
    parcel->writeInt32(width);
    parcel->writeInt32(height);
    parcel->writeInt32(format);
    parcel->writeInt32(flags);
    return NO_ERROR;
@@ -373,6 +379,7 @@ sp<Surface> SurfaceControl::getSurface() const
Surface::Surface(const sp<SurfaceControl>& surface)
    : mClient(surface->mClient), mSurface(surface->mSurface),
      mToken(surface->mToken), mIdentity(surface->mIdentity),
      mWidth(surface->mWidth), mHeight(surface->mHeight),
      mFormat(surface->mFormat), mFlags(surface->mFlags),
      mBufferMapper(BufferMapper::get())
{
@@ -386,6 +393,8 @@ Surface::Surface(const Parcel& parcel)
    mSurface    = interface_cast<ISurface>(parcel.readStrongBinder());
    mToken      = parcel.readInt32();
    mIdentity   = parcel.readInt32();
    mWidth      = parcel.readInt32();
    mHeight     = parcel.readInt32();
    mFormat     = parcel.readInt32();
    mFlags      = parcel.readInt32();

@@ -401,6 +410,7 @@ void Surface::init()
    android_native_window_t::dequeueBuffer    = dequeueBuffer;
    android_native_window_t::lockBuffer       = lockBuffer;
    android_native_window_t::queueBuffer      = queueBuffer;
    android_native_window_t::query            = query;
    mSwapRectangle.makeInvalid();
    DisplayInfo dinfo;
    SurfaceComposerClient::getDisplayInfo(0, &dinfo);
@@ -492,6 +502,13 @@ int Surface::queueBuffer(android_native_window_t* window,
    return self->queueBuffer(buffer);
}

int Surface::query(android_native_window_t* window, 
        int what, int* value)
{
    Surface* self = getSelf(window);
    return self->query(what, value);
}

// ----------------------------------------------------------------------------

status_t Surface::dequeueBuffer(sp<SurfaceBuffer>* buffer)
@@ -499,6 +516,9 @@ status_t Surface::dequeueBuffer(sp<SurfaceBuffer>* buffer)
    android_native_buffer_t* out;
    status_t err = dequeueBuffer(&out);
    *buffer = SurfaceBuffer::getSelf(out);
    // reset the width/height with the what we get from the buffer
    mWidth  = uint32_t(out->width);
    mHeight = uint32_t(out->height);
    return err;
}

@@ -586,6 +606,19 @@ int Surface::queueBuffer(android_native_buffer_t* buffer)
    return NO_ERROR;
}

int Surface::query(int what, int* value)
{
    switch (what) {
        case NATIVE_WINDOW_WIDTH:
            *value = int(mWidth);
            return NO_ERROR;
        case NATIVE_WINDOW_HEIGHT:
            *value = int(mHeight);
            return NO_ERROR;
    }
    return BAD_VALUE;
}

// ----------------------------------------------------------------------------

status_t Surface::lock(SurfaceInfo* info, bool blocking) {
Loading