| | |
| | | #include <arpa/inet.h> |
| | | #include <regex> |
| | | #include <pthread.h> |
| | | #include <semaphore.h> |
| | | #include <string> |
| | | |
| | | #include "net.h" |
| | | #include "../jni_log.h" |
| | | |
| | | #define DEBUG(fmt, args...) LOGD("<net> <%s>: " fmt, __func__, ##args) |
| | | #define PARSE_BUFF_SIZE 4096 |
| | | |
| | | using namespace std; |
| | | |
| | | CTcpPort::CTcpPort() |
| | | { |
| | | m_iServiceType = TYPE_CLIENT; |
| | | m_sIp.clear(); |
| | | m_nPort = 0; |
| | | m_connected = false; |
| | | m_pClientSocket = 0; |
| | | m_pServerSocket = 0; |
| | | |
| | | event_func = NULL; |
| | | event_func_context = NULL; |
| | | receive_data_func = NULL; |
| | | receive_data_func_context = NULL; |
| | | } |
| | | |
| | | CTcpPort::~CTcpPort() |
| | | { |
| | | CloseTcpPort(); |
| | | } |
| | | |
| | | bool CTcpPort::IsOpen(void) |
| | | { |
| | | if (m_iServiceType == TYPE_SERVER) { |
| | | if (m_pServerSocket > 0) { |
| | | return true; |
| | | } else { |
| | | return false; |
| | | } |
| | | } else { |
| | | if (m_pClientSocket > 0) { |
| | | return true; |
| | | } else { |
| | | return false; |
| | | } |
| | | } |
| | | } |
| | | |
| | | bool CTcpPort::OpenTcpPort(const char *ip, int port) |
| | | { |
| | | if (IsOpen()) { |
| | | return true; |
| | | } |
| | | |
| | | m_sIp = ip; |
| | | m_nPort = port; |
| | | |
| | | pthread_t platform_pid; |
| | | pthread_attr_t attr; |
| | | pthread_attr_init(&attr); |
| | | pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);//detached |
| | | pthread_create(&platform_pid, &attr, TcpConnectThread, this); |
| | | |
| | | return true; |
| | | } |
| | | |
| | | /************************************************************* |
| | | host_name:domain name |
| | | net_addr:return numbers-and-dots notation |
| | | */ |
| | | int GetHostIP(const char *host_name, char *net_addr) |
| | | int CTcpPort::GetHostIP(const char *host_name, char *net_addr) |
| | | { |
| | | struct hostent *hptr; |
| | | char **pptr; |
| | |
| | | return -2; |
| | | } |
| | | |
| | | static bool is_domain_name(const char *ip) |
| | | bool CTcpPort::is_domain_name(const char *ip) |
| | | { |
| | | regex pattern0("^((2(5[0-5]|[0-4]\\d))|[0-1]?\\d{1,2})(\\.((2(5[0-5]|[0-4]\\d))|[0-1]?\\d{1,2})){3}$"); |
| | | string target(ip); |
| | |
| | | return !regex_match(target, pattern0); |
| | | } |
| | | |
| | | static int socket_set_keepalive(int fd) |
| | | int CTcpPort::socket_set_keepalive(int fd) |
| | | { |
| | | int alive, idle, cnt, intv; |
| | | |
| | |
| | | return 0; |
| | | } |
| | | |
| | | static int tcp_connect(char *ip, uint16_t port) |
| | | int CTcpPort::tcp_connect(char *ip, uint16_t port) |
| | | { |
| | | struct sockaddr_in server_sockaddr; |
| | | int soc; |
| | |
| | | return( -1 ); |
| | | } |
| | | |
| | | static int udp_connect(const char *ip, uint16_t port) { |
| | | struct sockaddr_in server_sockaddr; |
| | | int soc; |
| | | int opt; |
| | | int arg; |
| | | void *CTcpPort::TcpConnectThread(void *p) |
| | | { |
| | | CTcpPort *pCTcpPort = (CTcpPort *)p; |
| | | |
| | | if ((soc = socket(PF_INET, SOCK_DGRAM, 0)) == -1) { |
| | | return -1; |
| | | char net_addr[32] = {0}; |
| | | |
| | | if (pCTcpPort->is_domain_name(pCTcpPort->m_sIp.c_str())) { |
| | | if (pCTcpPort->GetHostIP(pCTcpPort->m_sIp.c_str(), net_addr) != 0) { |
| | | goto CONNECT_END; |
| | | } |
| | | } else { |
| | | strcpy(net_addr, pCTcpPort->m_sIp.c_str()); |
| | | } |
| | | |
| | | /*Enable send broadcast packet*/ |
| | | opt = 1; |
| | | if (setsockopt(soc, SOL_SOCKET, SO_BROADCAST, &opt, sizeof(opt)) != 0) { |
| | | perror("setsockopt"); |
| | | close(soc); |
| | | return -1; |
| | | pCTcpPort->m_pClientSocket = pCTcpPort->tcp_connect(net_addr, pCTcpPort->m_nPort); |
| | | |
| | | if (pCTcpPort->m_pClientSocket > 0) { |
| | | if (pCTcpPort->event_func != NULL) { |
| | | pCTcpPort->event_func(0, pCTcpPort, pCTcpPort->event_func_context); |
| | | } |
| | | |
| | | pthread_t platform_pid; |
| | | pthread_attr_t attr; |
| | | pthread_attr_init(&attr); |
| | | pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);//detached |
| | | pthread_create(&platform_pid, &attr, TcpListenThread, p); |
| | | } else { |
| | | if (pCTcpPort->event_func != NULL) { |
| | | pCTcpPort->event_func(-1, pCTcpPort, pCTcpPort->event_func_context); |
| | | } |
| | | } |
| | | |
| | | // Set non-blocking |
| | | if( (arg = fcntl(soc, F_GETFL, NULL)) < 0 ) { |
| | | close(soc); |
| | | return -1; |
| | | } |
| | | |
| | | if ( fcntl(soc, F_SETFL, arg | O_NONBLOCK) < 0 ) { |
| | | close(soc); |
| | | return -1; |
| | | } |
| | | |
| | | server_sockaddr.sin_family = AF_INET; |
| | | server_sockaddr.sin_addr.s_addr = inet_addr(ip);//htonl(INADDR_ANY); |
| | | server_sockaddr.sin_port = htons(port); |
| | | bzero(&server_sockaddr.sin_zero, 8); |
| | | |
| | | return soc; |
| | | CONNECT_END: |
| | | pthread_exit(NULL); |
| | | } |
| | | |
| | | int WriteTCP(int fd, const uint8_t * buf, uint32_t len) |
| | | void *CTcpPort::TcpListenThread(void *p) |
| | | { |
| | | int fds_ret; |
| | | struct timeval tv; |
| | | fd_set rdfds; |
| | | fd_set exfds; |
| | | uint8_t RxBuf[PARSE_BUFF_SIZE]; |
| | | |
| | | CTcpPort *pCTcpPort = (CTcpPort *)p; |
| | | |
| | | while (pCTcpPort->m_pClientSocket > 0) { |
| | | tv.tv_sec = 5; |
| | | tv.tv_usec = 0; |
| | | FD_ZERO(&rdfds); //clean |
| | | FD_SET(pCTcpPort->m_pClientSocket, &rdfds); //set |
| | | |
| | | fds_ret = select(pCTcpPort->m_pClientSocket + 1, &rdfds, NULL, NULL, &tv); |
| | | |
| | | if (fds_ret < 0) { |
| | | break; |
| | | } else if(fds_ret == 0) { |
| | | //Occur failure(such as line disconnect) |
| | | } else if(FD_ISSET(pCTcpPort->m_pClientSocket, &rdfds)) { |
| | | int recvLen = recv(pCTcpPort->m_pClientSocket, RxBuf, sizeof(RxBuf), 0); |
| | | |
| | | if (recvLen == 0) { |
| | | LOGW("tcp error TCP disconnected 0 errno = %d", errno); |
| | | break; |
| | | } else if (recvLen < 0) { |
| | | if (errno == EINTR || errno == EWOULDBLOCK || errno == EAGAIN) { |
| | | |
| | | } else { |
| | | LOGW("tcp error TCP disconnected errno = %d", errno);; |
| | | break; |
| | | } |
| | | } |
| | | |
| | | if (recvLen > 0) { |
| | | if (pCTcpPort->receive_data_func != NULL) { |
| | | pCTcpPort->receive_data_func(RxBuf, recvLen, pCTcpPort, pCTcpPort->receive_data_func_context); |
| | | } |
| | | } |
| | | } |
| | | } |
| | | |
| | | pCTcpPort->CloseTcpPort(); |
| | | |
| | | if (pCTcpPort->event_func) { |
| | | pCTcpPort->event_func(-1, pCTcpPort, pCTcpPort->event_func_context); |
| | | } |
| | | |
| | | pthread_exit(NULL); |
| | | } |
| | | |
| | | void CTcpPort::set_event_callback(void (*callback)(int, void *, void *), void *context) |
| | | { |
| | | event_func = callback; |
| | | event_func_context = context; |
| | | } |
| | | |
| | | void CTcpPort::set_data_callback(void (*callback)(void *, int, void *, void *), void *context) |
| | | { |
| | | receive_data_func = callback; |
| | | receive_data_func_context = context; |
| | | } |
| | | |
| | | int CTcpPort::WriteTCP(const uint8_t * buf, uint32_t len) |
| | | { |
| | | int ret = 0; |
| | | int fds_ret; |
| | | struct timeval tv; |
| | | fd_set rdfds; |
| | | |
| | | if (fd < 0) |
| | | if (m_pClientSocket <= 0) |
| | | return -2; |
| | | |
| | | /******************************************************* |
| | |
| | | tv.tv_usec = 0; |
| | | |
| | | FD_ZERO(&rdfds); //clean |
| | | FD_SET(fd, &rdfds); //set |
| | | FD_SET(m_pClientSocket, &rdfds); //set |
| | | |
| | | fds_ret = select(fd + 1, NULL, &rdfds, NULL, &tv); |
| | | fds_ret = select(m_pClientSocket + 1, NULL, &rdfds, NULL, &tv); |
| | | |
| | | if (fds_ret < 0) { |
| | | DEBUG("tcp error send select error"); |
| | |
| | | DEBUG("tcp error Occur failure(such as line disconnect)"); |
| | | //Occur failure(such as line disconnect) |
| | | ret = -1; |
| | | } else if(FD_ISSET(fd, &rdfds)) { |
| | | ret = send(fd, buf, len, 0); |
| | | } else if(FD_ISSET(m_pClientSocket, &rdfds)) { |
| | | ret = send(m_pClientSocket, buf, len, 0); |
| | | if(ret == -1) { |
| | | DEBUG("tcp error TCP Send Error"); |
| | | } |
| | |
| | | return ret; |
| | | } |
| | | |
| | | int ReadTCP(int fd, uint8_t * buf, uint32_t len) |
| | | bool CTcpPort::CloseTcpPort(void) |
| | | { |
| | | if (fd < 0) { |
| | | return -2; |
| | | DEBUG("DisconnectTCP fd = %d", m_pClientSocket); |
| | | |
| | | if (m_pClientSocket > 0) { |
| | | shutdown(m_pClientSocket, SHUT_RDWR); |
| | | close(m_pClientSocket); |
| | | m_pClientSocket = 0; |
| | | return true; |
| | | } |
| | | |
| | | int recvLen = recv(fd, buf, len, 0); //read socket data from server |
| | | |
| | | if (recvLen == 0) { |
| | | LOGW("tcp error TCP disconnected 0 errno = %d", errno); |
| | | return -1; |
| | | } else if (recvLen < 0) { |
| | | if (errno == EINTR || errno == EWOULDBLOCK || errno == EAGAIN) { |
| | | return 0; |
| | | } else { |
| | | LOGW("tcp error TCP disconnected errno = %d", errno);; |
| | | return -1; |
| | | } |
| | | } |
| | | |
| | | return recvLen; |
| | | } |
| | | |
| | | int ConnectTCP(const char *ip, uint16_t port) |
| | | { |
| | | char net_addr[32] = {0}; |
| | | |
| | | if (is_domain_name(ip)) { |
| | | if (GetHostIP(ip, net_addr) != 0) { |
| | | return -3; |
| | | } |
| | | } else { |
| | | strcpy(net_addr, ip); |
| | | } |
| | | |
| | | return tcp_connect(net_addr, port); |
| | | } |
| | | |
| | | void DisconnectTCP(int fd) |
| | | { |
| | | DEBUG("DisconnectTCP fd = %d", fd); |
| | | if (fd >= 0) { |
| | | shutdown(fd, SHUT_RDWR); |
| | | close(fd); |
| | | } |
| | | } |
| | | |
| | | int EstablishUDP(const char *ip, uint16_t port) |
| | | { |
| | | char net_addr[32] = {0}; |
| | | |
| | | if (is_domain_name(ip)) { |
| | | if (GetHostIP(ip, net_addr) != 0) { |
| | | return -3; |
| | | } |
| | | } else { |
| | | strcpy(net_addr, ip); |
| | | } |
| | | |
| | | return udp_connect(net_addr, port); |
| | | } |
| | | |
| | | void RemoveUDP(int fd) |
| | | { |
| | | close(fd); |
| | | } |
| | | |
| | | int WriteUDP(int fd, char *ip, uint16_t port, const uint8_t * buf, uint32_t len) |
| | | { |
| | | int ret = 0; |
| | | int fds_ret; |
| | | struct timeval tv; |
| | | fd_set rdfds; |
| | | |
| | | if (fd < 0) |
| | | return -2; |
| | | |
| | | /******************************************************* |
| | | TCP send with nonblock, if occur failure(such as line disconnect...), |
| | | will send timeout, so terminate TCP. |
| | | */ |
| | | tv.tv_sec = 5; |
| | | tv.tv_usec = 0; |
| | | |
| | | FD_ZERO(&rdfds); //clean |
| | | FD_SET(fd, &rdfds); //set |
| | | |
| | | fds_ret = select(fd + 1, NULL, &rdfds, NULL, &tv); |
| | | |
| | | if (fds_ret < 0) |
| | | { |
| | | DEBUG("UDP send select error"); |
| | | return -1; |
| | | } |
| | | else if(fds_ret == 0) |
| | | { |
| | | DEBUG("Occur failure(such as line disconnect)"); |
| | | ret = -1; |
| | | } |
| | | else if(FD_ISSET(fd, &rdfds)) |
| | | { |
| | | struct sockaddr_in server_sockaddr; |
| | | |
| | | server_sockaddr.sin_family = AF_INET; |
| | | server_sockaddr.sin_addr.s_addr = inet_addr(ip);//htonl(INADDR_ANY); |
| | | server_sockaddr.sin_port = htons(port); |
| | | bzero(&server_sockaddr.sin_zero, 8); |
| | | |
| | | ret = sendto(fd, buf, len, 0, (struct sockaddr *)&server_sockaddr, sizeof(struct sockaddr_in)); |
| | | |
| | | if(ret == -1) |
| | | { |
| | | DEBUG("UDP Send Error"); |
| | | } |
| | | } |
| | | else |
| | | { |
| | | DEBUG("UDP send has error\n"); |
| | | } |
| | | |
| | | return ret; |
| | | } |
| | | |
| | | int ReadUDP(int fd, uint8_t * buf, uint32_t len) |
| | | { |
| | | struct sockaddr_in from_addr; |
| | | socklen_t from_len; |
| | | |
| | | int recvLen = recvfrom(fd, buf, len, 0, |
| | | (struct sockaddr *) &from_addr, |
| | | &from_len);//read socket data from server// |
| | | |
| | | if (recvLen == 0) { |
| | | return 0; |
| | | } else if (recvLen < 0) { |
| | | if (errno == EINTR || errno == EWOULDBLOCK || errno == EAGAIN) { |
| | | return 0; |
| | | } else { |
| | | DEBUG("UDP ERROR!! = %d", errno); |
| | | return -1; |
| | | } |
| | | } |
| | | |
| | | return recvLen; |
| | | return false; |
| | | } |
| | |
| | | #ifndef RTKBASESTATION_NET_H |
| | | #define RTKBASESTATION_NET_H |
| | | |
| | | int WriteTCP(int fd, const uint8_t * buf, uint32_t len); |
| | | int ReadTCP(int fd, uint8_t * buf, uint32_t len); |
| | | int ConnectTCP(const char *ip, uint16_t port); |
| | | void DisconnectTCP(int fd); |
| | | int EstablishUDP(const char *ip, uint16_t port); |
| | | void RemoveUDP(int fd); |
| | | int WriteUDP(int fd, char *ip, uint16_t port, const uint8_t * buf, uint32_t len); |
| | | int ReadUDP(int fd, uint8_t * buf, uint32_t len); |
| | | #include <string> |
| | | |
| | | enum SERVICE_TYPE { |
| | | TYPE_SERVER, |
| | | TYPE_CLIENT |
| | | }; |
| | | |
| | | class CTcpPort |
| | | { |
| | | public: |
| | | SERVICE_TYPE m_iServiceType; |
| | | std::string m_sIp; |
| | | int m_nPort; |
| | | bool m_connected; |
| | | |
| | | int m_pServerSocket; |
| | | int m_pClientSocket; |
| | | |
| | | public: |
| | | CTcpPort(); |
| | | virtual ~CTcpPort(); |
| | | |
| | | bool IsOpen(void); |
| | | bool CloseTcpPort(); |
| | | bool OpenTcpPort(const char *ip, int port); |
| | | void set_event_callback(void (*callback)(int, void *, void *), void *context); |
| | | void set_data_callback(void (*callback)(void *, int, void *, void *), void *context); |
| | | int WriteTCP(const uint8_t * buf, uint32_t len); |
| | | private: |
| | | int GetHostIP(const char *host_name, char *net_addr); |
| | | bool is_domain_name(const char *ip); |
| | | int socket_set_keepalive(int fd); |
| | | int tcp_connect(char *ip, uint16_t port); |
| | | |
| | | void(*event_func)(int, void *, void *); //数据回调函数指针 |
| | | void *event_func_context; //数据回调函数上下文 |
| | | |
| | | void(*receive_data_func)(void *, int, void *, void *); //数据回调函数指针 |
| | | void *receive_data_func_context; //数据回调函数上下文 |
| | | |
| | | static void *TcpConnectThread(void *p); |
| | | static void *TcpListenThread(void *p); |
| | | }; |
| | | |
| | | //int WriteTCP(int fd, const uint8_t * buf, uint32_t len); |
| | | //int ReadTCP(int fd, uint8_t * buf, uint32_t len); |
| | | //int ConnectTCP(const char *ip, uint16_t port); |
| | | //void DisconnectTCP(int fd); |
| | | |
| | | #endif //RTKBASESTATION_NET_H |
| | |
| | | { |
| | | DEBUG("获取模拟路考灯光测试项目 N = %d %d", n, ExamStart); |
| | | |
| | | static const int cov[] = {0, |
| | | static const int CONV_TABLE[] = {(FLASH_BEAM_LAMP<<8)+OFF_LIGHT, |
| | | (TURN_SIGNAL_LAMP<<8)+OFF_LIGHT, |
| | | (TURN_SIGNAL_LAMP<<8)+OFF_LIGHT, |
| | | (TURN_SIGNAL_LAMP<<8)+OFF_LIGHT, |
| | | (FOG_LAMP<<8)+OFF_LIGHT, |
| | | (CLEARANCE_LAMP<<8)+OFF_LIGHT, |
| | | (MAIN_BEAM_LAMP<<8)+OFF_LIGHT, |
| | | (DIPPED_BEAM_LAMP<<8)+OFF_LIGHT, |
| | | 0, |
| | | (DIPPED_BEAM_LAMP<<8)+DIPPED_BEAM_LIGHT, |
| | | (MAIN_BEAM_LAMP<<8)+MAIN_BEAM_LIGHT, |
| | | (CLEARANCE_LAMP<<8)+CLEARANCE_LIGHT, |
| | |
| | | (TURN_SIGNAL_LAMP<<8)+RIGHT_TURN_LIGHT, |
| | | (TURN_SIGNAL_LAMP<<8)+HAZARD_LIGHTS, |
| | | (FLASH_BEAM_LAMP<<8)+FLASH_BEAM_LIGHT}; |
| | | |
| | | const int *cov = CONV_TABLE + 8; |
| | | |
| | | if (ExamStart) return; |
| | | |
| | |
| | | DummyLightContent[i].wrongCode = cfg[i].wrongCode; |
| | | // Sensor Name<<8 + Sensor Status |
| | | for (int j = 0; j < cfg[i].process.size(); ++j) { |
| | | DummyLightContent[i].process[j] = cov[cfg[i].process[j]]; |
| | | DummyLightContent[i].process.push_back(cov[cfg[i].process[j]]); |
| | | } |
| | | for (int j = 0; j < cfg[i].solution.size(); ++j) { |
| | | DummyLightContent[i].solution[j] = cov[cfg[i].solution[j]]; |
| | | DummyLightContent[i].solution.push_back(cov[cfg[i].solution[j]]); |
| | | } |
| | | } |
| | | } |
| | |
| | | "近光灯", |
| | | "雾灯", |
| | | "示廓灯", |
| | | "远近光", |
| | | "闪灯提示", |
| | | "远光灯", |
| | | "安全带", |
| | | "启动引擎", |
| | |
| | | Document doc; |
| | | doc.Parse(value); |
| | | if (!doc.HasParseError()) { |
| | | DEBUG("解析灯光配置..."); |
| | | if (doc.HasMember("exam")) { |
| | | const Value& s = doc["exam"]; |
| | | s.GetInt(); |
| | |
| | | int n = 0; |
| | | struct dummy_light_exam *content = new struct dummy_light_exam[s.Size()]; |
| | | |
| | | DEBUG("题目数量 %d", s.Size()); |
| | | |
| | | for(Value::ConstValueIterator itr = s.Begin(); itr != s.End(); ++itr) { |
| | | |
| | | if (itr->HasMember("item") && itr->HasMember("tts")) { |
| | | const Value &s1 = (*itr)["item"]; |
| | | const Value &s2 = (*itr)["tts"]; |
| | | |
| | | content[n].item = s1.GetInt(); |
| | | content[n].tts = s2.GetString(); |
| | | |
| | | DEBUG("题目 %s", s2.GetString()); |
| | | } |
| | | |
| | | if (itr->HasMember("wrong_code")) { |
| | | const Value &s = (*itr)["wrong_code"]; |
| | | |
| | | content[n].wrongCode = s.GetInt(); |
| | | |
| | | DEBUG("题目wrongCode %d", s.GetInt()); |
| | | } |
| | | |
| | | if (itr->HasMember("process")) { |
| | | const Value& s = doc["process"]; |
| | | const Value& s = (*itr)["process"]; |
| | | for(Value::ConstValueIterator itr2 = s.Begin(); itr2 != s.End(); ++itr2) { |
| | | DEBUG("题目process %d", itr2->GetInt()); |
| | | content[n].process.push_back(itr2->GetInt()); |
| | | } |
| | | } |
| | | if (itr->HasMember("solution")) { |
| | | const Value& s = doc["solution"]; |
| | | const Value& s = (*itr)["solution"]; |
| | | for(Value::ConstValueIterator itr2 = s.Begin(); itr2 != s.End(); ++itr2) { |
| | | DEBUG("题目solution %d", itr2->GetInt()); |
| | | content[n].solution.push_back(itr2->GetInt()); |
| | | } |
| | | } |
| | |
| | | |
| | | if (RxBufLen > 0) { |
| | | // DEBUG("RECV LEN %d", RxBufLen); |
| | | ParseMcu(RxBuf, RxBufLen); |
| | | if (Virtual2IsConnected()) { |
| | | |
| | | } else { |
| | | ParseMcu(RxBuf, RxBufLen); |
| | | } |
| | | RxBufLen = 0; |
| | | } |
| | | } |
| | |
| | | #include "../common/apptimer.h" |
| | | #include "../defs.h" |
| | | #include "parse_gps.h" |
| | | #include "../mcu/mcu_if.h" |
| | | |
| | | #define DEBUG(fmt, args...) LOGD("<virtual_device> <%s>: " fmt, __func__, ##args) |
| | | |
| | |
| | | int port; |
| | | } VAddr; |
| | | |
| | | static CTcpPort *ctp = NULL, *ctp2 = NULL; |
| | | static bool virtRtkIsValid = false; |
| | | static int connectCnt = 0; |
| | | static void TcpEventCallback(int stat, void *p, void *context); |
| | | static void TcpDataCallback(void *buffer, int length, void *p, void *context); |
| | | |
| | | static bool virtRtkIsValid2 = false; |
| | | static int connectCnt2 = 0; |
| | | static void TcpEventCallback2(int stat, void *p, void *context); |
| | | static void TcpDataCallback2(void *buffer, int length, void *p, void *context); |
| | | |
| | | static void ConnectLater(union sigval sig); |
| | | static void ConnectV(void); |
| | | static void *VDataListenThread(void *p); |
| | | |
| | | void InitVirtualDevice(const char *domain_name, int port) |
| | | { |
| | |
| | | strcpy(VAddr.domain_name, domain_name); |
| | | VAddr.port = port; |
| | | |
| | | ConnectV(); |
| | | if (ctp == NULL) { |
| | | ctp = new CTcpPort(); |
| | | |
| | | ctp->set_event_callback(TcpEventCallback, NULL); |
| | | ctp->set_data_callback(TcpDataCallback, NULL); |
| | | |
| | | ctp->OpenTcpPort(domain_name, port); |
| | | } |
| | | |
| | | if (ctp2 == NULL) { |
| | | ctp2 = new CTcpPort(); |
| | | |
| | | ctp2->set_event_callback(TcpEventCallback2, NULL); |
| | | ctp2->set_data_callback(TcpDataCallback2, NULL); |
| | | |
| | | ctp2->OpenTcpPort(domain_name, port + 1); |
| | | } |
| | | } |
| | | |
| | | bool VirtualIsConnected(void) |
| | |
| | | return temp; |
| | | } |
| | | |
| | | bool Virtual2IsConnected(void) |
| | | { |
| | | bool temp; |
| | | |
| | | do { |
| | | temp = virtRtkIsValid2; |
| | | } while (temp != virtRtkIsValid2); |
| | | |
| | | return temp; |
| | | } |
| | | |
| | | static void ConnectLater(union sigval sig) { |
| | | AppTimer_delete(ConnectLater); |
| | | |
| | | ConnectV(); |
| | | if (sig.sival_int == 1) { |
| | | if (ctp != NULL) { |
| | | ctp->OpenTcpPort(VAddr.domain_name, VAddr.port); |
| | | } |
| | | } else { |
| | | if (ctp2 != NULL) { |
| | | ctp2->OpenTcpPort(VAddr.domain_name, VAddr.port + 1); |
| | | } |
| | | } |
| | | } |
| | | |
| | | static void ConnectV(void) |
| | | static void TcpEventCallback(int stat, void *p, void *context) |
| | | { |
| | | pthread_t pid; |
| | | pthread_attr_t attr; |
| | | pthread_attr_init(&attr); |
| | | pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);//detached |
| | | pthread_create(&pid, &attr, VDataListenThread, &VAddr); |
| | | CTcpPort *pTcpPort = (CTcpPort *)p; |
| | | |
| | | if (stat == 0) { |
| | | DEBUG("虚拟平台连接成功 %s: %d", pTcpPort->m_sIp.c_str(), pTcpPort->m_nPort); |
| | | virtRtkIsValid = true; |
| | | connectCnt = 0; |
| | | PlayTTS("模拟器连接", NULL); |
| | | } else { |
| | | DEBUG("虚拟平台连接失败"); |
| | | virtRtkIsValid = false; |
| | | connectCnt++; |
| | | |
| | | if (connectCnt < 3) { |
| | | AppTimer_add(ConnectLater, D_SEC(3), 1); |
| | | } |
| | | PlayTTS("模拟器断开", NULL); |
| | | } |
| | | } |
| | | |
| | | static void TcpDataCallback(void *buffer, int length, void *p, void *context) |
| | | { |
| | | static uint8_t RxBuf[PARSE_BUFF_SIZE]; |
| | | static int RxBufLen = 0; |
| | | |
| | | if (length > 0) { |
| | | memcpy(RxBuf + RxBufLen, buffer, length); |
| | | RxBufLen += length; |
| | | |
| | | const uint8_t *ptr = parseGPS(RxBuf, RxBuf + RxBufLen); |
| | | |
| | | if(ptr != RxBuf) { |
| | | memcpy(RxBuf, ptr, RxBufLen - (ptr - RxBuf)); |
| | | RxBufLen -= ptr - RxBuf; |
| | | } else if(RxBufLen == PARSE_BUFF_SIZE) { //填满了,且没有一个\r,都抛弃 |
| | | DEBUG("Parse GPS error"); |
| | | RxBufLen = 0; |
| | | } |
| | | } |
| | | } |
| | | |
| | | static void TcpEventCallback2(int stat, void *p, void *context) |
| | | { |
| | | CTcpPort *pTcpPort = (CTcpPort *)p; |
| | | |
| | | if (stat == 0) { |
| | | DEBUG("灯光虚拟平台连接成功 %s: %d", pTcpPort->m_sIp.c_str(), pTcpPort->m_nPort); |
| | | virtRtkIsValid2 = true; |
| | | connectCnt2 = 0; |
| | | PlayTTS("灯光模拟器连接", NULL); |
| | | } else { |
| | | DEBUG("灯光虚拟平台连接失败"); |
| | | virtRtkIsValid2 = false; |
| | | connectCnt2++; |
| | | |
| | | if (connectCnt2 < 3) { |
| | | AppTimer_add(ConnectLater, D_SEC(3), 2); |
| | | } |
| | | PlayTTS("灯光模拟器断开", NULL); |
| | | } |
| | | } |
| | | |
| | | static void TcpDataCallback2(void *buffer, int length, void *p, void *context) |
| | | { |
| | | static uint8_t RxBuf[PARSE_BUFF_SIZE]; |
| | | static int RxBufLen = 0; |
| | | |
| | | if (length > 0) { |
| | | memcpy(RxBuf + RxBufLen, buffer, length); |
| | | RxBufLen += length; |
| | | |
| | | if (RxBufLen > 0) { |
| | | ParseMcu(RxBuf, RxBufLen); |
| | | RxBufLen = 0; |
| | | } |
| | | } |
| | | } |
| | | |
| | | /* |
| | | static void *VDataListenThread(void *p) { |
| | | struct vSocket *vs = (struct vSocket *)p; |
| | | |
| | |
| | | |
| | | pthread_exit(NULL); |
| | | } |
| | | */ |
| | |
| | | |
| | | void InitVirtualDevice(const char *domain_name, int port); |
| | | bool VirtualIsConnected(void); |
| | | bool Virtual2IsConnected(void); |
| | | |
| | | #endif //MYAPPLICATION2_VIRTUAL_RTK_H |
| | |
| | | |
| | | #define DEBUG(fmt, args...) LOGD("<parse_net> <%s>: " fmt, __func__, ##args) |
| | | |
| | | #define ENABLE_DEBUG_PROTOCOL |
| | | #define xENABLE_DEBUG_PROTOCOL |
| | | |
| | | using namespace std; |
| | | |
| | |
| | | #include "../test_items2/stop_car.h" |
| | | #include "../test_items2/operate_gear.h" |
| | | #include "../test_items2/drive_straight.h" |
| | | #include "../rtk_module/virtual_rtk.h" |
| | | |
| | | #define PARSE_BUFF_SIZE 4096 |
| | | |
| | |
| | | |
| | | static bool mAyDevice = false; |
| | | |
| | | struct platformSocket exceptSocket, currSocket; |
| | | struct platformSocket exceptSocket; |
| | | static sem_t sem_status_changed; |
| | | |
| | | static bool requestPlatformSendRtk = false; |
| | | static int platform_tcp_fd = 0; |
| | | static CTcpPort *ctp = NULL; |
| | | |
| | | static pthread_mutex_t platform_tx_mutex = PTHREAD_MUTEX_INITIALIZER; |
| | | static pthread_mutex_t events_mutex = PTHREAD_MUTEX_INITIALIZER; |
| | | |
| | | static struct gpsBrief gbf; |
| | |
| | | |
| | | static void ReqRtkPlatformConfigTimeout(union sigval sig); |
| | | |
| | | static void TcpEventCallback(int stat, void *p, void *context); |
| | | static void TcpDataCallback(void *buffer, int length, void *p, void *context); |
| | | |
| | | static void ConnectPlatform(const char *domain_name, int port); |
| | | static void ConnectPlatformLater(union sigval sig); |
| | | |
| | | static void *PlatformDataListenThread(void *p); |
| | | static void *StatusListenThread(void *p); |
| | | static void PlatformChangeEntry(uint32_t events, const uint8_t *data, int length); |
| | | |
| | |
| | | memset(&rbf, 0, sizeof(rbf)); |
| | | memset(&defaultMcuRom, 0, sizeof(defaultMcuRom)); |
| | | |
| | | pthread_mutex_init(&platform_tx_mutex, NULL); |
| | | pthread_mutex_init(&events_mutex, NULL); |
| | | |
| | | eventQueue = NULL; |
| | | |
| | | platform_tcp_fd = -1; |
| | | |
| | | memset(&currSocket, 0, sizeof(currSocket)); |
| | | memset(&platformStatus, 0, sizeof(platformStatus)); |
| | | |
| | | sem_init(&sem_status_changed, 0, 0); |
| | |
| | | platformStatus.registed = 0; |
| | | } |
| | | |
| | | pthread_mutex_lock(&platform_tx_mutex); |
| | | if (platform_tcp_fd > 0 && (exceptSocket.port != currSocket.port || strcmp(currSocket.domain_name, exceptSocket.domain_name))) { |
| | | DisconnectTCP(platform_tcp_fd); |
| | | platform_tcp_fd = -1; |
| | | } else if (platform_tcp_fd <= 0) { |
| | | ConnectPlatform(exceptSocket.domain_name, exceptSocket.port); |
| | | } |
| | | pthread_mutex_unlock(&platform_tx_mutex); |
| | | ConnectPlatform(exceptSocket.domain_name, exceptSocket.port); |
| | | |
| | | // pthread_mutex_lock(&platform_tx_mutex); |
| | | // if (platform_tcp_fd > 0 && (exceptSocket.port != currSocket.port || strcmp(currSocket.domain_name, exceptSocket.domain_name))) { |
| | | // DisconnectTCP(platform_tcp_fd); |
| | | // platform_tcp_fd = -1; |
| | | // } else if (platform_tcp_fd <= 0) { |
| | | // ConnectPlatform(exceptSocket.domain_name, exceptSocket.port); |
| | | // } |
| | | // pthread_mutex_unlock(&platform_tx_mutex); |
| | | } |
| | | |
| | | void PlatformStatusChanged(uint32_t event, const uint8_t *data, int length) |
| | |
| | | return; |
| | | |
| | | DEBUG("连接RTK平台 %s: %d", domain_name, port); |
| | | // TODO |
| | | struct platformSocketInfo *ptr = (struct platformSocketInfo *)malloc(sizeof(struct platformSocketInfo)); |
| | | |
| | | strcpy(ptr->domain_name, domain_name); |
| | | ptr->port = port; |
| | | if (ctp == NULL) { |
| | | ctp = new CTcpPort(); |
| | | |
| | | pthread_t platform_pid; |
| | | pthread_attr_t attr; |
| | | pthread_attr_init(&attr); |
| | | pthread_attr_setdetachstate(&attr, PTHREAD_CREATE_DETACHED);//detached |
| | | pthread_create(&platform_pid, &attr, PlatformDataListenThread, ptr); |
| | | ctp->set_event_callback(TcpEventCallback, NULL); |
| | | ctp->set_data_callback(TcpDataCallback, NULL); |
| | | } |
| | | |
| | | if (!ctp->IsOpen()) { |
| | | ctp->OpenTcpPort(domain_name, port); |
| | | } else if ((ctp->m_nPort != port || strcmp(ctp->m_sIp.c_str(), domain_name))) { |
| | | ctp->CloseTcpPort(); |
| | | } |
| | | } |
| | | |
| | | static void TcpEventCallback(int stat, void *p, void *context) |
| | | { |
| | | CTcpPort *pTcpPort = (CTcpPort *)p; |
| | | uint8_t buffer[256]; |
| | | |
| | | strcpy((char *)buffer, pTcpPort->m_sIp.c_str()); |
| | | |
| | | buffer[pTcpPort->m_sIp.length() + 1] = HI_UINT16(pTcpPort->m_nPort); |
| | | buffer[pTcpPort->m_sIp.length() + 2] = LO_UINT16(pTcpPort->m_nPort); |
| | | |
| | | if (stat == 0) { |
| | | PlatformStatusChanged(PLATFORM_CONNECT_EVT, buffer, pTcpPort->m_sIp.length() + 3); |
| | | } else { |
| | | PlatformStatusChanged(PLATFORM_DISCONNECT_EVT, buffer, pTcpPort->m_sIp.length() + 3); |
| | | } |
| | | } |
| | | |
| | | static void TcpDataCallback(void *buffer, int length, void *p, void *context) |
| | | { |
| | | if (length > 0) { |
| | | Parse(DATA_ACCESS_PLATFORM, (uint8_t *)buffer, length); |
| | | } |
| | | } |
| | | |
| | | static void ConnectPlatformLater(union sigval sig) { |
| | |
| | | { |
| | | switch (events) { |
| | | case PLATFORM_CONNECT_EVT: { |
| | | DEBUG("平台连接成功 %s:%d", currSocket.domain_name, currSocket.port); |
| | | MA_RtkPlatformConnect(1, currSocket.domain_name, currSocket.port); |
| | | DEBUG("平台连接成功 %s:%d", data, BUILD_UINT16(data[strlen((char *)data) + 2], data[strlen((char *)data) + 1])); |
| | | MA_RtkPlatformConnect(1, (char *)data, BUILD_UINT16(data[strlen((char *)data) + 2], data[strlen((char *)data) + 1])); |
| | | |
| | | platformStatus.connected = 1; |
| | | if (!platformStatus.registed || platformStatus.platformKeyLength == 0) { |
| | |
| | | } |
| | | |
| | | case PLATFORM_DISCONNECT_EVT: { |
| | | DEBUG("平台断开 %s:%d", currSocket.domain_name, currSocket.port); |
| | | MA_RtkPlatformConnect(0, currSocket.domain_name, currSocket.port); |
| | | DEBUG("平台断开 %s:%d", data, BUILD_UINT16(data[strlen((char *)data) + 2], data[strlen((char *)data) + 1])); |
| | | MA_RtkPlatformConnect(0, (char *)data, BUILD_UINT16(data[strlen((char *)data) + 2], data[strlen((char *)data) + 1])); |
| | | |
| | | AppTimer_delete(ConnectPlatformLater); |
| | | AppTimer_add(ConnectPlatformLater, D_SEC(2)); |
| | |
| | | break; |
| | | } |
| | | case BLUETOOTH_DATA_EVT: { |
| | | ParseMcu(data, length); |
| | | if (Virtual2IsConnected()) { |
| | | |
| | | } else { |
| | | ParseMcu(data, length); |
| | | } |
| | | break; |
| | | } |
| | | case SENSOR_CHANGE_EVT: { |
| | |
| | | } |
| | | } |
| | | |
| | | static void *PlatformDataListenThread(void *p) { |
| | | struct platformSocket *ptr = (struct platformSocket *)p; |
| | | |
| | | uint8_t RxBuf[PARSE_BUFF_SIZE]; |
| | | |
| | | int fds_ret; |
| | | struct timeval tv; |
| | | fd_set rdfds; |
| | | fd_set exfds; |
| | | |
| | | int fd = -1; |
| | | int RxBufLen = 0; |
| | | |
| | | fd = ConnectTCP(ptr->domain_name, ptr->port); |
| | | |
| | | pthread_mutex_lock(&platform_tx_mutex); |
| | | platform_tcp_fd = fd; |
| | | |
| | | currSocket = *ptr; |
| | | |
| | | pthread_mutex_unlock(&platform_tx_mutex); |
| | | |
| | | if (fd > 0) { |
| | | PlatformStatusChanged(PLATFORM_CONNECT_EVT, NULL, 0); |
| | | } |
| | | |
| | | while (fd > 0) { |
| | | tv.tv_sec = 5; |
| | | tv.tv_usec = 0; |
| | | FD_ZERO(&rdfds); //clean |
| | | FD_SET(fd, &rdfds); //set |
| | | |
| | | fds_ret = select(fd + 1, &rdfds, NULL, NULL, &tv); |
| | | |
| | | if (fds_ret < 0) { |
| | | break; |
| | | } else if(fds_ret == 0) { |
| | | //Occur failure(such as line disconnect) |
| | | } else if(FD_ISSET(fd, &rdfds)) { |
| | | RxBufLen = ReadTCP(fd, RxBuf, sizeof(RxBuf)); |
| | | |
| | | if (RxBufLen < 0) { |
| | | break; |
| | | } else if (RxBufLen > 0) { |
| | | Parse(DATA_ACCESS_PLATFORM, RxBuf, RxBufLen); |
| | | } |
| | | } |
| | | } |
| | | |
| | | pthread_mutex_lock(&platform_tx_mutex); |
| | | if (platform_tcp_fd > 0) { |
| | | DisconnectTCP(platform_tcp_fd); |
| | | platform_tcp_fd = -1; |
| | | } |
| | | pthread_mutex_unlock(&platform_tx_mutex); |
| | | free(ptr); |
| | | |
| | | PlatformStatusChanged(PLATFORM_DISCONNECT_EVT, NULL, 0); |
| | | pthread_exit(NULL); |
| | | } |
| | | |
| | | int WritePlatform(const uint8_t * buf, uint32_t len) |
| | | { |
| | | int ret = -1; |
| | | |
| | | pthread_mutex_lock(&platform_tx_mutex); |
| | | if (platform_tcp_fd > 0) { |
| | | ret = WriteTCP(platform_tcp_fd, buf, len); |
| | | if (ctp != NULL && ctp->IsOpen()) { |
| | | ret = ctp->WriteTCP(buf, len); |
| | | } |
| | | pthread_mutex_unlock(&platform_tx_mutex); |
| | | |
| | | return ret; |
| | | } |
| | |
| | | |
| | | static uint16_t gpioStore; |
| | | static int left_turn_signal, right_turn_signal; |
| | | static int flashMainBeamCnt; |
| | | |
| | | enum { |
| | | SENSOR_SEATBELT, |
| | |
| | | static void ChangeLRLight(int light); |
| | | static void ConfirmTurnSigalLater(union sigval sig); |
| | | static void flashBeamLightClose(union sigval sig); |
| | | static void confirmFlashBeamLightLater(union sigval sig); |
| | | |
| | | static void SensorChanged(int id, int value); |
| | | |
| | | void CarSensorInit(void) |
| | |
| | | memset(&Sensor, 0, sizeof(Sensor)); |
| | | |
| | | left_turn_signal = right_turn_signal = 0; |
| | | flashMainBeamCnt = 0; |
| | | |
| | | pthread_mutex_init(&sonser_mutex, NULL); |
| | | pthread_mutex_init(&status_rw_mutex, NULL); |
| | |
| | | WriteCarStatus(FLASH_BEAM_LAMP, OFF_LIGHT); |
| | | } |
| | | |
| | | static void confirmFlashBeamLightLater(union sigval sig) |
| | | { |
| | | AppTimer_delete(confirmFlashBeamLightLater); |
| | | flashMainBeamCnt = 0; |
| | | } |
| | | |
| | | static void SensorChanged(int id, int value) |
| | | { |
| | | // DEBUG("状态改变 %d = %d", id, value); |
| | | DEBUG("状态改变 %d = %d", id, value); |
| | | switch (id) { |
| | | case SENSOR_LEFT_TURN_SIGNAL: { |
| | | left_turn_signal = value; |
| | |
| | | break; |
| | | } |
| | | case SENSOR_MAIN_BEAM_LIGHT: { |
| | | static uint32_t t1 = 0; |
| | | |
| | | if (value == 0) { |
| | | WriteCarStatus(MAIN_BEAM_LAMP, OFF_LIGHT); |
| | | } else { |
| | | WriteCarStatus(MAIN_BEAM_LAMP, MAIN_BEAM_LIGHT); |
| | | } |
| | | |
| | | if (++flashMainBeamCnt > 3) { // 亮-灭-亮-灭 |
| | | WriteCarStatus(FLASH_BEAM_LAMP, FLASH_BEAM_LIGHT); |
| | | |
| | | if (value != 0) { |
| | | t1 = AppTimer_GetTickCount(); |
| | | } else if (AppTimer_GetTickCount() - t1 < D_SEC(3)) { |
| | | // 3秒内完成亮灭,闪灯 |
| | | if (ReadCarStatus(FLASH_BEAM_LAMP) != FLASH_BEAM_LIGHT) { |
| | | WriteCarStatus(FLASH_BEAM_LAMP, FLASH_BEAM_LIGHT); |
| | | } |
| | | AppTimer_delete(flashBeamLightClose); |
| | | AppTimer_add(flashBeamLightClose, D_SEC(2)); |
| | | } |
| | | |
| | | AppTimer_delete(confirmFlashBeamLightLater); |
| | | AppTimer_add(confirmFlashBeamLightLater, D_SEC(3)); |
| | | break; |
| | | } |
| | | case SENSOR_SEATBELT: { |
| | |
| | | AppTimer_delete(CheckSolution); |
| | | } |
| | | |
| | | // 记录中间过程 |
| | | void handleLigthExam(uint16_t id, int value) |
| | | { |
| | | if (testing) { |
| | |
| | | } |
| | | } |
| | | |
| | | // 检查最终状态 |
| | | static void CheckSolution(union sigval sig) |
| | | { |
| | | int question = sig.sival_int; |
| | | |
| | | AppTimer_delete(CheckSolution); |
| | | |
| | | if (content[question].process.size() > 0) { |
| | |
| | | } |
| | | |
| | | for (int i = 0; i < content[question].solution.size(); ++i) { |
| | | if (ReadCarStatus((content[question].solution[i]>>8)&0xFF) != content[question].solution[i] & 0xFF) { |
| | | if (ReadCarStatus((content[question].solution[i]>>8)&0xFF) != (content[question].solution[i] & 0xFF)) { |
| | | AddExamFault(content[question].wrongCode, &currRtkTime); |
| | | break; |
| | | } |
| | |
| | | static void ExamDummyLight(void) |
| | | { |
| | | if (testing && question < contentNum) { |
| | | DEBUG("灯光题目: %s", content[question].tts.c_str()); |
| | | PlayTTS(content[question].tts, DummyLightTTSDone); |
| | | } else { |
| | | testing = false; |