Refactoring parcel a little, parcelTransact needs more work

This commit is contained in:
plutoo 2017-11-26 09:22:45 +01:00 committed by yellows8
parent 1cf6bb2056
commit 7f2135754a
2 changed files with 57 additions and 43 deletions

View File

@ -2,10 +2,10 @@
#include <switch.h>
typedef struct {
u8 ParcelData[0x400];
u32 ParcelData_maxsize;
u32 ParcelData_size;
u32 ParcelData_pos;
u8 payload[0x400];
u32 capacity;
u32 size;
u32 read_pos;
u8 *ParcelObjects;
u32 ParcelObjectsSize;
@ -19,7 +19,7 @@ void* parcelReadData(parcelContext *ctx, void* data, size_t data_size);
void parcelWriteInt32(parcelContext *ctx, s32 val);
void parcelWriteUInt32(parcelContext *ctx, u32 val);
void parcelWriteString16_fromchar(parcelContext *ctx, const char *str);
void parcelWriteString16(parcelContext *ctx, const char *str);
void parcelWriteInterfaceToken(parcelContext *ctx, const char *interface);

View File

@ -12,7 +12,7 @@ size_t parcel_reply_log_size = 0;
void parcelInitializeContext(parcelContext *ctx) {
memset(ctx, 0, sizeof(parcelContext));
ctx->ParcelData_maxsize = sizeof(ctx->ParcelData);
ctx->capacity = sizeof(ctx->payload);
}
Result parcelTransact(binderSession *session, u32 code, parcelContext *in_parcel, parcelContext *parcel_reply) {
@ -22,31 +22,36 @@ Result parcelTransact(binderSession *session, u32 code, parcelContext *in_parcel
size_t outparcel_size = sizeof(outparcel);
u32 *inparcel32 = (u32*)inparcel;
u32 *outparcel32 = (u32*)outparcel;
u32 ParcelDataSize = in_parcel->ParcelData_size;
u32 payloadSize = in_parcel->size;
u32 ParcelObjectsSize = in_parcel->ParcelObjectsSize;
memset(inparcel, 0, sizeof(inparcel));
memset(outparcel, 0, outparcel_size);
if((size_t)ParcelDataSize >= sizeof(inparcel) || (size_t)ParcelObjectsSize >= sizeof(inparcel) || ((size_t)ParcelDataSize)+((size_t)ParcelObjectsSize)+0x10 >= sizeof(inparcel)) return MAKERESULT(MODULE_LIBNX, LIBNX_BADINPUT);
if ((size_t)payloadSize >= sizeof(inparcel))
return MAKERESULT(MODULE_LIBNX, LIBNX_BADINPUT);
if ((size_t)ParcelObjectsSize >= sizeof(inparcel))
return MAKERESULT(MODULE_LIBNX, LIBNX_BADINPUT);
if (((size_t)payloadSize)+((size_t)ParcelObjectsSize)+0x10 >= sizeof(inparcel))
return MAKERESULT(MODULE_LIBNX, LIBNX_BADINPUT);
inparcel32[0] = ParcelDataSize;//ParcelDataSize
inparcel32[1] = 0x10;//ParcelDataOffset
inparcel32[0] = payloadSize;//payloadSize
inparcel32[1] = 0x10;//payloadOffset
inparcel32[2] = ParcelObjectsSize;//ParcelObjectsSize
inparcel32[3] = 0x10+ParcelDataSize;//ParcelObjectsOffset
inparcel32[3] = 0x10+payloadSize;//ParcelObjectsOffset
if(in_parcel->ParcelData && ParcelDataSize)memcpy(&inparcel[inparcel32[1]], in_parcel->ParcelData, ParcelDataSize);
if(in_parcel->payload && payloadSize)memcpy(&inparcel[inparcel32[1]], in_parcel->payload, payloadSize);
if(in_parcel->ParcelObjects && ParcelObjectsSize)memcpy(&inparcel[inparcel32[3]], in_parcel->ParcelObjects, ParcelObjectsSize);
rc = binderTransactParcel(session, code, inparcel, ParcelDataSize+ParcelObjectsSize+0x10, outparcel, outparcel_size, 0);
rc = binderTransactParcel(session, code, inparcel, payloadSize+ParcelObjectsSize+0x10, outparcel, outparcel_size, 0);
if (R_FAILED(rc)) return rc;
if((size_t)outparcel32[1] >= outparcel_size || ((size_t)outparcel32[0])+((size_t)outparcel32[1]) >= outparcel_size) return MAKERESULT(MODULE_LIBNX, LIBNX_BADINPUT);
if((size_t)outparcel32[2] >= outparcel_size || ((size_t)outparcel32[2])+((size_t)outparcel32[3]) >= outparcel_size) return MAKERESULT(MODULE_LIBNX, LIBNX_BADINPUT);
if((size_t)outparcel32[0] >= outparcel_size || (size_t)outparcel32[3] >= outparcel_size) return MAKERESULT(MODULE_LIBNX, LIBNX_BADINPUT);
memcpy(parcel_reply->ParcelData, &outparcel[outparcel32[1]], outparcel32[0]);
parcel_reply->ParcelData_size = outparcel32[0];
memcpy(parcel_reply->payload, &outparcel[outparcel32[1]], outparcel32[0]);
parcel_reply->size = outparcel32[0];
#ifdef PARCEL_LOGGING
if(parcel_reply_log_size + sizeof(inparcel) + outparcel_size <= sizeof(parcel_reply_log)) {
@ -61,43 +66,44 @@ Result parcelTransact(binderSession *session, u32 code, parcelContext *in_parcel
}
void* parcelWriteData(parcelContext *ctx, void* data, size_t data_size) {
void* ptr = &ctx->ParcelData[ctx->ParcelData_size];
void* ptr = &ctx->payload[ctx->size];
if(data_size & BIT(31))
return NULL;
if(data_size & BIT(31)) return NULL;
data_size = (data_size+3) & ~3;
if(ctx->ParcelData_size + data_size >= ctx->ParcelData_maxsize) return NULL;
if(ctx->size + data_size >= ctx->capacity)
return NULL;
if(data)memcpy(ptr, data, data_size);
ctx->ParcelData_size+= data_size;
if (data)
memcpy(ptr, data, data_size);
ctx->size += data_size;
return ptr;
}
void* parcelReadData(parcelContext *ctx, void* data, size_t data_size) {
void* ptr = ctx->ParcelData;
size_t aligned_data_size;
void* ptr = ctx->payload;
if(data_size & BIT(31)) return NULL;
aligned_data_size = (data_size+3) & ~3;
if(data_size & BIT(31))
return NULL;
if(ctx->ParcelData_pos + aligned_data_size >= ctx->ParcelData_size) return NULL;
size_t aligned_data_size = (data_size+3) & ~3;
if(data)memcpy(data, &ctx->ParcelData[ctx->ParcelData_pos], data_size);
ctx->ParcelData_pos+= aligned_data_size;
if(ctx->read_pos + aligned_data_size >= ctx->size)
return NULL;
if(data)
memcpy(data, &ctx->payload[ctx->read_pos], data_size);
ctx->read_pos += aligned_data_size;
return ptr;
}
void parcelWriteInt32(parcelContext *ctx, s32 val) {
parcelWriteData(ctx, &val, sizeof(val));
}
void parcelWriteUInt32(parcelContext *ctx, u32 val) {
parcelWriteData(ctx, &val, sizeof(val));
}
void parcelWriteString16_fromchar(parcelContext *ctx, const char *str) {
void parcelWriteString16(parcelContext *ctx, const char *str) {
u32 pos, len;
u16 *ptr;
@ -106,18 +112,14 @@ void parcelWriteString16_fromchar(parcelContext *ctx, const char *str) {
len++;
ptr = parcelWriteData(ctx, NULL, len*2);
if(ptr==NULL)return;
if (ptr == NULL)
return;
for(pos=0; pos<len; pos++) {
for (pos=0; pos<len; pos++) {
ptr[pos] = (u16)str[pos];
}
}
void parcelWriteInterfaceToken(parcelContext *ctx, const char *interface) {
parcelWriteInt32(ctx, 0x100);
parcelWriteString16_fromchar(ctx, interface);
}
s32 parcelReadInt32(parcelContext *ctx) {
s32 val = 0;
parcelReadData(ctx, &val, sizeof(val));
@ -130,3 +132,15 @@ u32 parcelReadUInt32(parcelContext *ctx) {
return val;
}
void parcelWriteInt32(parcelContext *ctx, s32 val) {
parcelWriteData(ctx, &val, sizeof(val));
}
void parcelWriteUInt32(parcelContext *ctx, u32 val) {
parcelWriteData(ctx, &val, sizeof(val));
}
void parcelWriteInterfaceToken(parcelContext *ctx, const char *interface) {
parcelWriteInt32(ctx, 0x100);
parcelWriteString16(ctx, interface);
}