Added bufferProducerGraphicBuffer struct. Parse the bufferProducerRequestBuffer parcel reply properly. Renamed bufferProducerTegraBufferInit to bufferProducerGraphicBufferInit + renamed the enum for it, and handle input/output for it properly. Properly return rc in bufferProducerGraphicBufferInit().

This commit is contained in:
yellows8 2017-12-19 12:13:37 -05:00
parent c0780f5267
commit dd4a9bbca6
4 changed files with 37 additions and 23 deletions

View File

@ -25,6 +25,10 @@ typedef struct {
u32 numPendingBuffers; u32 numPendingBuffers;
} PACKED bufferProducerQueueBufferOutput; } PACKED bufferProducerQueueBufferOutput;
typedef struct {
u32 unk[0x16c>>2];
} PACKED bufferProducerGraphicBuffer;
//From Android window.h. //From Android window.h.
/* attributes queriable with query() */ /* attributes queriable with query() */
enum { enum {
@ -49,11 +53,11 @@ enum {
Result bufferProducerInitialize(binderSession *session); Result bufferProducerInitialize(binderSession *session);
void bufferProducerExit(); void bufferProducerExit();
Result bufferProducerRequestBuffer(s32 bufferIdx); Result bufferProducerRequestBuffer(s32 bufferIdx, bufferProducerGraphicBuffer *buf);
Result bufferProducerDequeueBuffer(bool async, u32 width, u32 height, s32 format, u32 usage, s32 *buf, bufferProducerFence *fence); Result bufferProducerDequeueBuffer(bool async, u32 width, u32 height, s32 format, u32 usage, s32 *buf, bufferProducerFence *fence);
Result bufferProducerDetachBuffer(s32 slot); Result bufferProducerDetachBuffer(s32 slot);
Result bufferProducerQueueBuffer(s32 buf, bufferProducerQueueBufferInput *input, bufferProducerQueueBufferOutput *output); Result bufferProducerQueueBuffer(s32 buf, bufferProducerQueueBufferInput *input, bufferProducerQueueBufferOutput *output);
Result bufferProducerQuery(s32 what, s32* value); Result bufferProducerQuery(s32 what, s32* value);
Result bufferProducerConnect(s32 api, bool producerControlledByApp, bufferProducerQueueBufferOutput *output); Result bufferProducerConnect(s32 api, bool producerControlledByApp, bufferProducerQueueBufferOutput *output);
Result bufferProducerDisconnect(s32 api); Result bufferProducerDisconnect(s32 api);
Result bufferProducerTegraBufferInit(s32 buf, u8 input[0x178]); Result bufferProducerGraphicBufferInit(s32 buf, bufferProducerGraphicBuffer *input);

View File

@ -20,7 +20,7 @@ enum {
/* 0xB */ DISCONNECT, /* 0xB */ DISCONNECT,
/* 0xC */ SET_SIDEBAND_STREAM, /* 0xC */ SET_SIDEBAND_STREAM,
/* 0xD */ ALLOCATE_BUFFERS, /* 0xD */ ALLOCATE_BUFFERS,
/* 0xE */ TEGRA_BUFFER_INIT, // Custom Switch-specific command - unofficial name. /* 0xE */ GRAPHIC_BUFFER_INIT, // Custom Switch-specific command - unofficial name.
}; };
static char g_bufferProducer_InterfaceDescriptor[] = "android.gui.IGraphicBufferProducer"; static char g_bufferProducer_InterfaceDescriptor[] = "android.gui.IGraphicBufferProducer";
@ -38,7 +38,7 @@ void bufferProducerExit()
g_bufferProducerBinderSession = NULL; g_bufferProducerBinderSession = NULL;
} }
Result bufferProducerRequestBuffer(s32 bufferIdx) Result bufferProducerRequestBuffer(s32 bufferIdx, bufferProducerGraphicBuffer *buf)
{ {
Result rc; Result rc;
Parcel parcel, parcel_reply; Parcel parcel, parcel_reply;
@ -55,12 +55,15 @@ Result bufferProducerRequestBuffer(s32 bufferIdx)
rc = parcelTransact(g_bufferProducerBinderSession, REQUEST_BUFFER, &parcel, &parcel_reply); rc = parcelTransact(g_bufferProducerBinderSession, REQUEST_BUFFER, &parcel, &parcel_reply);
if (R_SUCCEEDED(rc)) { if (R_SUCCEEDED(rc)) {
/*
int nonNull = parcelReadInt32(&parcel_reply); int nonNull = parcelReadInt32(&parcel_reply);
if (nonNull != 0) { if (nonNull != 0) {
// Fixme size_t tmpsize=0;
fatalSimple(222 | (100 << 9)); void* tmp_ptr;
tmp_ptr = parcelReadFlattenedObject(&parcel_reply, &tmpsize);
if (tmp_ptr==NULL || tmpsize!=sizeof(bufferProducerGraphicBuffer)) return MAKERESULT(MODULE_LIBNX, LIBNX_BADINPUT);
if (buf) memcpy(buf, tmp_ptr, sizeof(bufferProducerGraphicBuffer));
} }
int status = parcelReadInt32(&parcel_reply); int status = parcelReadInt32(&parcel_reply);
@ -68,7 +71,6 @@ Result bufferProducerRequestBuffer(s32 bufferIdx)
if (status != 0) { if (status != 0) {
rc = MAKERESULT(MODULE_LIBNX, LIBNX_BUFFERPRODUCER_ERROR); rc = MAKERESULT(MODULE_LIBNX, LIBNX_BUFFERPRODUCER_ERROR);
} }
*/
} }
return rc; return rc;
@ -247,10 +249,11 @@ Result bufferProducerDisconnect(s32 api)
return rc; return rc;
} }
Result bufferProducerTegraBufferInit(s32 buf, u8 input[0x178]) Result bufferProducerGraphicBufferInit(s32 buf, bufferProducerGraphicBuffer *input)
{ {
Result rc; Result rc;
Parcel parcel, parcel_reply; Parcel parcel, parcel_reply;
bool flag = 0;
if (g_bufferProducerBinderSession==NULL) return MAKERESULT(MODULE_LIBNX, LIBNX_NOTINITIALIZED); if (g_bufferProducerBinderSession==NULL) return MAKERESULT(MODULE_LIBNX, LIBNX_NOTINITIALIZED);
@ -259,14 +262,19 @@ Result bufferProducerTegraBufferInit(s32 buf, u8 input[0x178])
parcelWriteInterfaceToken(&parcel, g_bufferProducer_InterfaceDescriptor); parcelWriteInterfaceToken(&parcel, g_bufferProducer_InterfaceDescriptor);
parcelWriteInt32(&parcel, buf); parcelWriteInt32(&parcel, buf);
parcelWriteData(&parcel, input, 0x178);
rc = parcelTransact(g_bufferProducerBinderSession, TEGRA_BUFFER_INIT, &parcel, &parcel_reply); if (input!=NULL) flag = 1;
parcelWriteInt32(&parcel, flag);
if (flag) parcelWriteFlattenedObject(&parcel, input, sizeof(bufferProducerGraphicBuffer));
rc = parcelTransact(g_bufferProducerBinderSession, GRAPHIC_BUFFER_INIT, &parcel, &parcel_reply);
if (R_SUCCEEDED(rc)) { if (R_SUCCEEDED(rc)) {
// TODO: parse reply int result = parcelReadInt32(&parcel_reply);
if (result != 0)
rc = MAKERESULT(MODULE_LIBNX, LIBNX_BUFFERPRODUCER_ERROR);
} }
return 0; return rc;
} }

