예제 #1
0
// Set senderid, packetcounter and CRC into the partly filled packet, encrypt it using the given AES key number and send it.
void send_packet(uint8_t aes_key_nr, uint8_t packet_len)
{
	pkg_header_set_senderid(device_id);

	inc_packetcounter();
	pkg_header_set_packetcounter(packetcounter);

	// set CRC32
	pkg_header_set_crc32(crc32(bufx + 4, packet_len - 4));
	
	// load AES key (0 is first AES key)
	if (aes_key_nr >= aes_key_count)
	{
		aes_key_nr = aes_key_count - 1;
	}
	
	e2p_basestation_get_aeskey(aes_key_nr, aes_key);
	
	// show info
	decode_data(packet_len);

	// encrypt and send
	__PACKETSIZEBYTES = packet_len;
	rfm12_send_bufx();
}
예제 #2
0
// process message "brightness"
void process_brightness(MessageTypeEnum messagetype)
{
	// "Set" or "SetGet" -> modify dimmer state and abort any running animation
	if ((messagetype == MESSAGETYPE_SET) || (messagetype == MESSAGETYPE_SETGET))
	{
		start_brightness = end_brightness = msg_dimmer_brightness_get_brightness();

		UART_PUTF("Requested Brightness: %u%%;", start_brightness);
		
		animation_length = 0;
		animation_mode = 0;
		animation_position = 0;

		setPWMDutyCyclePercent(start_brightness);
						
		/* TODO: Write to EEPROM (?)
		// write back switch state to EEPROM
		switch_state[i] = req_state;
		switch_timeout[i] = req_timeout;
		
		eeprom_write_word((uint16_t*)EEPROM_POS_SWITCH_STATE + i * 2, u16);
		*/
	}

	// remember some values before the packet buffer is destroyed
	uint32_t acksenderid = pkg_header_get_senderid();
	uint32_t ackpacketcounter = pkg_header_get_packetcounter();

	inc_packetcounter();

	// "Set" -> send "Ack"
	if (messagetype == MESSAGETYPE_SET)
	{
		pkg_header_init_dimmer_brightness_ack();

		UART_PUTS("Sending Ack\r\n");
	}
	// "Get" or "SetGet" -> send "AckStatus"
	else
	{
		pkg_header_init_dimmer_brightness_ackstatus();
		
		// set message data
		msg_dimmer_brightness_set_brightness(start_brightness);

		UART_PUTS("Sending AckStatus\r\n");
	}

	// set common fields
	pkg_header_set_senderid(device_id);
	pkg_header_set_packetcounter(packetcounter);
	
	pkg_headerext_common_set_acksenderid(acksenderid);
	pkg_headerext_common_set_ackpacketcounter(ackpacketcounter);
	pkg_headerext_common_set_error(false); // FIXME: Move code for the Ack to a function and also return an Ack when errors occur before!
	
	pkg_header_calc_crc32();
	
	rfm12_send_bufx();
}
void send_prepared_message(void)
{
	inc_packetcounter();
	
	pkg_header_set_senderid(device_id);
	pkg_header_set_packetcounter(packetcounter);
	
	rfm12_send_bufx();
	rfm12_tick(); // send packet, and then WAIT SOME TIME BEFORE GOING TO SLEEP (otherwise packet would not be sent)

	led_blink(200, 0, 1);
}
예제 #4
0
void send_version_status(void)
{
	inc_packetcounter();

	UART_PUTF4("Sending Version: v%u.%u.%u (%08lx)\r\n", VERSION_MAJOR, VERSION_MINOR, VERSION_PATCH, VERSION_HASH);
	
	// Set packet content
	pkg_header_init_generic_version_status();
	pkg_header_set_senderid(device_id);
	pkg_header_set_packetcounter(packetcounter);
	msg_generic_version_set_major(VERSION_MAJOR);
	msg_generic_version_set_minor(VERSION_MINOR);
	msg_generic_version_set_patch(VERSION_PATCH);
	msg_generic_version_set_hash(VERSION_HASH);
	pkg_header_calc_crc32();

	rfm12_send_bufx();
}
예제 #5
0
void send_dimmer_status(void)
{
	UART_PUTS("Sending Dimmer Status:\r\n");

	inc_packetcounter();
	uint8_t bri = (uint8_t)current_brightness;
	
	// Set packet content
	pkg_header_init_dimmer_brightness_status();
	pkg_header_set_senderid(device_id);
	pkg_header_set_packetcounter(packetcounter);
	msg_dimmer_brightness_set_brightness(bri);

	pkg_header_calc_crc32();
	
	UART_PUTF("CRC32 is %lx (added as first 4 bytes)\r\n", getBuf32(0));
	UART_PUTF("Brightness: %u%%\r\n", bri);

	rfm12_send_bufx();
}
예제 #6
0
// Search for a request to repeat (with timeout reached) and write the data to the send buffer bufx.
// Return a pointer to the request if successful, 0 if no request to repeat was found.
// Automatically decrease timeout counters for all waiting requests in the queue,
// delete a request if it is repeated the last time and cleanup the queue and repeat_buffer accordingly.
// This function has to be called once a second, because the timeout values represent the amount of seconds.
//
// TODO (optimization): Change the behaviour so that a new packet can be sent out of the queue without a delay (currently, we have ~0.5s delay in average).
// So check the queue for "timeout 0" packets more often, but don't reduce the timeout in this case.
request_t * find_request_to_repeat(uint32_t packet_counter)
{
    uint8_t i;
    uint8_t slot;
    request_t * res = 0;

    for (i = 0; i < REQUEST_QUEUE_RECEIVERS; i++)
    {
        if (request_queue[i][0] != SLOT_UNUSED)
        {
            // count down timeout from first element per queue
            slot = request_queue[i][1];

            if (request_buffer[slot].timeout > 0)
            {
                request_buffer[slot].timeout--;
            }

            // set bufx to the request to retry, if timeout is reached
            if ((request_buffer[slot].timeout == 0) && (res == 0))
            {
                res = &request_buffer[slot];

                // Init header
                memset(&bufx[0], 0, sizeof(bufx));
                pkg_header_set_senderid(0); // FIXME: Use DeviceID instead?!
                pkg_header_set_packetcounter(packet_counter);

                // set message type
                pkg_header_set_messagetype(request_buffer[slot].message_type);

                // set header extension (incl. receiver_id) + data
                memcpy(bufx + 9, request_buffer[slot].data, request_buffer[slot].data_bytes); // header size = 9 bytes

                // remember packet counter
                request_buffer[slot].packet_counter = packet_counter;

                request_buffer[slot].retry_count++;

                if (request_buffer[slot].retry_count > REQUEST_RETRY_COUNT)
                {
                    // delete request from queue
                    request_buffer[slot].message_type = MESSAGETYPE_UNUSED;

                    uint8_t x;

                    for (x = 1; x < REQUEST_QUEUE_PACKETS; x++)
                    {
                        request_queue[i][x] = request_queue[i][x + 1];
                    }

                    request_queue[i][REQUEST_QUEUE_PACKETS] = SLOT_UNUSED;

                    // delete request queue completely (if no requests are in the queue)
                    if (request_queue[i][1] == SLOT_UNUSED)
                    {
                        request_queue[i][0] = SLOT_UNUSED;
                    }
                }
                else
                {
                    request_buffer[slot].timeout = (request_buffer[slot].retry_count - 1) * REQUEST_ADDITIONAL_TIMEOUT_S + REQUEST_INITIAL_TIMEOUT_S;
                }
            }
        }

        //UART_PUTS("\r\n");
    }

    return res;
}