diff --git a/runtime/LibcWrappers.cpp b/runtime/LibcWrappers.cpp index 15ded7dc..68b0636a 100644 --- a/runtime/LibcWrappers.cpp +++ b/runtime/LibcWrappers.cpp @@ -635,4 +635,48 @@ long int SYM(atol)(const char *s) { return result; } + +char *SYM(strcpy)(char *dest, const char *src) { + tryAlternative(dest, _sym_get_parameter_expression(0), SYM(strcpy)); + tryAlternative(src, _sym_get_parameter_expression(1), SYM(strcpy)); + + auto *result = strcpy(dest, src); + _sym_set_return_expression(nullptr); + + size_t cpyLen = strlen(src); + if (isConcrete(src, cpyLen) && isConcrete(dest, cpyLen)) + return result; + + auto srcShadow = ReadOnlyShadow(src, cpyLen); + auto destShadow = ReadWriteShadow(dest, cpyLen); + + std::copy(srcShadow.begin(), srcShadow.end(), destShadow.begin()); + + return result; +} + +char *SYM(strncpy)(char *dest, const char *src, size_t n) { + tryAlternative(dest, _sym_get_parameter_expression(0), SYM(strncpy)); + tryAlternative(src, _sym_get_parameter_expression(1), SYM(strncpy)); + tryAlternative(n, _sym_get_parameter_expression(2), SYM(strncpy)); + + auto *result = strncpy(dest, src, n); + _sym_set_return_expression(nullptr); + + size_t srcLen = strnlen(src, n); + size_t copied = std::min(n, srcLen); + if (isConcrete(src, copied) && isConcrete(dest, n)) + return result; + + auto srcShadow = ReadOnlyShadow(src, copied); + auto destShadow = ReadWriteShadow(dest, n); + + std::copy(srcShadow.begin(), srcShadow.end(), destShadow.begin()); + if (copied < n) { + ReadWriteShadow destRestShadow(dest + copied, n - copied); + std::fill(destRestShadow.begin(), destRestShadow.end(), nullptr); + } + + return result; +} } diff --git a/runtime/test_wrappers/test_strcpy.c b/runtime/test_wrappers/test_strcpy.c new file mode 100644 index 00000000..53bffc13 --- /dev/null +++ b/runtime/test_wrappers/test_strcpy.c @@ -0,0 +1,31 @@ +#include +#include +#include +#include +#include +#include +int main(int argc, char *argv[]) { + + char buf[1024]; + ssize_t i; + if ((i = read(0, buf, sizeof(buf) - 1)) < 24) return 0; + buf[i] = 0; + if (buf[0] != 'A') return 0; + if (buf[1] != 'B') return 0; + if (buf[2] != 'C') return 0; + if (buf[3] != 'D') return 0; + if (memcmp(buf + 4, "1234", 4) || memcmp(buf + 8, "EFGH", 4)) return 0; + + char buf_2[4]; + strcpy(buf_2, buf+12); + if (memcmp(buf_2, "NICE", 4)){ + printf("NOT HIT!\n"); + return 0; + } else { + printf("HIT!\n"); + + } + + return 0; + +}