View File

@ -162,7 +162,7 @@ static Result _gfxInit(viServiceType servicetype, const char *DisplayName, u32 L
rc = _gfxDequeueBuffer(); rc = _gfxDequeueBuffer();
if (R_FAILED(rc)) break; if (R_FAILED(rc)) break;
rc = bufferProducerRequestBuffer(g_gfxCurrentProducerBuffer); rc = bufferProducerRequestBuffer(g_gfxCurrentProducerBuffer, NULL);
if (R_FAILED(rc)) break; if (R_FAILED(rc)) break;
g_gfx_ProducerSlotsRequested[i] = 1; g_gfx_ProducerSlotsRequested[i] = 1;

View File

@ -47,8 +47,9 @@ static u64 nvmap_obj6_mapbuffer_xdb_offset;
static u64 g_nvgfx_gpfifo_pos = 0; static u64 g_nvgfx_gpfifo_pos = 0;
//Some of this struct is based on tegra_dc_ext_flip_windowattr. //Some of this struct is based on tegra_dc_ext_flip_windowattr.
static u32 g_gfxprod_BufferInitData[0x178>>2] = { //TODO: How much of this struct do official apps really set? Most of it seems to be used as-is from the bufferProducerRequestBuffer() output.
0x1, 0x16c, 0x0, static bufferProducerGraphicBuffer g_gfxprod_BufferInitData = {
.unk = {
0x47424652, 0x47424652,
1280, 720, 1280, 720,
1280, 1280,
@ -79,6 +80,7 @@ static u32 g_gfxprod_BufferInitData[0x178>>2] = {
0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0,
0x0, 0x0,
0x0, 0x0 //Unknown, some timestamp perhaps? 0x0, 0x0 //Unknown, some timestamp perhaps?
}
}; };
Result nvmapobjInitialize(nvmapobj *obj, size_t size) { Result nvmapobjInitialize(nvmapobj *obj, size_t size) {
@ -132,7 +134,7 @@ Result nvgfxInitialize(void) {
u32 pos=0, i=0; u32 pos=0, i=0;
s32 tmp=0; s32 tmp=0;
u32 tmpval=0; u32 tmpval=0;
u64 *ptr64 = (u64*)g_gfxprod_BufferInitData; u64 *ptr64 = (u64*)g_gfxprod_BufferInitData.unk;
if(g_nvgfxInitialized)return 0; if(g_nvgfxInitialized)return 0;
u32 framebuf_nvmap_handle = 0;//Special handle ID for framebuf/windowbuf. u32 framebuf_nvmap_handle = 0;//Special handle ID for framebuf/windowbuf.
@ -311,12 +313,12 @@ Result nvgfxInitialize(void) {
//The above gets a nvmap_handle, but normally it's the same value passed to nvioctlNvmap_GetId(). //The above gets a nvmap_handle, but normally it's the same value passed to nvioctlNvmap_GetId().
g_gfxprod_BufferInitData[0xa] = i; g_gfxprod_BufferInitData.unk[0x7] = i;
g_gfxprod_BufferInitData[0xe] = tmpval; g_gfxprod_BufferInitData.unk[0xb] = tmpval;
g_gfxprod_BufferInitData[0x20] = tmpval; g_gfxprod_BufferInitData.unk[0x1d] = tmpval;
g_gfxprod_BufferInitData[0x21] = g_nvgfx_singleframebuf_size*i; g_gfxprod_BufferInitData.unk[0x1e] = g_nvgfx_singleframebuf_size*i;
ptr64[0x170>>3] = svcGetSystemTick(); ptr64[0x164>>3] = svcGetSystemTick();
rc = bufferProducerTegraBufferInit(i, (u8*)g_gfxprod_BufferInitData); rc = bufferProducerGraphicBufferInit(i, &g_gfxprod_BufferInitData);
if (R_FAILED(rc)) break; if (R_FAILED(rc)) break;
} }
if (R_FAILED(rc)) break; if (R_FAILED(rc)) break;