static UA_Int64 sendReadRequest(ConnectionInfo *connectionInfo, UA_Int32 nodeIds_size,UA_NodeId* nodeIds){ /*UA_Int32 sock, UA_UInt32 channelId, UA_UInt32 tokenId, UA_UInt32 sequenceNumber, UA_UInt32 requestId, UA_NodeId authenticationToken, UA_Int32 nodeIds_size,UA_NodeId* nodeIds) { */ UA_ByteString *message = UA_ByteString_new(); UA_ByteString_newMembers(message, 65536); UA_UInt32 tmpChannelId = connectionInfo->channelId; size_t offset = 0; UA_TcpMessageHeader msghdr; msghdr.messageTypeAndFinal = UA_MESSAGETYPEANDFINAL_MSGF; UA_NodeId type; type.identifier.numeric = 631; type.identifierType = UA_NODEIDTYPE_NUMERIC; type.namespaceIndex = 0; UA_ReadRequest rq; UA_ReadRequest_init(&rq); rq.maxAge = 0; rq.nodesToRead = UA_Array_new(&UA_TYPES[UA_TYPES_READVALUEID], nodeIds_size); rq.nodesToReadSize = 1; for(UA_Int32 i=0;i<nodeIds_size;i++) { UA_ReadValueId_init(&(rq.nodesToRead[i])); rq.nodesToRead[i].attributeId = 6; //WriteMask UA_NodeId_init(&(rq.nodesToRead[i].nodeId)); rq.nodesToRead[i].nodeId = nodeIds[i]; UA_QualifiedName_init(&(rq.nodesToRead[0].dataEncoding)); } rq.requestHeader.timeoutHint = 10000; rq.requestHeader.timestamp = UA_DateTime_now(); rq.requestHeader.authenticationToken = connectionInfo->authenticationToken; rq.timestampsToReturn = 0x03; rq.requestHeader.requestHandle = 1 + connectionInfo->sequenceHdr.requestId; msghdr.messageSize = 16 + UA_TcpMessageHeader_calcSizeBinary(&msghdr) + UA_NodeId_calcSizeBinary(&type) + UA_ReadRequest_calcSizeBinary(&rq); UA_TcpMessageHeader_encodeBinary(&msghdr,message,&offset); UA_UInt32_encodeBinary(&tmpChannelId, message, &offset); UA_UInt32_encodeBinary(&connectionInfo->tokenId, message, &offset); UA_UInt32_encodeBinary(&connectionInfo->sequenceHdr.sequenceNumber, message, &offset); UA_UInt32_encodeBinary(&connectionInfo->sequenceHdr.requestId, message, &offset); UA_NodeId_encodeBinary(&type,message,&offset); UA_ReadRequest_encodeBinary(&rq, message, &offset); UA_DateTime tic = UA_DateTime_now(); UA_Int32 sendret = send(connectionInfo->socket, message->data, offset, 0); UA_Array_delete(rq.nodesToRead, &UA_TYPES[UA_TYPES_READVALUEID], nodeIds_size); UA_ByteString_delete(message); if (sendret < 0) { printf("send readrequest failed"); return 1; } return tic; }
static UA_Int32 sendActivateSession(UA_Int32 sock, UA_UInt32 channelId, UA_UInt32 tokenId, UA_UInt32 sequenceNumber, UA_UInt32 requestId, UA_NodeId authenticationToken) { UA_ByteString *message = UA_ByteString_new(); UA_ByteString_newMembers(message, 65536); UA_UInt32 tmpChannelId = channelId; size_t offset = 0; UA_TcpMessageHeader msghdr; msghdr.messageTypeAndFinal = UA_MESSAGETYPEANDFINAL_MSGF; msghdr.messageSize = 86; UA_NodeId type; type.identifier.numeric = 467; type.identifierType = UA_NODEIDTYPE_NUMERIC; type.namespaceIndex = 0; UA_ActivateSessionRequest rq; UA_ActivateSessionRequest_init(&rq); rq.requestHeader.requestHandle = 2; rq.requestHeader.authenticationToken = authenticationToken; rq.requestHeader.timestamp = UA_DateTime_now(); rq.requestHeader.timeoutHint = 10000; msghdr.messageSize = 16 + UA_TcpMessageHeader_calcSizeBinary(&msghdr) + UA_NodeId_calcSizeBinary(&type) + UA_ActivateSessionRequest_calcSizeBinary(&rq); UA_TcpMessageHeader_encodeBinary(&msghdr, message, &offset); UA_UInt32_encodeBinary(&tmpChannelId, message, &offset); UA_UInt32_encodeBinary(&tokenId, message, &offset); UA_UInt32_encodeBinary(&sequenceNumber, message, &offset); UA_UInt32_encodeBinary(&requestId, message, &offset); UA_NodeId_encodeBinary(&type, message, &offset); UA_ActivateSessionRequest_encodeBinary(&rq, message, &offset); UA_Int32 sendret = send(sock, message->data, offset, 0); UA_ByteString_delete(message); if (sendret < 0) { printf("send opensecurechannel failed"); return 1; } return 0; }
/* we have no networklayer. instead, attach the reusable buffer to the handle */ UA_Connection ClientNetworkLayerTCP_connect(UA_ConnectionConfig localConf, char *endpointUrl, UA_Logger *logger) { UA_Connection connection; UA_Connection_init(&connection); connection.localConf = localConf; #ifndef UA_MULTITHREADING connection.handle = UA_ByteString_new(); UA_ByteString_newMembers(connection.handle, localConf.maxMessageSize); #endif size_t urlLength = strlen(endpointUrl); if(urlLength < 11 || urlLength >= 512) { UA_LOG_WARNING((*logger), UA_LOGCATEGORY_COMMUNICATION, "Server url size invalid"); return connection; } if(strncmp(endpointUrl, "opc.tcp://", 10) != 0) { UA_LOG_WARNING((*logger), UA_LOGCATEGORY_COMMUNICATION, "Server url does not begin with opc.tcp://"); return connection; } UA_UInt16 portpos = 9; UA_UInt16 port = 0; for(;portpos < urlLength-1; portpos++) { if(endpointUrl[portpos] == ':') { port = atoi(&endpointUrl[portpos+1]); break; } } if(port == 0) { UA_LOG_WARNING((*logger), UA_LOGCATEGORY_COMMUNICATION, "Port invalid"); return connection; } char hostname[512]; for(int i=10; i < portpos; i++) hostname[i-10] = endpointUrl[i]; hostname[portpos-10] = 0; #ifdef _WIN32 WORD wVersionRequested; WSADATA wsaData; wVersionRequested = MAKEWORD(2, 2); WSAStartup(wVersionRequested, &wsaData); if((connection.sockfd = socket(PF_INET, SOCK_STREAM,0)) == (UA_Int32)INVALID_SOCKET) { #else if((connection.sockfd = socket(AF_INET, SOCK_STREAM, 0)) == -1) { #endif UA_LOG_WARNING((*logger), UA_LOGCATEGORY_COMMUNICATION, "Could not create socket"); return connection; } struct hostent *server = gethostbyname(hostname); if(server == NULL) { UA_LOG_WARNING((*logger), UA_LOGCATEGORY_COMMUNICATION, "DNS lookup of %s failed", hostname); return connection; } struct sockaddr_in server_addr; memset(&server_addr, 0, sizeof(server_addr)); memcpy((char *)&server_addr.sin_addr.s_addr, (char *)server->h_addr_list[0], server->h_length); server_addr.sin_family = AF_INET; server_addr.sin_port = htons(port); connection.state = UA_CONNECTION_OPENING; if(connect(connection.sockfd, (struct sockaddr *) &server_addr, sizeof(server_addr)) < 0) { ClientNetworkLayerClose(&connection); UA_LOG_WARNING((*logger), UA_LOGCATEGORY_COMMUNICATION, "Connection failed"); return connection; } #ifdef SO_NOSIGPIPE int val = 1; if (setsockopt(connection.sockfd, SOL_SOCKET, SO_NOSIGPIPE, (void*)&val, sizeof(val)) < 0) { UA_LOG_WARNING((*logger), UA_LOGCATEGORY_COMMUNICATION, "Couldn't set SO_NOSIGPIPE"); } #endif //socket_set_nonblocking(connection.sockfd); connection.write = socket_write; connection.recv = socket_recv; connection.close = ClientNetworkLayerClose; connection.getBuffer = ClientNetworkLayerGetBuffer; connection.releaseBuffer = ClientNetworkLayerReleaseBuffer; return connection; }