Below is the file 'profile.c' from this revision. You can also download the file.

/* profile.c */

#include <stddef.h>
#include <string.h>
#include <avr/io.h>
#include <avr/pgmspace.h>
#include <util/atomic.h>

#include "common.h"
#include "profile.h"
#include "menu.h"
#include "config.h"
#include "fields.h"
#include "therm.h"

const profile_t profiles[2] PROGMEM = {
//  { "123456789012345678901", 250,
//    { "Lead free solder     ", 250 + 2732, {
    { "NoPb  ", 250 + 2732, {
        { 1500 + 2732, 100, 0 },
        { 2000 + 2732, 100, 0 },
        { 2500 + 2732,  40, 0 },
        { 2500 + 2732,  30, 0 },
        { 1000 + 2732,  30, 0 },
        {    0 + 2732,   0, 0 }
    } },
//    { "Leaded solder        ", 250 + 2732, {
    { "Pb    ", 250 + 2732, {
        { 1000 + 2732, 100, 0 },
        { 1500 + 2732, 100, 0 },
        { 2350 + 2732,  40, 0 },
        { 2350 + 2732,  30, 0 },
        { 1000 + 2732,  30, 0 },
        {    0 + 2732,   0, 0 }
    } }
};

profile_t profile;
profile_t *profile_p = &profile;
uint8_t current_profile;

void profile_select(uint8_t n)
{
    current_profile = n;
    memcpy_P(&profile, &profiles[n], sizeof(profile_t));
}

void profile_save(void)
{
//    memcpy(&profiles[current_profile], profile_p, sizeof(profile_t));
}


#if 0
static void select_profile_fields(uint8_t row)
{
    memcpy(field_values, profiles[row].name, PROFILE_NAME_LENGTH);
}
#endif

void set_profile_temperature(temp_t temp)
{
    uint8_t row = field_row;

    if (row > 1)
	profile_p->lines[row-2].temperature = temp;
    else
	profile_p->start_temp = temp;
}

temp_t get_profile_temperature(uint8_t row)
{
    if (row > 1)
	return profile_p->lines[row-2].temperature;
    else
	return profile_p->start_temp;
}

void set_profile_time(uint8_t row, uint16_t time, uint8_t time_units)
{
    profile_p->lines[row].time = time;
    profile_p->lines[row].time_units = time_units;
}

uint16_t profile_get_time(uint8_t line)
{
    return profile_p->lines[line].time;
}

uint8_t profile_get_time_units(uint8_t row)
{
    return profile_p->lines[row].time_units;
}

uint32_t profile_time(uint8_t line)
{
    uint32_t time = profile_get_time(line);
    uint8_t time_units = profile_get_time_units(line);
    while (time_units--)
	time = time * 60;

    return time;
}

temp_t temperature_at_time(uint32_t time) {
    uint32_t time0, time1;
    temp_t temp0, temp1;
    uint8_t i;

    temp1 = get_profile_temperature(1);
    time1 = 0;

    for (i = 0; i < 6; i++) {
	uint32_t ptime;
	temp0 = temp1;
	time0 = time1;
	ptime = profile_time(i);
	if (ptime > 0) {
	    temp1 = get_profile_temperature(2+i);
	    time1 += ptime;
	}
	if (time <= time1)
	    break;
    }

    if (time > time1)
	return INVALID_TEMPERATURE;

    return temp0 + ((int32_t)temp1 - (int32_t)temp0) * (int32_t)(time - time0) / (int32_t)(time1 - time0);
}