Project

General

Profile

Revision 1586

Implementation of exponential. Not tested, don't even know if it works at all.

View differences:

trunk/code/projects/fp_math/fp_math.c
10 10

  
11 11
#define TABLE_LENGTH 64
12 12
#define TABLE_STEP 1621//.160757
13
#define EXP_MAGICONSTANT
13 14

  
14
static inline int32_t trig_lookup(int32_t theta, int32_t* table);
15

  
16 15
static int32_t linspace[TABLE_LENGTH] PROGMEM = { 
17 16
	0, 1621, 3242, 4863, 6485, 8106, 9727, 11348, 
18 17
	12969, 14590, 16212, 17833, 19454, 21075, 22696, 24317, 
......
44 43
	return fp_cos(theta + FP_PI_OVER_TWO);
45 44
}
46 45

  
46
int32_t fp_exp(int32_t x) { 
47
	//Try with partial fractions for now.
48
	int32_t xsquare = fp_mult(x,x);
49
	int32_t result, i;
50
	
51
	if(theta > EXP_MAGICONSTANT) { 
52
		usb_puts("Output value is out of range.\n\r");
53
		return -1;
54
	}
55
	
56
	//This is again, massive amounts of lazyness.
57
	//The approximation fails outside this range (approximately).
58
	if(theta < -17)
59
		return 0;
60
	
61
	result = xsquare;
62
	for(i= (22 << 16); i > (2 << 16); i-= (4 << 16)) { 
63
		result += i;
64
		result = fp_div(xsquare, result);
65
	}
66
	
67
	result += (2 << 16) - x;
68
	return (1 << 16) + fp_div(fp_mult((2 << 16), x), result);
69

  
70
}
71

  
47 72
//Quadratic interpolation.
48 73
int32_t fp_cos(int32_t theta) { 
49 74
	uint8_t n;	
......
69 94
		n++;
70 95
	
71 96
	//theta is between x_{n} and x_{n+1}
72
	
73 97
	if(n == TABLE_LENGTH - 1) { 
74 98
		//Perform linear interpolation, since we're close to zero anyway.
75 99
		x_n = pgm_read_dword(&linspace[TABLE_LENGTH - 1]);
trunk/code/projects/fp_math/fp_math.h
3 3
#define _FP_MATH_H_
4 4

  
5 5
#define FP_PI 205887
6
#define FP_E 178145
6 7

  
7 8
#include <stdint.h>
8 9

  

Also available in: Unified diff