rlm@1: #include rlm@1: #include rlm@1: rlm@1: #include "CheatSearch.h" rlm@1: rlm@1: CheatSearchBlock cheatSearchBlocks[4]; rlm@1: rlm@1: CheatSearchData cheatSearchData = { rlm@1: 0, rlm@1: cheatSearchBlocks rlm@1: }; rlm@1: rlm@1: static bool cheatSearchEQ(u32 a, u32 b) rlm@1: { rlm@1: return a == b; rlm@1: } rlm@1: rlm@1: static bool cheatSearchNE(u32 a, u32 b) rlm@1: { rlm@1: return a != b; rlm@1: } rlm@1: rlm@1: static bool cheatSearchLT(u32 a, u32 b) rlm@1: { rlm@1: return a < b; rlm@1: } rlm@1: rlm@1: static bool cheatSearchLE(u32 a, u32 b) rlm@1: { rlm@1: return a <= b; rlm@1: } rlm@1: rlm@1: static bool cheatSearchGT(u32 a, u32 b) rlm@1: { rlm@1: return a > b; rlm@1: } rlm@1: rlm@1: static bool cheatSearchGE(u32 a, u32 b) rlm@1: { rlm@1: return a >= b; rlm@1: } rlm@1: rlm@1: static bool cheatSearchSignedEQ(s32 a, s32 b) rlm@1: { rlm@1: return a == b; rlm@1: } rlm@1: rlm@1: static bool cheatSearchSignedNE(s32 a, s32 b) rlm@1: { rlm@1: return a != b; rlm@1: } rlm@1: rlm@1: static bool cheatSearchSignedLT(s32 a, s32 b) rlm@1: { rlm@1: return a < b; rlm@1: } rlm@1: rlm@1: static bool cheatSearchSignedLE(s32 a, s32 b) rlm@1: { rlm@1: return a <= b; rlm@1: } rlm@1: rlm@1: static bool cheatSearchSignedGT(s32 a, s32 b) rlm@1: { rlm@1: return a > b; rlm@1: } rlm@1: rlm@1: static bool cheatSearchSignedGE(s32 a, s32 b) rlm@1: { rlm@1: return a >= b; rlm@1: } rlm@1: rlm@1: static bool (*cheatSearchFunc[])(u32, u32) = { rlm@1: cheatSearchEQ, rlm@1: cheatSearchNE, rlm@1: cheatSearchLT, rlm@1: cheatSearchLE, rlm@1: cheatSearchGT, rlm@1: cheatSearchGE rlm@1: }; rlm@1: rlm@1: static bool (*cheatSearchSignedFunc[])(s32, s32) = { rlm@1: cheatSearchSignedEQ, rlm@1: cheatSearchSignedNE, rlm@1: cheatSearchSignedLT, rlm@1: cheatSearchSignedLE, rlm@1: cheatSearchSignedGT, rlm@1: cheatSearchSignedGE rlm@1: }; rlm@1: rlm@1: void cheatSearchSetSavedAndBits(CheatSearchBlock *block) rlm@1: { rlm@1: if (!block->saved) rlm@1: { rlm@1: block->saved = (u8 *)malloc(block->size); rlm@1: memcpy(block->saved, block->data, block->size); rlm@1: } rlm@1: if (!block->bits) rlm@1: { rlm@1: block->bits = (u8 *)malloc(block->size >> 3); rlm@1: memset(block->bits, 0xff, block->size >> 3); rlm@1: } rlm@1: } rlm@1: rlm@1: void cheatSearchZeroBlock(CheatSearchBlock *block) rlm@1: { rlm@1: block->data = 0; rlm@1: block->offset = 0; rlm@1: block->size = 0; rlm@1: free(block->saved); rlm@1: free(block->bits); rlm@1: block->saved = 0; rlm@1: block->bits = 0; rlm@1: } rlm@1: rlm@1: void cheatSearchCleanup(CheatSearchData *cs) rlm@1: { rlm@1: int count = cs->count; rlm@1: rlm@1: for (int i = 0; i < count; i++) rlm@1: { rlm@1: CheatSearchBlock &block = cs->blocks[i]; rlm@1: free(block.saved); rlm@1: free(block.bits); rlm@1: block.saved = 0; rlm@1: block.bits = 0; rlm@1: } rlm@1: cs->count = 0; rlm@1: } rlm@1: rlm@1: void cheatSearchStart(const CheatSearchData *cs) rlm@1: { rlm@1: int count = cs->count; rlm@1: rlm@1: for (int i = 0; i < count; i++) rlm@1: { rlm@1: CheatSearchBlock *block = &cs->blocks[i]; rlm@1: rlm@1: memset(block->bits, 0xff, block->size >> 3); rlm@1: memcpy(block->saved, block->data, block->size); rlm@1: } rlm@1: } rlm@1: rlm@1: s32 cheatSearchSignedRead(u8 *data, int off, int size) rlm@1: { rlm@1: u32 res = data[off++]; rlm@1: rlm@1: switch (size) rlm@1: { rlm@1: case BITS_8: rlm@1: res <<= 24; rlm@1: return ((s32)res) >> 24; rlm@1: case BITS_16: rlm@1: res |= ((u32)data[off++])<<8; rlm@1: res <<= 16; rlm@1: return ((s32)res) >> 16; rlm@1: case BITS_32: rlm@1: res |= ((u32)data[off++])<<8; rlm@1: res |= ((u32)data[off++])<<16; rlm@1: res |= ((u32)data[off++])<<24; rlm@1: return (s32)res; rlm@1: } rlm@1: return (s32)res; rlm@1: } rlm@1: rlm@1: u32 cheatSearchRead(u8 *data, int off, int size) rlm@1: { rlm@1: u32 res = data[off++]; rlm@1: if (size == BITS_16) rlm@1: res |= ((u32)data[off++])<<8; rlm@1: else if (size == BITS_32) rlm@1: { rlm@1: res |= ((u32)data[off++])<<8; rlm@1: res |= ((u32)data[off++])<<16; rlm@1: res |= ((u32)data[off++])<<24; rlm@1: } rlm@1: return res; rlm@1: } rlm@1: rlm@1: void cheatSearch(const CheatSearchData *cs, int compare, int size, rlm@1: bool isSigned) rlm@1: { rlm@1: if (compare < 0 || compare > SEARCH_GE) rlm@1: return; rlm@1: int inc = 1; rlm@1: if (size == BITS_16) rlm@1: inc = 2; rlm@1: else if (size == BITS_32) rlm@1: inc = 4; rlm@1: rlm@1: if (isSigned) rlm@1: { rlm@1: bool (*func)(s32, s32) = cheatSearchSignedFunc[compare]; rlm@1: rlm@1: for (int i = 0; i < cs->count; i++) rlm@1: { rlm@1: CheatSearchBlock *block = &cs->blocks[i]; rlm@1: int size2 = block->size; rlm@1: u8 *bits = block->bits; rlm@1: u8 *data = block->data; rlm@1: u8 *saved = block->saved; rlm@1: rlm@1: for (int j = 0; j < size2; j += inc) rlm@1: { rlm@1: if (IS_BIT_SET(bits, j)) rlm@1: { rlm@1: s32 a = cheatSearchSignedRead(data, j, size); rlm@1: s32 b = cheatSearchSignedRead(saved, j, size); rlm@1: rlm@1: if (!func(a, b)) rlm@1: { rlm@1: CLEAR_BIT(bits, j); rlm@1: if (size == BITS_16) rlm@1: CLEAR_BIT(bits, j+1); rlm@1: if (size == BITS_32) rlm@1: { rlm@1: CLEAR_BIT(bits, j+2); rlm@1: CLEAR_BIT(bits, j+3); rlm@1: } rlm@1: } rlm@1: } rlm@1: } rlm@1: } rlm@1: } rlm@1: else rlm@1: { rlm@1: bool (*func)(u32, u32) = cheatSearchFunc[compare]; rlm@1: rlm@1: for (int i = 0; i < cs->count; i++) rlm@1: { rlm@1: CheatSearchBlock *block = &cs->blocks[i]; rlm@1: int size2 = block->size; rlm@1: u8 *bits = block->bits; rlm@1: u8 *data = block->data; rlm@1: u8 *saved = block->saved; rlm@1: rlm@1: for (int j = 0; j < size2; j += inc) rlm@1: { rlm@1: if (IS_BIT_SET(bits, j)) rlm@1: { rlm@1: u32 a = cheatSearchRead(data, j, size); rlm@1: u32 b = cheatSearchRead(saved, j, size); rlm@1: rlm@1: if (!func(a, b)) rlm@1: { rlm@1: CLEAR_BIT(bits, j); rlm@1: if (size == BITS_16) rlm@1: CLEAR_BIT(bits, j+1); rlm@1: if (size == BITS_32) rlm@1: { rlm@1: CLEAR_BIT(bits, j+2); rlm@1: CLEAR_BIT(bits, j+3); rlm@1: } rlm@1: } rlm@1: } rlm@1: } rlm@1: } rlm@1: } rlm@1: } rlm@1: rlm@1: void cheatSearchValue(const CheatSearchData *cs, int compare, int size, rlm@1: bool isSigned, u32 value) rlm@1: { rlm@1: if (compare < 0 || compare > SEARCH_GE) rlm@1: return; rlm@1: int inc = 1; rlm@1: if (size == BITS_16) rlm@1: inc = 2; rlm@1: else if (size == BITS_32) rlm@1: inc = 4; rlm@1: rlm@1: if (isSigned) rlm@1: { rlm@1: bool (*func)(s32, s32) = cheatSearchSignedFunc[compare]; rlm@1: rlm@1: for (int i = 0; i < cs->count; i++) rlm@1: { rlm@1: CheatSearchBlock *block = &cs->blocks[i]; rlm@1: int size2 = block->size; rlm@1: u8 *bits = block->bits; rlm@1: u8 *data = block->data; rlm@1: rlm@1: for (int j = 0; j < size2; j += inc) rlm@1: { rlm@1: if (IS_BIT_SET(bits, j)) rlm@1: { rlm@1: s32 a = cheatSearchSignedRead(data, j, size); rlm@1: s32 b = (s32)value; rlm@1: rlm@1: if (!func(a, b)) rlm@1: { rlm@1: CLEAR_BIT(bits, j); rlm@1: if (size == BITS_16) rlm@1: CLEAR_BIT(bits, j+1); rlm@1: if (size == BITS_32) rlm@1: { rlm@1: CLEAR_BIT(bits, j+2); rlm@1: CLEAR_BIT(bits, j+3); rlm@1: } rlm@1: } rlm@1: } rlm@1: } rlm@1: } rlm@1: } rlm@1: else rlm@1: { rlm@1: bool (*func)(u32, u32) = cheatSearchFunc[compare]; rlm@1: rlm@1: for (int i = 0; i < cs->count; i++) rlm@1: { rlm@1: CheatSearchBlock *block = &cs->blocks[i]; rlm@1: int size2 = block->size; rlm@1: u8 *bits = block->bits; rlm@1: u8 *data = block->data; rlm@1: rlm@1: for (int j = 0; j < size2; j += inc) rlm@1: { rlm@1: if (IS_BIT_SET(bits, j)) rlm@1: { rlm@1: u32 a = cheatSearchRead(data, j, size); rlm@1: rlm@1: if (!func(a, value)) rlm@1: { rlm@1: CLEAR_BIT(bits, j); rlm@1: if (size == BITS_16) rlm@1: CLEAR_BIT(bits, j+1); rlm@1: if (size == BITS_32) rlm@1: { rlm@1: CLEAR_BIT(bits, j+2); rlm@1: CLEAR_BIT(bits, j+3); rlm@1: } rlm@1: } rlm@1: } rlm@1: } rlm@1: } rlm@1: } rlm@1: } rlm@1: rlm@1: int cheatSearchGetCount(const CheatSearchData *cs, int size) rlm@1: { rlm@1: int res = 0; rlm@1: int inc = 1; rlm@1: if (size == BITS_16) rlm@1: inc = 2; rlm@1: else if (size == BITS_32) rlm@1: inc = 4; rlm@1: rlm@1: for (int i = 0; i < cs->count; i++) rlm@1: { rlm@1: CheatSearchBlock *block = &cs->blocks[i]; rlm@1: rlm@1: int size2 = block->size; rlm@1: u8 *bits = block->bits; rlm@1: for (int j = 0; j < size2; j += inc) rlm@1: { rlm@1: if (IS_BIT_SET(bits, j)) rlm@1: res++; rlm@1: } rlm@1: } rlm@1: return res; rlm@1: } rlm@1: rlm@1: void cheatSearchUpdateValues(const CheatSearchData *cs) rlm@1: { rlm@1: for (int i = 0; i < cs->count; i++) rlm@1: { rlm@1: CheatSearchBlock *block = &cs->blocks[i]; rlm@1: rlm@1: memcpy(block->saved, block->data, block->size); rlm@1: } rlm@1: }