Important changes to repositories hosted on mbed.com
Mbed hosted mercurial repositories are deprecated and are due to be permanently deleted in July 2026.
To keep a copy of this software download the repository Zip archive or clone locally using Mercurial.
It is also possible to export all your personal repositories from the account settings page.
Fork of GR-PEACH_test_wo_rtos by
Revision 7:c87a84872d85, committed 2015-01-11
- Comitter:
- kenjiArai
- Date:
- Sun Jan 11 09:48:17 2015 +0000
- Parent:
- 6:849caec97744
- Commit message:
- ADC performance check
Changed in this revision
--- a/L3GD20.lib Fri Jan 09 22:50:07 2015 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,1 +0,0 @@ -http://developer.mbed.org/users/kenjiArai/code/L3GD20/#7d0cec583aa3
--- a/LIS3DH.lib Fri Jan 09 22:50:07 2015 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,1 +0,0 @@ -http://developer.mbed.org/users/kenjiArai/code/LIS3DH/#64dac49da306
--- a/TextLCD.lib Fri Jan 09 22:50:07 2015 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,1 +0,0 @@ -http://developer.mbed.org/users/wim/code/TextLCD/#9f5f86dfd44a
--- a/main.cpp Fri Jan 09 22:50:07 2015 +0000
+++ b/main.cpp Sun Jan 11 09:48:17 2015 +0000
@@ -6,7 +6,7 @@
* http://www.page.sannet.ne.jp/kenjia/index.html
* http://mbed.org/users/kenjiArai/
* Created: November 29th, 2014
- * Revised: January 10th, 2015
+ * Revised: January 11th, 2015
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
* INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE
@@ -17,15 +17,10 @@
// Include ---------------------------------------------------------------------------------------
#include "mbed.h"
-#include "L3GD20.h"
-#include "LIS3DH.h"
-#include "TextLCD.h"
// Definition ------------------------------------------------------------------------------------
#define USE_COM // use Communication with PC(UART)
-#define USE_I2C_LCD
-#define USE_I2C_SENSOR
-
+
// Com
#ifdef USE_COM
#define BAUD(x) pcx.baud(x)
@@ -41,114 +36,462 @@
#define READABLE(x) {;}
#endif
+// Use TL431ACZ-AP
+// Akizuki NJM431 (equivalent)
+// http://akizukidenshi.com/catalog/g/gI-00431/
+#define VREF (2.478f) // measured data (not Typ. data)
+
+#if defined(TARGET_RZ_A1H)
+//#define ADC_BUF_SIZE (4096 * 40)
+#define ADC_BUF_SIZE (1024)
+#elif defined(TARGET_NUCLEO_F401RE) || defined(TARGET_NUCLEO_F411RE)
+#define ADC_BUF_SIZE (1024)
+#elif defined(TARGET_K64F)
+#define ADC_BUF_SIZE (1024)
+#endif
+
+
// Object ----------------------------------------------------------------------------------------
-// LED's
-DigitalOut LEDs[4] = {
- DigitalOut(LED1), DigitalOut(LED2), DigitalOut(LED3), DigitalOut(LED4)
-};
-// Swiches
-DigitalIn USER_SWITCH[2] = {
- #if defined(TARGET_RZ_A1H)
- DigitalIn(P6_0), DigitalIn(P6_1)
- #elif defined(TARGET_NUCLEO_F401RE) || defined(TARGET_NUCLEO_F411RE)\
- || defined(TARGET_NUCLEO_L152RE)
- DigitalIn(PC_13), DigitalIn(A0)
- #elif defined(TARGET_LPC1768)
- DigitalIn(A0), DigitalIn(A1)
- #elif defined(TARGET_K64F)
- DigitalIn(PTA4), DigitalIn(PTC6)
- #endif
-};
// com
#ifdef USE_COM
Serial pcx(USBTX, USBRX); // Communication with Host
#endif
-I2C i2c(D14,D15);
-// Gyro
-L3GX_GYRO gyro(i2c, L3GD20_V_CHIP_ADDR, L3GX_DR_95HZ, L3GX_BW_HI, L3GX_FS_250DPS);
-// Acc
-LIS3DH acc(i2c, LIS3DH_G_CHIP_ADDR, LIS3DH_DR_NR_LP_50HZ, LIS3DH_FS_8G);
-#ifdef USE_I2C_LCD
-// LCD
-TextLCD_I2C_N lcd0(&i2c, 0x7c, TextLCD::LCD16x2); // LCD(Akizuki AQM0802A)
-#endif
+// Analog
+AnalogIn adc0(A0); // Connect TL431ACZ-AP
+AnalogIn adc1(A1);
+AnalogIn adc2(A2);
+AnalogIn adc3(A3);
+AnalogIn adc4(A4);
+AnalogIn adc5(A5);
+// timer
+Timer timer;
// RAM -------------------------------------------------------------------------------------------
-float fa[3]; // Acc 0:X, 1:Y, 2:Z
-float fg[3]; // Gyro 0:X, 1:Y, 2:Z
+static char linebuf[64];
+
+typedef struct {
+ float adc0;
+ float adc1;
+ float adc2;
+ float adc3;
+ float adc4;
+ float adc5;
+ int a0_time;
+ int a1_time;
+ int a2_time;
+ int a3_time;
+ int a4_time;
+ int a5_time;
+ uint32_t n;
+} ADC_DataTypeDef;
-uint8_t show_flag;
-uint32_t count;
+ADC_DataTypeDef data_buffer[ADC_BUF_SIZE];
+
+// avarage & max.min
+uint32_t d_max_min[2];
+
+double ave_adc0;
+double ave_adc1;
+double ave_adc2;
+double ave_adc3;
+double ave_adc4;
+double ave_adc5;
+float d_max_min0[2];
+float d_max_min1[2];
+float d_max_min2[2];
+float d_max_min3[2];
+float d_max_min4[2];
+float d_max_min5[2];
// ROM / Constant data ---------------------------------------------------------------------------
+#if defined(TARGET_RZ_A1H)
+static char *const mon_msg = "ADC checking program for GR-PEACH mbed, created on "__DATE__"";
+#elif defined(TARGET_NUCLEO_F401RE) || defined(TARGET_NUCLEO_F411RE)
+static char *const mon_msg = "ADC checking program for Nucleo mbed, created on "__DATE__"";
+#elif defined(TARGET_K64F)
+static char *const mon_msg = "ADC checking program for K64F mbed, created on "__DATE__"";
+#endif
// Function prototypes ---------------------------------------------------------------------------
// Function prototypes ---------------------------------------------------------------------------
+void msg_hlp (void);
+void reset_max_min(uint32_t *bf);
+void check_max_min(uint32_t dt, uint32_t *bf);
+void reset_f_max_min(void);
+void check_f_max_min(float dt, float *bf);
+void get_line (char *buff, int len);
+void blink(void const *n);
+void put_rn ( void );
+void put_r ( void );
+int xatoi (char **str, int32_t *res);
//-------------------------------------------------------------------------------------------------
// Control Program
//-------------------------------------------------------------------------------------------------
-void blink(void const *n) {
- LEDs[(int)n] = !LEDs[(int)n];
-}
+int main(void)
+{
+ char *ptr;
+ float dt;
+ uint32_t i;
+ uint32_t t;
+
+ BAUD(9600);
+ put_rn();
+ put_rn();
+ PRINTF("%s [Help:'?' key]", mon_msg);
+ put_rn();
+ for (;;) {
+ put_r();
+ PUTC('>');
+ ptr = linebuf;
+ get_line(ptr, sizeof(linebuf));
+ switch (*ptr++) {
+ //---------------------------------------------------------------------------------------------
+ // Save ADC data into RAM
+ //---------------------------------------------------------------------------------------------
+ case 's' :
+ for (i = 0; i < ADC_BUF_SIZE; i++) {
+ timer.reset();
+ timer.start();
+ dt = adc0.read();
+ t = timer.read_us();
+ data_buffer[i].adc0 = dt;
+ data_buffer[i].a0_time = t;
-// Read switch status
-int read_sw(uint8_t n){
- if (USER_SWITCH[n] == 0){ return 1;
- } else { return 0;}
-}
+ timer.reset();
+ timer.start();
+ dt = adc1.read();
+ t = timer.read_us();
+ data_buffer[i].adc1 = dt;
+ data_buffer[i].a1_time = t;
+
+ timer.reset();
+ timer.start();
+ dt = adc2.read();
+ t = timer.read_us();
+ data_buffer[i].adc2 = dt;
+ data_buffer[i].a2_time = t;
+
+ timer.reset();
+ timer.start();
+ dt = adc3.read();
+ t = timer.read_us();
+ data_buffer[i].adc3 = dt;
+ data_buffer[i].a3_time = t;
+
+ timer.reset();
+ timer.start();
+ dt =adc4.read();
+ t = timer.read_us();
+ data_buffer[i].adc4 = dt;
+ data_buffer[i].a4_time = t;
+
+ timer.reset();
+ dt = adc5.read();
+ t = timer.read_us();
+ data_buffer[i].adc5 = dt;
+ data_buffer[i].a5_time = t;
-// Update sensor data
-void update_angle(void){
-#ifdef USE_I2C_SENSOR
- // read acceleration data from sensor
- acc.read_data(fa);
- // read gyroscope data from sensor
- gyro.read_data(fg);
-#else
- fa[0] = fa[1] = fa[2] = 1.11f;
- fg[0] = fg[1] = fg[2] = 1.11f;
-#endif
+ data_buffer[i].n = i + 1;
+ if (i%100 == 0) {
+ put_rn();
+ PRINTF("%d", i);
+ put_rn();
+ } else {
+ PUTC('.');
+ }
+ if ( READABLE() ) {
+ put_rn();
+ GETC();
+ break;
+ }
+ }
+ data_buffer[i + 1].n = 0;
+ put_rn();
+ PRINTF("Finished at %d", i);
+ put_rn();
+ break;
+ //---------------------------------------------------------------------------------------------
+ // Display saved ADC data
+ //---------------------------------------------------------------------------------------------
+ case 'd' :
+ put_rn();
+ PRINTF("Show all saved data");
+ put_rn();
+ for (i = 0; (i < ADC_BUF_SIZE) && (data_buffer[i].n != 0) ; i++) {
+ PRINTF("No.%5d, ", i);
+ PRINTF("A0= %4.4f , A1= %4.4f , ", data_buffer[i].adc0, data_buffer[i].adc1);
+ PRINTF("A2= %4.4f , A3= %4.4f , ", data_buffer[i].adc2, data_buffer[i].adc3);
+ PRINTF("A4= %4.4f , A5= %4.4f , ", data_buffer[i].adc4, data_buffer[i].adc5);
+ PRINTF("Time/0= %d /1= %d /2= %d /3= %d /4= %d /5= %d [uS]",
+ data_buffer[i].a0_time, data_buffer[i].a1_time, data_buffer[i].a2_time,
+ data_buffer[i].a3_time, data_buffer[i].a4_time, data_buffer[i].a5_time);
+ put_rn();
+ if ( READABLE() ) {
+ GETC();
+ break;
+ }
+ }
+ break;
+ //---------------------------------------------------------------------------------------------
+ // Check convertion time
+ //---------------------------------------------------------------------------------------------
+ case 't' :
+ uint32_t time_all = 0;
+
+ put_r();
+ reset_max_min(d_max_min);
+ for (i = 0; (i < ADC_BUF_SIZE) && (data_buffer[i].n != 0) ; i++) {
+ time_all += (data_buffer[i].a0_time + data_buffer[i].a1_time +data_buffer[i].a2_time
+ + data_buffer[i].a3_time + data_buffer[i].a4_time + data_buffer[i].a5_time);
+ check_max_min(data_buffer[i].a0_time, d_max_min);
+ check_max_min(data_buffer[i].a1_time, d_max_min);
+ check_max_min(data_buffer[i].a2_time, d_max_min);
+ check_max_min(data_buffer[i].a3_time, d_max_min);
+ check_max_min(data_buffer[i].a4_time, d_max_min);
+ check_max_min(data_buffer[i].a5_time, d_max_min);
+ }
+ PRINTF("Conversion time/ave = %f [uS], Number of sample %d, Max %d [uS], Min %d [uS]",
+ (double)time_all / (i * 6), i, d_max_min[1], d_max_min[0]);
+ put_rn();
+ break;
+ //---------------------------------------------------------------------------------------------
+ // Analysis saved data
+ //---------------------------------------------------------------------------------------------
+ case 'a' :
+ put_r();
+ reset_f_max_min();
+ for (i = 0; (i < ADC_BUF_SIZE) && (data_buffer[i].n != 0) ; i++) {
+ ave_adc0 += data_buffer[i].adc0;
+ ave_adc1 += data_buffer[i].adc1;
+ ave_adc2 += data_buffer[i].adc2;
+ ave_adc3 += data_buffer[i].adc3;
+ ave_adc4 += data_buffer[i].adc4;
+ ave_adc5 += data_buffer[i].adc5;
+ check_f_max_min(data_buffer[i].adc0, d_max_min0);
+ check_f_max_min(data_buffer[i].adc1, d_max_min1);
+ check_f_max_min(data_buffer[i].adc2, d_max_min2);
+ check_f_max_min(data_buffer[i].adc3, d_max_min3);
+ check_f_max_min(data_buffer[i].adc4, d_max_min4);
+ check_f_max_min(data_buffer[i].adc5, d_max_min5);
+ }
+ PRINTF("Number of sample %d", i);
+ put_rn();
+ PRINTF("ADC0/ave = %f , Max %f , Min %f , Dif %f",
+ ave_adc0 / i, d_max_min0[1], d_max_min0[0], d_max_min0[1] - d_max_min0[0]);
+ put_rn();
+ PRINTF("ADC1/ave = %f , Max %f , Min %f , Dif %f",
+ ave_adc1 / i, d_max_min1[1], d_max_min1[0], d_max_min1[1] - d_max_min1[0]);
+ put_rn();
+ PRINTF("ADC2/ave = %f , Max %f , Min %f , Dif %f",
+ ave_adc2 / i, d_max_min2[1], d_max_min2[0], d_max_min2[1] - d_max_min2[0]);
+ put_rn();
+ PRINTF("ADC3/ave = %f , Max %f , Min %f , Dif %f",
+ ave_adc3 / i, d_max_min3[1], d_max_min3[0], d_max_min3[1] - d_max_min3[0]);
+ put_rn();
+ PRINTF("ADC4/ave = %f , Max %f , Min %f , Dif %f",
+ ave_adc4 / i, d_max_min4[1], d_max_min4[0], d_max_min4[1] - d_max_min4[0]);
+ put_rn();
+ PRINTF("ADC5/ave = %f , Max %f , Min %f , Dif %f",
+ ave_adc5 / i, d_max_min5[1], d_max_min5[0], d_max_min5[1] - d_max_min5[0]);
+ put_rn();
+ break;
+ //---------------------------------------------------------------------------------------------
+ // Buffer information
+ //---------------------------------------------------------------------------------------------
+ case 'b' :
+ put_r();
+ PRINTF("Buffer information", i);
+ put_rn();
+ PRINTF("Start address: 0x%08x", &data_buffer[0]);
+ put_rn();
+ PRINTF("End address: 0x%08x", &data_buffer[ADC_BUF_SIZE - 1]);
+ put_rn();
+ PRINTF("Size of Buf: %d (0x%x)", sizeof(data_buffer), sizeof(data_buffer));
+ put_rn();
+ break;
+ //---------------------------------------------------------------------------------------------
+ // Check Vcc
+ //---------------------------------------------------------------------------------------------
+ case 'v' :
+ put_r();
+ PRINTF("This is special function only if A0 conneceted 2.5V Shunt reg. e.g. TL431, NJM431.");
+ put_rn();
+ PRINTF("Please make sure #define VREF as your condition.");
+ put_rn();
+ while(true){
+ PRINTF("Vcc= %4.4f [v]", VREF / adc0.read());
+ put_rn();
+ if ( READABLE() ) {
+ GETC();
+ break;
+ }
+ wait(0.5);
+ }
+ break;
+ //---------------------------------------------------------------------------------------------
+ // help
+ //---------------------------------------------------------------------------------------------
+ case '?' :
+ put_r();
+ msg_hlp();
+ break;
+ }
+ }
}
-// Update sensor data
-void display(void){
-#ifdef USE_I2C_LCD
- lcd0.locate(0, 0); // 1st line top
- lcd0.printf(" G=%4.1f ", sqrt(fa[0]*fa[0] + fa[1]*fa[1] + fa[2]*fa[2]));
- lcd0.locate(0, 1); // 2nd line top
- lcd0.printf("%8d",count++);
-#endif
+// Help Massage
+void msg_hlp (void)
+{
+ PRINTF(mon_msg);
+ put_rn();
+ PRINTF("s - Save ADC data into RAM");
+ put_rn();
+ PRINTF("d - Display saved ADC data");
+ put_rn();
+ PRINTF("t - Check convertion time");
+ put_rn();
+ PRINTF("a - Analysis saved data");
+ put_rn();
+ PRINTF("b - Buffer information");
+ put_rn();
+ PRINTF("v - Check Vcc");
+ put_rn();
+}
+
+void reset_max_min(uint32_t *bf)
+{
+ *(bf + 1) = 0;
+ *bf = 0xffffffff;
}
-void send_pc(void){
- PRINTF("G:%+6.1f,%+6.1f,%+6.1f, ", fg[0], fg[1], fg[2]);
- PRINTF("A:%+6.1f,%+6.1f,%+6.1f \r\n", fa[0], fa[1], fa[2]);
+void check_max_min(uint32_t dt, uint32_t *bf)
+{
+ if (dt > *(bf + 1)){
+ *(bf + 1) = dt;
+ } else if (dt < *bf){
+ *bf = dt;
+ }
+}
+
+void reset_f_max_min(void)
+{
+ d_max_min0[0] = 1.0f;
+ d_max_min0[1] = 0.0f;
+ d_max_min1[0] = 1.0f;
+ d_max_min1[1] = 0.0f;
+ d_max_min2[0] = 1.0f;
+ d_max_min2[1] = 0.0f;
+ d_max_min3[0] = 1.0f;
+ d_max_min3[1] = 0.0f;
+ d_max_min4[0] = 1.0f;
+ d_max_min4[1] = 0.0f;
+ d_max_min5[0] = 1.0f;
+ d_max_min5[1] = 0.0f;
+}
+
+void check_f_max_min(float dt, float *bf)
+{
+ if (dt > *(bf + 1)){
+ *(bf + 1) = dt;
+ } else if (dt < *bf){
+ *bf = dt;
+ }
}
-int main(void) {
- // I2C LCD
-#ifdef USE_I2C_LCD
- lcd0.locate(0, 0); // 1st line top
- lcd0.printf("I2C test");
- lcd0.locate(0, 1); // 2nd line top
- lcd0.puts(" JH1PJL ");
- lcd0.setContrast(0x14);
-#endif
- count = 0;
- while (true) {
- update_angle();
- display();
- send_pc();
- //wait(0.2);
- blink((void *)0);
- //wait(0.2);
- blink((void *)1);
- //wait(0.2);
- blink((void *)2);
- //wait(0.2);
- blink((void *)3);
- //wait(0.2);
+///////////////////////////////////////////////////////////////////////////////////////////////////
+// Get key input data
+void get_line (char *buff, int len)
+{
+ char c;
+ int idx = 0;
+
+ for (;;) {
+ c = GETC();
+ // Added by Kenji Arai / JH1PJL May 9th, 2010
+ if (c == '\r') {
+ buff[idx++] = c;
+ break;
+ }
+ if ((c == '\b') && idx) {
+ idx--;
+ PUTC(c);
+ PUTC(' ');
+ PUTC(c);
+ }
+ if (((uint8_t)c >= ' ') && (idx < len - 1)) {
+ buff[idx++] = c;
+ PUTC(c);
+ }
}
+ buff[idx] = 0;
+ PUTC('\n');
}
+
+// Put \r\n
+void put_rn ( void )
+{
+ PUTC('\r');
+ PUTC('\n');
+}
+
+// Put \r
+void put_r ( void )
+{
+ PUTC('\r');
+}
+
+int xatoi (char **str, int32_t *res)
+{
+ unsigned long val;
+ unsigned char c, radix, s = 0;
+
+ while ((c = **str) == ' ') (*str)++;
+ if (c == '-') {
+ s = 1;
+ c = *(++(*str));
+ }
+ if (c == '0') {
+ c = *(++(*str));
+ if (c <= ' ') {
+ *res = 0;
+ return 1;
+ }
+ if (c == 'x') {
+ radix = 16;
+ c = *(++(*str));
+ } else {
+ if (c == 'b') {
+ radix = 2;
+ c = *(++(*str));
+ } else {
+ if ((c >= '0')&&(c <= '9')) {
+ radix = 8;
+ } else {
+ return 0;
+ }
+ }
+ }
+ } else {
+ if ((c < '1')||(c > '9')) {
+ return 0;
+ }
+ radix = 10;
+ }
+ val = 0;
+ while (c > ' ') {
+ if (c >= 'a') c -= 0x20;
+ c -= '0';
+ if (c >= 17) {
+ c -= 7;
+ if (c <= 9) return 0;
+ }
+ if (c >= radix) return 0;
+ val = val * radix + c;
+ c = *(++(*str));
+ }
+ if (s) val = -val;
+ *res = val;
+ return 1;
+}
