#include "LinuxApiMock.h" #include "Log.h" #include "linux_api.h" #include #include const char *OPEN_GPIO_7 = "/sys/class/gpio/gpio7/direction"; const char *OPEN_GPIO_6 = "/sys/class/gpio/gpio6/direction"; const char *OPEN_GPIO_66 = "/sys/class/gpio/gpio66/direction"; const char *OPEN_GPIO_69 = "/sys/class/gpio/gpio69/direction"; const char *OPEN_GPIO_pir = "/sys/class/gpio/gpio3/direction"; #ifdef __cplusplus extern "C" { #endif FILE *__wrap_fopen(const char *pathname, const char *mode) { std::string path = pathname; FILE *result = nullptr; if (path.find("gpio7/") != std::string::npos) { result = LinuxApiMock::GetInstance()->fopen(OPEN_GPIO_7, mode); } if (path.find("gpio6/") != std::string::npos) { result = LinuxApiMock::GetInstance()->fopen(OPEN_GPIO_6, mode); } if (path.find("gpio66/") != std::string::npos) { result = LinuxApiMock::GetInstance()->fopen(OPEN_GPIO_66, mode); } if (path.find("gpio69/") != std::string::npos) { result = LinuxApiMock::GetInstance()->fopen(OPEN_GPIO_69, mode); } if (path.find("gpio3/") != std::string::npos) { result = LinuxApiMock::GetInstance()->fopen(OPEN_GPIO_pir, mode); } if (!result) { result = LinuxApiMock::GetInstance()->fopen(pathname, mode); } if (!result) { result = __real_fopen(pathname, mode); } return result; } int __wrap_linux_fclose(FILE *stream) { return LinuxApiMock::GetInstance()->fclose(stream); } int __wrap_fprintf_gpio(FILE *stream, const U32 pinNum) { return LinuxApiMock::GetInstance()->fprintf_gpio(stream, pinNum); } int __wrap_fprintf_dir(FILE *stream, const char *dir) { return LinuxApiMock::GetInstance()->fprintf_dir(stream, dir); } size_t __wrap_linux_fread(void *ptr, size_t size, size_t nmemb, FILE *stream) { std::string buf; size_t readLength = LinuxApiMock::GetInstance()->fread(buf, size, nmemb, stream); memcpy(ptr, buf.c_str(), buf.length()); return readLength; } int __wrap_linux_open(const char *pathname, int flags) { int fd = LinuxApiMock::GetInstance()->open(pathname, flags); if (fd == DONOT_USE_MOCK_OPEN) { return __real_linux_open(pathname, flags); } return fd; } ssize_t __wrap_linux_write(int fd, const void *buf, size_t count) { int length = LinuxApiMock::GetInstance()->write(fd, buf, count); if (length == MOCK_WRITE_FAILED) { return __real_linux_write(fd, buf, count); } return length; } ssize_t __wrap_linux_read(int fd, void *buf, size_t count) { while (LinuxApiMock::GetInstance()->read_block(fd)) { std::this_thread::sleep_for(std::chrono::milliseconds(10)); } int length = LinuxApiMock::GetInstance()->read(fd, buf, count); if (length == MOCK_READ_NOTHING) { return __real_linux_read(fd, buf, count); } return length; } int __wrap_linux_close(int fd) { int result = LinuxApiMock::GetInstance()->close(fd); if (result == DONOT_USE_MOCK_OPEN) { return __real_linux_close(fd); } return result; } int __wrap_linux_fcntl(int fd, int cmd, int flag) { return FCNTL_SUCCEED; } int __wrap_tcgetattr(int fd, struct termios *termios_p) { return tcgetattr_SUCCEED; } int __wrap_tcsetattr(int fd, int optional_actions, const struct termios *termios_p) { return tcgetattr_SUCCEED; } int __wrap_select(int nfds, fd_set *readfds, fd_set *writefds, fd_set *exceptfds, struct timeval *timeout) { int result = LinuxApiMock::GetInstance()->select(nfds, readfds, writefds, exceptfds, timeout); if (result == MOCK_SELECT_FAILED) { std::this_thread::sleep_for(std::chrono::milliseconds((timeout->tv_sec) * 1000 + (timeout->tv_sec) / 1000)); return MOCK_SELECT_NOT_READABLE; } if (result == MOCK_SELECT_CALL_REAL_SELECT) { return __real_select(nfds, readfds, writefds, exceptfds, timeout); } return result; } const struct hostent *DONOT_USE_MOCK_GETHOSTBYNAME = nullptr; struct hostent *__wrap_gethostbyname(const char *name) { struct hostent *resutl = LinuxApiMock::GetInstance()->gethostbyname(name); if (DONOT_USE_MOCK_GETHOSTBYNAME == resutl) { return __real_gethostbyname(name); } return resutl; } int __wrap_connect(int sockfd, const struct sockaddr *addr, socklen_t addrlen) { int result = LinuxApiMock::GetInstance()->connect(sockfd, addr, addrlen); if (DONOT_USE_MOCK_CONNECT == result) { return __real_connect(sockfd, addr, addrlen); } return result; } int __wrap_socket(int domain, int type, int protocol) { int result = LinuxApiMock::GetInstance()->socket(domain, type, protocol); if (DONOT_USE_MOCK_SOCKET == result) { return __real_socket(domain, type, protocol); } return result; } #ifdef __cplusplus } #endif FILE *LinuxApiMock::fopen(const char *pathname, const char *mode) { return __real_fopen(pathname, mode); } int LinuxApiMock::fclose(FILE *stream) { return __real_linux_fclose(stream); } int LinuxApiMock::fprintf_gpio(FILE *stream, const U32 pinNum) { return __real_fprintf_gpio(stream, pinNum); } int LinuxApiMock::fprintf_dir(FILE *stream, const char *dir) { return __real_fprintf_dir(stream, dir); } size_t LinuxApiMock::fread(std::string &buf, size_t size, size_t nmemb, FILE *stream) { // return __real_fread(ptr, size, nmemb, stream); return 0; } int LinuxApiMock::open(const char *pathname, int flags) { return __real_linux_open(pathname, flags); } int LinuxApiMock::close(int fd) { return __real_linux_close(fd); } ssize_t LinuxApiMock::write(int fd, const void *buf, size_t count) { return __real_linux_write(fd, buf, count); } ssize_t LinuxApiMock::read(int fd, void *buf, size_t count) { return __real_linux_read(fd, buf, count); } int LinuxApiMock::select(int nfds, fd_set *readfds, fd_set *writefds, fd_set *exceptfds, struct timeval *timeout) { return __real_select(nfds, readfds, writefds, exceptfds, timeout); } struct hostent *LinuxApiMock::gethostbyname(const char *name) { return __real_gethostbyname(name); } int LinuxApiMock::connect(int sockfd, const struct sockaddr *addr, socklen_t addrlen) { return __real_connect(sockfd, addr, addrlen); } int LinuxApiMock::socket(int domain, int type, int protocol) { return __real_socket(domain, type, protocol); }