Esempio n. 1
0
int fastcall read(int hnd, void *buf, unsigned count)
{
    static WORD map;
    int ret;
        
	hnd = hnd;
    if(!screen_initialized)
        return uart_read_buffer(buf, count);

    map = MAPPER_MAP1;
    MAPPER_MAP1 = MAP_RAMDMA;
    IRQ_TMR_CTRL = TMR_ENABLE;
    
    if(string_input((char *)cursor_pos, buf, count))
        ret = strlen(buf);
    else
        ret = 0;
        
    IRQ_TMR_CTRL = TMR_DISABLE;
    MAPPER_MAP1 = map;
    return ret;
}
Esempio n. 2
0
void modbus_rtu_master_tick(void)
{
    modbus* bus;

    // tick all busses
    for(bus = busses; bus < (busses + MODBUS_NUMBER_OF_BUSSES); bus++)
    {
        modbus_state oldState;

        oldState = bus->state;

        switch(bus->state)
        {
        case BUS_STATE_IDLE:
            {
                modbus_message* message;
                if(list_peek_first(&bus->messageQueue, (void**)&message)) // is there a message waiting to be sent
                {
                    if(message->state == MODBUS_MESSAGE_STATE_DISCARDED) // has message been discared by the application while waiting in the queue?
                    {
                        list_remove(&bus->messageQueue, message);

                        modbus_rtu_master_release_message(message);

                        NABTO_LOG_TRACE(("Completing discard request (bus=%u, query=%u).", bus->identifier, (int)message));
                    }
                    else // start transferring the message
                    {
                        uint32_t compensatedReponseTime = message->maximumResponsetime + calculate_transmission_time(message->frameSize);

                        NABTO_LOG_TRACE(("Sending query (bus=%u, timeout=%u, compensated timeout=%u).", bus->identifier, (int)message->maximumResponsetime, (int)compensatedReponseTime));

                        uart_flush_receiver(bus->uartChannel);
                        uart_write_buffer(bus->uartChannel, message->frame, message->frameSize);

                        message->state = MODBUS_MESSAGE_STATE_TRANSFERRING;

                        nabtoSetFutureStamp(&bus->responseTimeout, compensatedReponseTime); // time to wait for start of response: transmission time of outgoing frame + maximum response time
                        bus->responseSize = 0;
                        bus->responseOverrun = false;

                        bus->state = BUS_STATE_BUSY;
                        
                        NABTO_LOG_TRACE(("Query sent (bus=%u, timeout=%u, compensated timeout=%u).", bus->identifier, (int)message->maximumResponsetime, (int)compensatedReponseTime));
                        NABTO_LOG_BUFFER(NABTO_LOG_SEVERITY_LEVEL_TRACE, ("Query (length=%u): (shown with CRC)", (int)message->frameSize), message->frame, message->frameSize);
                    }
                }
            }
            break;

        case BUS_STATE_BUSY:
            {
                uint16_t length;
                
                length = uart_can_read(bus->uartChannel);

                if(length > 0) // has data been received?
                {
                    if(bus->responseOverrun == false) // ignore all data after an overrun has occurred
                    {
                        if((bus->responseSize + length) <= MODBUS_MAXIMUM_FRAME_SIZE) // is there room for the data?
                        {
                            // add data to response buffer
                            uart_read_buffer(bus->uartChannel, bus->response + bus->responseSize, length);
                            bus->responseSize += length;
                        }
                        else // response buffer overrun
                        {
                            uart_flush_receiver(bus->uartChannel); // discard data
                            bus->responseOverrun = true; // mark response as over size
                            NABTO_LOG_TRACE(("Receiving oversize response (bus=%u, oversize length=%u)!", bus->identifier, (int)((bus->responseSize + length) - MODBUS_MAXIMUM_FRAME_SIZE)));
                        }
                    }
                    else
                    {
                        uart_flush_receiver(bus->uartChannel); // discard data
                        NABTO_LOG_TRACE(("Dumping overrun data (bus=%u, length=%u)!", bus->identifier, (int)length));
                    }

                    nabtoSetFutureStamp(&bus->frameCommitTimeout, FRAME_SILENT_DURATION); // reset packet commit timer
                }
                else if(bus->responseSize > 0) // has the response begun
                {
                    if(nabtoIsStampPassed(&bus->frameCommitTimeout)) // has the frame ended
                    {
                        modbus_message* message;
                        list_peek_first(&bus->messageQueue, (void**)&message);

                        if(message->state == MODBUS_MESSAGE_STATE_DISCARDED) // has the message been discarded
                        {
                            list_remove(&bus->messageQueue, message);

                            modbus_rtu_master_release_message(message); // perform actual release of discarded message

                            bus->state = BUS_STATE_IDLE;

                            NABTO_LOG_TRACE(("Received response for dumped query (bus=%u, query=%u, response length=%u).", bus->identifier, (int)message, (int)bus->responseSize));
                        }
                        else
                        {
                            if(modbus_rtu_crc_verify_crc_field(bus->response, bus->responseSize)) // does reponse pass CRC check?
                            {
                                NABTO_LOG_BUFFER(NABTO_LOG_SEVERITY_LEVEL_TRACE, ("Received response (bus=%u, length=%u): (shown with CRC)", bus->identifier, (int)bus->responseSize), bus->response, bus->responseSize);

                                // replace the query in the message with the response (removing CRC)
                                memcpy(message->frame, bus->response, bus->responseSize - 2);
                                message->frameSize = bus->responseSize - 2;

                                message->state = MODBUS_MESSAGE_STATE_COMPLETED; // mark message as completed

                                // move message from transfer queue to completed list
                                list_remove(&bus->messageQueue, message);
                                list_append(&completedList, message);

                                bus->state = BUS_STATE_IDLE;

                                NABTO_LOG_TRACE(("Received response for query (bus=%u, query=%u).", bus->identifier, (int)message));
                            }
                            else
                            {
                                NABTO_LOG_TRACE(("Received bad response for query (bus=%u, query=%u)!", bus->identifier, (int)message));
                                retransmit_current_message(bus);
                            }
                        }
                    }
                }
                else if(nabtoIsStampPassed(&bus->responseTimeout)) // the response has not begun within the time limit
                {
                    modbus_message* message;
                    list_peek_first(&bus->messageQueue, (void**)&message);

                    NABTO_LOG_TRACE(("No response received (bus=%u, message=%u)!", bus->identifier, (int)message));

                    if(message->state == MODBUS_MESSAGE_STATE_DISCARDED) // has the application discarded the message?
                    {
                        list_remove(&bus->messageQueue, message);

                        modbus_rtu_master_release_message(message); // perform actual release of discarded message

                        bus->state = BUS_STATE_IDLE;
                        
                        NABTO_LOG_TRACE(("Completing discard request (bus=%u, query=%u).", bus->identifier, (int)message));
                    }
                    else // no - just continue and retransmit the message
                    {
                        retransmit_current_message(bus);
                    }
                }
            }
            break;
        }

        if(oldState != bus->state)
        {
            NABTO_LOG_TRACE(("State change in bus %u: %s -> %s", bus->identifier, modbusStateNames[oldState], modbusStateNames[bus->state]));
        }
    }
}