short int Receive() { static char buf[UDP_MAX_SIZE]; char unknown[24]; unsigned char badr[24]; char *pos; struct sockaddr_in from; unsigned int fromlen; int size; unsigned int sts; remote_udp_header header; remtrans_item *remtrans; unsigned char search_remtrans; rem_t_transbuff *transbuff; rem_t_transbuff *transbuff_behind; remtrans_item *transp; /* We have made a select, so we're pretty sure there is something to take */ fromlen = sizeof(struct sockaddr); size = recvfrom(my_socket, &buf, sizeof(buf), 0, (struct sockaddr *) &from, &fromlen); if (size < 0) { /* Definitly error */ errh_Info("UDP Receive fail %s", rn_udp->RemoteHostname); rn_udp->ErrCount++; return(-1); } if (rn_udp->Disable) return(1); if (memcmp(&from.sin_addr, &their_addr.sin_addr, sizeof(struct in_addr)) != 0) { /*from.sin_port != their_addr.sin_port*/ memcpy(&badr, &from.sin_addr, 4); sprintf(unknown, "%d.%d.%d.%d", badr[0], badr[1], badr[2], badr[3]); errh_Info("UDP Receive from unknown source %s", unknown); rn_udp->ErrCount++; return(1); } /* Set link up */ time_since_rcv = 0; if (rn_udp->LinkUp == 0) { errh_Info("UDP link up %s", rn_udp->RemoteHostname); rn_udp->LinkUp = 1; } if (size > 0 && rn_udp->DisableHeader) { /* Header disabled, take the first receive remtrans object */ remtrans = rn.remtrans; search_remtrans = true; while(remtrans && search_remtrans) { /* Match? */ if (remtrans->objp->Direction == REMTRANS_IN) { search_remtrans = false; sts = RemTrans_Receive(remtrans, buf, size); } remtrans = (remtrans_item *) remtrans->next; } if (search_remtrans) { rn_udp->ErrCount++; errh_Info("UDP Receive no remtrans %s", rn_udp->RemoteHostname); } } else if (size >= 8) { memcpy(&header, &buf, sizeof(remote_udp_header)); /* Convert the header to host byte order */ header.msg_size = ntohs(header.msg_size); header.msg_id[0] = ntohs(header.msg_id[0]); header.msg_id[1] = ntohs(header.msg_id[1]); if (header.protocol_id[0] == STX && size == header.msg_size) { /* This is a valid remtrans */ if (header.protocol_id[1] == ETB || header.protocol_id[1] == ENQ) { if (header.msg_id[0] == 0 && header.msg_id[1] == 0) { /* Keepalive */ rn_udp->KeepaliveDiff--; } else { /* Data */ remtrans = (remtrans_item *) rn.remtrans; search_remtrans = true; while(remtrans && search_remtrans) { /* Match? */ if (remtrans->objp->Address[0] == header.msg_id[0] && remtrans->objp->Address[1] == header.msg_id[1] && remtrans->objp->Direction == REMTRANS_IN) { search_remtrans = false; pos = ((char *) &buf) + sizeof(remote_udp_header); sts = RemTrans_Receive(remtrans, pos, header.msg_size-sizeof(remote_udp_header)); if (header.protocol_id[1] == ENQ) { SendAck(header.msg_id[0], header.msg_id[1]); } } remtrans = (remtrans_item *) remtrans->next; } if (search_remtrans) { rn_udp->ErrCount++; errh_Info("UDP Receive no remtrans %s", rn_udp->RemoteHostname); } } } else if (header.protocol_id[1] == ACK) { /* Acknowledge message */ transbuff = (rem_t_transbuff *) rn.transbuff; transbuff_behind = (rem_t_transbuff *) rn.transbuff; while (transbuff) { transp = (remtrans_item *) transbuff->remtrans; if (header.msg_id[0] == transp->objp->Address[0] && header.msg_id[1] == transp->objp->Address[1]) { /* This is it, unlink the transbuff */ if (transbuff == transbuff_behind) rn.transbuff = (rem_t_transbuff *) transbuff->next; else transbuff_behind->next = (rem_t_transbuff *) transbuff->next; /* Decrement buffer counter */ transp->objp->Buffers--; /* Free transbuff */ free(transbuff); /* Break the while loop */ break; } transbuff_behind = transbuff; transbuff = (rem_t_transbuff *) transbuff->next; } } else { /* Weird header */ rn_udp->ErrCount++; errh_Info("UDP receive weird header %s, %02x %02x %04x %04x %04x", rn_udp->RemoteHostname, header.protocol_id[0], header.protocol_id[1], header.msg_size, header.msg_id[0], header.msg_id[1]); } } else { /* Weird header */ rn_udp->ErrCount++; errh_Info("UDP receive weird header %s, %02x %02x %04x %04x %04x", rn_udp->RemoteHostname, header.protocol_id[0], header.protocol_id[1], header.msg_size, header.msg_id[0], header.msg_id[1]); } } else { /* Not a remtrans UPD message */ rn_udp->ErrCount++; errh_Info("UDP receive weird message %s", rn_udp->RemoteHostname); } return(1); }
static unsigned int Receive() { int sts; int nbr_of_bytes_read = 0; unsigned char telegram[512]; char search_remtrans = FALSE; remtrans_item *remtrans; fd_set read_fd; struct timeval tv; load_timeval(&tv, rn_serial->ScanTime); nbr_of_bytes_read = 0; telegram[nbr_of_bytes_read] = 0; sts = 0; while (nbr_of_bytes_read < sizeof(telegram)-2) { // Om vi är under mottagning, vänta tills lästimeout if (nbr_of_bytes_read > 0) load_timeval(&tv, rn_serial->ReadTimeout); FD_ZERO(&read_fd); FD_SET(ser_fd, &read_fd); sts = select(ser_fd+1, &read_fd, NULL, NULL, &tv); if (sts > 0) { // Tecken finns att läsa sts = read(ser_fd, &telegram[nbr_of_bytes_read], 1); if(sts > 0) { nbr_of_bytes_read++; if (telegram[nbr_of_bytes_read-1]==rn_serial->TermChar[0] || telegram[nbr_of_bytes_read-1]==rn_serial->TermChar[1] || telegram[nbr_of_bytes_read-1]==rn_serial->TermChar[2] || telegram[nbr_of_bytes_read-1]==rn_serial->TermChar[3] || telegram[nbr_of_bytes_read-1]==rn_serial->TermChar[4] || telegram[nbr_of_bytes_read-1]==rn_serial->TermChar[5] || telegram[nbr_of_bytes_read-1]==rn_serial->TermChar[6] || telegram[nbr_of_bytes_read-1]==rn_serial->TermChar[7] ) break; } else { // Läsfel rn_serial->ErrCount++; break; } } else { // Timeout break; } } if (nbr_of_bytes_read > 0) // Vi tog emot ett eller flera tecken { telegram[nbr_of_bytes_read] = 0; if (debug) { printf("Vi tog emot en trans med terminering 0x%x\n", telegram[nbr_of_bytes_read-1]); printf("Telegramet var:%s\n", telegram); } search_remtrans = true; remtrans = rn.remtrans; while (remtrans && search_remtrans) { if (remtrans->objp->Direction == REMTRANS_IN ) search_remtrans = false; if ( search_remtrans ) remtrans = (remtrans_item *) remtrans->next; } /* endwhile */ if ( !search_remtrans ) { sts = RemTrans_Receive(remtrans, (char *)telegram, nbr_of_bytes_read); if ( EVEN(sts) ) { remtrans->objp->ErrCount++; return (FALSE); } } if (search_remtrans) { /* No corresponding RemTrans object found */ rn_serial->ErrCount++; return (FALSE); } } return(1); }
unsigned int wmq_receive() { MQLONG CompCode; MQLONG Reason; MQMD MsgDesc = {MQMD_DEFAULT}; MQLONG DataLength; MQCHAR Buffer[200000]; MQGMO GetMsgOpts = {MQGMO_DEFAULT}; MQLONG BufferLength = sizeof(Buffer); unsigned int sts; char search_remtrans; remtrans_item *remtrans; /* Set options */ GetMsgOpts.Options = MQGMO_NO_WAIT + MQGMO_ACCEPT_TRUNCATED_MSG; MsgDesc.Encoding = MQENC_NATIVE; MsgDesc.CodedCharSetId = MQCCSI_Q_MGR; /* Get message */ MQGET(Hconn, RcvHobj, &MsgDesc, &GetMsgOpts, BufferLength, Buffer, &DataLength, &CompCode, &Reason); if (CompCode != MQCC_FAILED) { if (debug) printf("Received message %d\n", (int) DataLength); search_remtrans = true; remtrans = rn.remtrans; while(remtrans && search_remtrans) { if ((strncmp(remtrans->objp->TransName, (char *) MsgDesc.CorrelId, MQ_CORREL_ID_LENGTH) == 0) && (remtrans->objp->Direction == REMTRANS_IN)) { search_remtrans = false; sts = RemTrans_Receive(remtrans, (char *) &Buffer, DataLength); if (sts != STATUS_OK && sts != STATUS_BUFF) errh_Error("Error from RemTrans_Receive, status %d", sts, 0); break; } remtrans = (remtrans_item *) remtrans->next; } if (search_remtrans) { rn_wmq->ErrCount++; errh_Info("No remtrans for received message, msgid %s", MsgDesc.MsgId, 0); } } else if (Reason != MQRC_NO_MSG_AVAILABLE) { rn_wmq->ErrCount++; errh_Error("Receive failed, reason %d", Reason, 0); if (Reason == MQRC_CONNECTION_BROKEN) { connected = 0; } } return(sts); }
static unsigned int ReceiveHandler(int fd) { unsigned int sts; //unsigned int nbr_of_bytes_written = 0; //unsigned int nbr_of_bytes_read = 0; unsigned int data_size = 0; unsigned int io_size = 0; unsigned int common_offset = 0; char cont = TRUE; char search_remtrans = FALSE; char name[7]; unsigned char BCC = '\0'; unsigned char receive_buffer[MAX_SIZE_TELEGRAM]; unsigned char sdle = DLE; unsigned char received_char; remtrans_item *remtrans; int i; fd_set read_fd; struct timeval tv; char type_name[4]; common_buffer_vnet *c_buf; /**** set up timeout,****/ load_timeval(&tv, rn_3964R->CharTimeout); // tv.tv_sec = TIMEOUT_REC_CHAR_SEC; // tv.tv_usec = TIMEOUT_REC_CHAR_USEC; /*************************************************************************/ /** Read telegram **/ /*************************************************************************/ cont = TRUE; data_size = 0; while (cont) { /* Read until DLE is received */ received_char=0; while(received_char != DLE) { load_timeval(&tv, rn_3964R->CharTimeout); FD_ZERO(&read_fd); FD_SET(fd, &read_fd); select(fd+1, &read_fd, NULL, NULL, &tv); if (read(fd, &received_char, 1) > 0) { //om det inte var timeout // Prevent writing oob if (data_size > MAX_SIZE_TELEGRAM - 10) return (FALSE); receive_buffer[data_size++]=received_char; } else //timeout gå tillbaka { errh_Error("3964R mottagning, character timeout"); return(FALSE); } } /* Read one more */ load_timeval(&tv, rn_3964R->CharTimeout); FD_ZERO(&read_fd); FD_SET(fd, &read_fd); select(fd+1, &read_fd, NULL, NULL, &tv); if (read(fd, &receive_buffer[data_size], 1) < 1) { errh_Error("3964R mottagning, character timeout"); return(FALSE); } if (receive_buffer[data_size] == ETX) { data_size++; /* Read one more, should be checksum */ load_timeval(&tv, rn_3964R->CharTimeout); FD_ZERO(&read_fd); FD_SET(fd, &read_fd); select(fd+1, &read_fd, NULL, NULL, &tv); if (read(fd, &receive_buffer[data_size], 1) < 1) { errh_Error("3964R mottagning, character timeout"); return(FALSE); } data_size++; cont = FALSE; } else if (receive_buffer[data_size] != DLE ) data_size++; } /*************************************************************************/ /** A complete message is received. Check BCC. **/ /*************************************************************************/ BCC = DLE ^ ETX; for (i=0; i<data_size-3; i++) if (receive_buffer[i] != DLE) BCC ^= receive_buffer[i]; if ( BCC == receive_buffer[data_size-1] ) { if(!write(fd,&sdle, 1)) return(FALSE); } else { /* Checksum in this telegram is wrong */ errh_Error("3964R mottagning, felaktig checksumma, %d, %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x %02x", data_size, receive_buffer[0], receive_buffer[1], receive_buffer[2], receive_buffer[3], receive_buffer[4], receive_buffer[5], receive_buffer[6], receive_buffer[7], receive_buffer[8], receive_buffer[9], receive_buffer[10], receive_buffer[11]); if (debug) printf(" Checksum error\n"); if (use_remote_io) { if(!write(fd,&sdle, 1)) return(FALSE); } else return(FALSE); } /*************************************************************************/ /** Find out if the received message is a array of io updates. **/ /** Treat the message and exit. **/ /*************************************************************************/ { io_buffer_vnet *io_buf = (io_buffer_vnet *) &receive_buffer; RemUtils_R50ToAscii((unsigned short *) &io_buf->io_name, (char *) &name); if (strstr(name, "PSS")) { io_size = io_buf->length * 2; /* Converted to bytes */ sts = RemIO_Receive_3964R(&rn, (unsigned char *) &io_buf->data, io_size-NET_HEADER_SIZE_IO); if (debug) printf(" Receiving I/O area\n"); time_since_io = 0; rn_3964R->LinkUp = 1; return(sts); } } /*************************************************************************/ /** Find out if the received message is a array of common data **/ /** Search for the RemTrans object that is the target. **/ /*************************************************************************/ c_buf = (common_buffer_vnet *) &receive_buffer; RemUtils_R50ToAscii((unsigned short *) &c_buf->common_name, (char *) &name); for ( i=0 ; i<4 ; i++ ) { type_name[i] = name[i+3]; } if ( (strncmp(type_name, "COM", 3)) == 0 ){ search_remtrans = true; remtrans = rn.remtrans; while(remtrans && search_remtrans) { if ( remtrans->objp->Address[0] == c_buf->common_name[0] && remtrans->objp->Address[1] == c_buf->common_name[1] ) search_remtrans = false; if ( search_remtrans ) remtrans = (remtrans_item *) remtrans->next; } /* endwhile */ /*************************************************************************/ /** Treat the common data update message and exit. **/ /*************************************************************************/ if ( !search_remtrans ){ io_size = c_buf->length * 2; /* Converted to bytes */ common_offset = c_buf->offset; if (io_size > remtrans->objp->MaxLength ){ remtrans->objp->ErrCount++; remtrans->objp->LastSts = STATUS_LENGTH; return(FALSE); } else { memcpy(&remtrans->datap[common_offset], c_buf, io_size); time_GetTime(&remtrans->objp->TransTime); remtrans->objp->TransCount++; remtrans->objp->DataValid = TRUE; remtrans->objp->LastSts = STATUS_OK; remtrans->objp->DataLength = data_size; } return(TRUE); } } /*************************************************************************/ /** This message contains a ordinary remtrans **/ /** Search for the RemTrans object that is the target. **/ /** If remote I/O is not used, the message is stored in the first **/ /** found (ingoing) remtrans object. If we use remote I/O we check for**/ /** matching message header **/ /*************************************************************************/ search_remtrans = true; remtrans = rn.remtrans; while(remtrans && search_remtrans) { if (remtrans->objp->Direction == REMTRANS_IN) { if (!use_remote_io) { search_remtrans = false; } else { if (remtrans->objp->Address[0] == c_buf->common_name[0] && remtrans->objp->Address[1] == c_buf->common_name[1]) search_remtrans = false; } } if ( search_remtrans ) remtrans = (remtrans_item *) remtrans->next; } /*************************************************************************/ /** Treat the remtrans message and exit. **/ /*************************************************************************/ if (!search_remtrans) { sts = RemTrans_Receive(remtrans, (char *)receive_buffer, data_size-3); if ( EVEN(sts) ) { remtrans->objp->ErrCount++; return (FALSE); } } else { /* No remtrans */ errh_Error("Remtrans 3964R no remtrans for this message"); rn_3964R->ErrCount++; return (FALSE); } return (TRUE); }
unsigned int rmq_receive() { pwr_tStatus sts; int search_remtrans = 0; remtrans_item* remtrans; amqp_rpc_reply_t ret; amqp_envelope_t envelope; struct timeval t = { 2, 0 }; rabbit_header header; int msg_received = 0; amqp_maybe_release_buffers(ctx->conn); ret = amqp_consume_message(ctx->conn, &envelope, &t, 0); switch (ret.reply_type) { case AMQP_RESPONSE_NORMAL: { break; } case AMQP_RESPONSE_NONE: return REM__SUCCESS; case AMQP_RESPONSE_SERVER_EXCEPTION: return REM__EXCEPTION; case AMQP_RESPONSE_LIBRARY_EXCEPTION: switch (ret.library_error) { case AMQP_STATUS_TIMEOUT: { amqp_destroy_envelope(&envelope); return REM__TIMEOUT; } case AMQP_STATUS_UNEXPECTED_STATE: { amqp_frame_t frame; sts = amqp_simple_wait_frame_noblock(ctx->conn, &frame, &t); if (sts == AMQP_STATUS_TIMEOUT) { printf("Wait frame timeout\n"); return REM__EXCEPTION; } else if (sts == AMQP_STATUS_OK) { if (frame.frame_type == AMQP_FRAME_METHOD) { switch (frame.payload.method.id) { case AMQP_BASIC_ACK_METHOD: printf("Basic ack method called\n"); break; case AMQP_BASIC_RETURN_METHOD: printf("Basic return method called\n"); break; case AMQP_CHANNEL_CLOSE_METHOD: printf("Channel close method called\n"); break; case AMQP_CONNECTION_CLOSE_METHOD: printf("Connection close method called\n"); break; default:; } } return REM__EXCEPTION; } else return REM__EXCEPTION; } } // Reconnect... rmq_close(1); return REM__EXCEPTION; default: printf("Unknown Reply type: %d\n", ret.reply_type); } if (debug) printf("Received message %d\n", (int)envelope.message.body.len); if (envelope.message.body.len > 0 && rn_rmq->DisableHeader) { /* Header disabled, take the first receive remtrans object */ remtrans = rn.remtrans; search_remtrans = 1; while (remtrans && search_remtrans) { /* Match? */ if (remtrans->objp->Direction == REMTRANS_IN) { search_remtrans = false; sts = RemTrans_Receive(remtrans, (char*)envelope.message.body.bytes, envelope.message.body.len); msg_received = 1; } remtrans = (remtrans_item*)remtrans->next; } if (search_remtrans) { rn_rmq->ErrCount++; errh_Info("RabbitMQ Receive no remtrans %s", rn_rmq->ReceiveQueue); } } else if (envelope.message.body.len >= sizeof(rabbit_header)) { memcpy(&header, envelope.message.body.bytes, sizeof(rabbit_header)); /* Convert the header to host byte order */ header.msg_size = ntohs(header.msg_size); header.msg_id[0] = ntohs(header.msg_id[0]); header.msg_id[1] = ntohs(header.msg_id[1]); search_remtrans = 1; remtrans = rn.remtrans; while (remtrans && search_remtrans) { if (remtrans->objp->Address[0] == header.msg_id[0] && remtrans->objp->Address[1] == header.msg_id[1] && remtrans->objp->Direction == REMTRANS_IN) { search_remtrans = false; sts = RemTrans_Receive(remtrans, (char*)envelope.message.body.bytes + sizeof(rabbit_header), envelope.message.body.len); if (sts != STATUS_OK && sts != STATUS_BUFF) errh_Error("Error from RemTrans_Receive, queue %s, status %d", rn_rmq->ReceiveQueue, sts, 0); msg_received = 1; break; } remtrans = (remtrans_item*)remtrans->next; } if (search_remtrans) { rn_rmq->ErrCount++; errh_Info("No remtrans for received message, queue %s, class %d, type %d", rn_rmq->ReceiveQueue, header.msg_id[0], header.msg_id[1]); } } if (ctx->op->Acknowledge) { if (msg_received) amqp_basic_ack(ctx->conn, ctx->channel, envelope.delivery_tag, 0); else /* Requeue the message */ amqp_basic_nack(ctx->conn, ctx->channel, envelope.delivery_tag, 0, 1); } amqp_destroy_envelope(&envelope); return sts; }