Trackball based on the NXP LPC11U24 and the ADNS-9500
Dependencies: ADNS9500 USBDevice mbed 25LCxxx_SPI
Revision 8:5674f5ab61cd, committed 2013-03-14
- Comitter:
- xxann5
- Date:
- Thu Mar 14 13:48:14 2013 +0000
- Parent:
- 7:d6ee49a89009
- Child:
- 9:ee05aa95f5c9
- Commit message:
- * support for 4th and 5th buttons.; * support for horizontal scrolling.; * support for 16bit x and y coordinates.; * added dispatch table for buttons. They are now programmable.; * support for programming the eeprom
Changed in this revision
--- a/25LCxxx_SPI.lib Mon Jan 14 04:27:55 2013 +0000 +++ b/25LCxxx_SPI.lib Thu Mar 14 13:48:14 2013 +0000 @@ -1,1 +1,1 @@ -http://mbed.org/users/hlipka/code/25LCxxx_SPI/#d9429070ea6f +http://mbed.org/users/xxann5/code/25LCxxx_SPI/#0c31e878a076
--- a/ADNS9500.lib Mon Jan 14 04:27:55 2013 +0000 +++ b/ADNS9500.lib Thu Mar 14 13:48:14 2013 +0000 @@ -1,1 +1,1 @@ -http://mbed.org/users/xxann5/code/ADNS9500/#de76a70defb3 +http://mbed.org/users/xxann5/code/ADNS9500/#af2fb65ee807
--- a/PinDetect.lib Mon Jan 14 04:27:55 2013 +0000 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,1 +0,0 @@ -http://mbed.org/users/AjK/code/PinDetect/#cb3afc45028b
--- a/USBDevice.lib Mon Jan 14 04:27:55 2013 +0000 +++ b/USBDevice.lib Thu Mar 14 13:48:14 2013 +0000 @@ -1,1 +1,1 @@ -http://mbed.org/users/xxann5/code/USBDevice/#01e3466e25ff +https://mbed.org/users/mbed_official/code/USBDevice/#4f27799a971d
--- a/main.cpp Mon Jan 14 04:27:55 2013 +0000 +++ b/main.cpp Thu Mar 14 13:48:14 2013 +0000 @@ -1,215 +1,463 @@ -/* Copyright (c) 2012-2013 Chris Majoros(chris@majoros.us), MIT License -* -* Permission is hereby granted, free of charge, to any person obtaining a copy of this software -* and associated documentation files (the "Software"), to deal in the Software without -* restriction, including without limitation the rights to use, copy, modify, merge, publish, -* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the -* Software is furnished to do so, subject to the following conditions: -* -* The above copyright notice and this permission notice shall be included in all copies or -* substantial portions of the Software. -* -* 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 AND -* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, -* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, -* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. -*/ +/* + * loststone is free sofware: you can redistribute it and/or modify + * it under the terms of the GNU General Public License 3 as published by + * the Free Software Foundation. + * + * loststone is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with loststone. If not, see <http://www.gnu.org/licenses/gpl.txt>. + * + * Copyright (c) 2012-2013 Chris Majoros(chris@majoros.us), GNU3 + */ #include "main.h" -DigitalOut myled(p15); int main(void) { + + printf("And away we go.\n\r"); + activity = 1; + run_mode.mode(PullUp); + Ser25LCxxx *eeprom; + + #ifdef MBED + SPI eeprom_spi( p11, p12, p13); // mosi, miso, sclk + #elif + SPI eeprom_spi( P0_21, P0_22, P1_20); // mosi, miso, sclk + #endif + + eeprom_spi.format(8,3); + eeprom_spi.frequency(1000000); + + #ifdef MBED + eeprom = new Ser25LCxxx( &eeprom_spi, p15, 0x10000, 0x20 ); + #elif + eeprom = new Ser25LCxxx( &eeprom_spi, P1_27, 0x10000, 0x20 ); + #endif - printf( "Hi i just started running\n\r"); - uint8_t o; - uint8_t i; - MOUSE_TYPE mtype; - - if( btn_program ){ - mtype = RAW; - o = 64; - i = 64; + //retreave default and system settings from the EEPROM and override the default values. + printf("Loading settings\n\r"); + for( int i = 0; i < sizeof(s)/sizeof(uint16_t); i++ ){ + printf("Setting %d: %X\r\n", i, s[i]); + //set_setting( eeprom, i, s[i], SETTINGS_BASE ); + //s[i] = get_setting( eeprom, i, SETTINGS_BASE ); + printf("Setting %d: %X\r\n", i, s[i]); + } + + //eeprom->write( s[ADNS_FW_OFFSET], ADNS9500_FIRMWARE_LEN, adns9500FWArray ); + + if( run_mode ){ + printf("Tracking mode\n\r"); + track( eeprom ); } else{ - mtype = REL_MOUSE; - o = 0; - i = 0; + printf("Programming mode\n\r"); + program( eeprom ); } - - // TODO switch to P#_# - SPI eeprom_spi( p11, p12, p13); // mosi, miso, sclk - eeprom_spi.format(8,3); - eeprom_spi.frequency(1000000); - Ser25LCxxx eeprom( &eeprom_spi, p14, 0x10000, 0x20 ); - - //Retreave settings from the EEPROM and override the default values. - for( int i = 0; i < sizeof(s)/sizeof(uint16_t); i++ ){ - s[i] = get_setting( &eeprom, i ); - printf( "Setting %02d: %d\r\n", i, s[i]); - } - - - //if( mtype == RAW ){ - // program(); - //} - //else{ - // track(); - //} } void track( Ser25LCxxx *eeprom ){ + activity = 0; /* * mosi miso sclk ncs FREQ, motion */ - sensor = new adns9500::ADNS9500(p5, p6, p7, p8, adns9500::MAX_SPI_FREQUENCY, p21); - - send_rep.length = 8; + mouse = new USBMouse( REL_MOUSE, s[VID], s[PID], s[RELEASE]) ; + + /* + * mosi == p5 / P0_9 + * miso == p6 / P0_8 + * sclk == p7 / P0_10 + * ncs == p8 / P1_16 + * spi_frequency = MAX_SPI_FREQUENCY + * motion == p14 / P0_22 + */ + + printf("Creating sensor object\n\r"); + #ifdef MBED + adns9500::ADNS9500 sensor(p5, p6, p7, p8, adns9500::MAX_SPI_FREQUENCY); + #elif + adns9500::ADNS9500 sensor(P0_9, P0_8, P0_10, P1_16, adns9500::MAX_SPI_FREQUENCY); + #endif - btn_hr.mode(PullUp); - btn_hr.attach_asserted(&btn_hr_press); - btn_hr.attach_deasserted(&btn_hr_release); - btn_hr.setSampleFrequency(); + static fn press_funcs[] = { + btn_l_press, + btn_m_press, + btn_r_press, + btn_f_press, + btn_b_press, + btn_z_press, + btn_hr_press}; + + static fn release_funcs[] = { + btn_l_release, + btn_m_release, + btn_r_release, + btn_f_release, + btn_b_release, + btn_z_release, + btn_hr_release}; + + printf("Inisializing buttons\n\r"); - btn_z.mode(PullUp); - btn_z.attach_asserted(&btn_z_press); - btn_z.attach_deasserted(&btn_z_release); - btn_z.setSampleFrequency(); -/* - btn_l.mode(PullUp); - btn_l.attach_asserted(&btn_l_press); - btn_l.attach_deasserted(&btn_l_release); - btn_l.setSampleFrequency(); -*/ - btn_m.mode(PullUp); - btn_m.attach_asserted(&btn_m_press); - btn_m.attach_deasserted(&btn_m_release); - btn_m.setSampleFrequency(); +// Mouse buttons + btn_a.mode(PullNone); + btn_a.fall(press_funcs[s[BTN_A]]); + btn_a.rise(release_funcs[s[BTN_A]]); + + btn_b.mode(PullNone); + btn_b.fall(press_funcs[s[BTN_B]]); + btn_b.rise(release_funcs[s[BTN_B]]); - btn_r.mode(PullUp); - btn_r.attach_asserted(&btn_r_press); - btn_r.attach_deasserted(&btn_r_release); - btn_r.setSampleFrequency(); - //btn_r.setAssertValue( 0 ); - //btn_r.setSamplesTillAssert( 5 ); + btn_c.mode(PullNone); + btn_c.fall(press_funcs[s[BTN_C]]); + btn_c.rise(release_funcs[s[BTN_C]]); + + btn_d.mode(PullNone); + btn_d.fall(press_funcs[s[BTN_D]]); + btn_d.rise(release_funcs[s[BTN_D]]); + + btn_e.mode(PullNone); + btn_e.fall(press_funcs[s[BTN_E]]); + btn_e.rise(release_funcs[s[BTN_E]]); - int dx, dy; + btn_f.mode(PullNone); + btn_f.fall(press_funcs[s[BTN_F]]); + btn_f.rise(release_funcs[s[BTN_F]]); + + btn_g.mode(PullNone); + btn_g.fall(press_funcs[s[BTN_G]]); + btn_g.rise(release_funcs[s[BTN_G]]); - sensor->attach(&motionCallback); +// Profile buttons + prfl_a.mode(PullUp); + prfl_a.fall(&prfl_a_set); + prfl_a.rise(&prfl_stub); - sensor->reset(); + prfl_b.mode(PullUp); + prfl_b.fall(&prfl_b_set); + prfl_b.rise(&prfl_stub); + + prfl_c.mode(PullUp); + prfl_c.fall(&prfl_c_set); + prfl_c.rise(&prfl_stub); - //Retreave adns meta data from the EEPROM and override the default values. - for( int i = 0; i < sizeof(a)/sizeof(uint16_t); i++ ){ - a[i] = get_adns_meta( eeprom, i ); - printf( "ADNS Meta %02d: %d\r\n", i, s[i]); - } + prfl_d.mode(PullUp); + prfl_d.fall(&prfl_d_set); + prfl_d.rise(&prfl_stub); - uint8_t *adns_fw; - adns_fw = get_adns_firmware( eeprom, 0, ADNS_FW_LEN ); + prfl_e.mode(PullUp); + prfl_e.fall(&prfl_e_set); + prfl_e.rise(&prfl_stub); + + debug.mode(PullUp); + debug.fall(&debug_out); + debug.rise(&debug_out); - // We are now does with the eeprom - delete eeprom; - - uint16_t crc = sensor->sromDownload( adns_fw, a[ADNS_FW_LEN] ); - - if( a[ADNS_CRC] != crc ) - { - error( "CRC does not match: [%x] [%x], Exiting.\r\n", a[ADNS_CRC], crc ); + int16_t dx, dy; + float mx, my; + + sensor.reset(); + + uint8_t *adns_fw; + + //eeprom->write(ADNS_FW_OFFSET, ADNS_FW_LEN, adns9500FWArray); + //adns_fw = eeprom->read( ADNS_FW_OFFSET, ADNS_FW_LEN ); +//eeprom->write( s[ADNS_FW_OFFSET], ADNS9500_FIRMWARE_LEN, adns9500FWArray ); + + activity = 1; + printf("Loading sensor firmware\r\n"); + uint16_t crc = sensor.sromDownload( adns9500FWArray, ADNS9500_FIRMWARE_LEN ); //FIXME + + if( ADNS6010_FIRMWARE_CRC != crc ){ //ADNS6010_FIRMWARE_CRC + printf("Firmware CRC does not match [%X] [%X]\n\r", + ADNS6010_FIRMWARE_CRC, + crc); + while (true){ + activity = 0; + wait(0.2); + activity = 1; + wait(0.2); + } } - + else{ + activity = 0; + printf("Firmware CRC matches [%X] [%X]\n\r", + ADNS6010_FIRMWARE_CRC, + crc); + } + // The firmware was set correctly. Freeing the 3K! of ram. - delete adns_fw; + //delete adns_fw; + + printf("Enableing lazer\n\r"); + sensor.enableLaser(); + sensor.setResolution( s[CPI_X], s[CPI_Y] ); - sensor->enableLaser(); - - sensor->setResolution( s[CPI_DEFAULT] ); - int btn_l_avg = 0; - DigitalOut myled(P0_7); + printf("Starting Loop\n\r"); + activity = 1; + //rest_counter = 0; while (true){ - - + //rest_counter++; + /* + * Moved the setResolution calls out of the interupt callbacks as they + * havequite a few waits in them. I am hopping this is the reasion why + * the hr and z buttons on occation stick or don't work the first time + * you press them. + */ + if( set_res_hr ){ + printf("Setting High hez\n\r"); + set_res_hr = false; + sensor.setResolution( s[CPI_HR_X], s[CPI_HR_Y] ); + } - btn_l_avg=(btn_l_avg * 9 + btn_l * 10)/10; - if (btn_l_avg > 5){ - btn_l_press(); + if( set_res_z ){ + printf("Setting Z rez\n\r"); + set_res_z = false; + sensor.setResolution( s[CPI_Z], s[CPI_H] ); } - else{ - btn_l_release(); + + if( set_res_default ){ + printf("Setting default rez\n\r"); + set_res_default = false; + sensor.setResolution( s[CPI_X], s[CPI_Y] ); } - - - if( motion_triggered ){ + + if( !motion_in){ motion_triggered = false; - sensor->getMotionDelta(dx, dy); - + sensor.getMotionDelta(dx, dy); + if( dx == 0 and dy == 0 ){ + // FIXME: why is the ADNS9500 dropping the motion pin and then + // giving me no motion? Do I have somthing wired up wrong? + continue; + } /* - * The sensor does not know its upside down and backwords - * so we are helping it out with the y axis. + * The sensor is not aware of its orientation so we need to muck + * with the values a it. */ if( z_axis_active ){ - mouse->scroll( - dy ); + printf("scroll,%X,%X,\n\r", -dx, dy); + mouse->scroll( dy, - dx ); } else{ - mouse->move( dx, - dy ); + + mx = (float(abs(dx))/float(s[CPI_X_MULITIPLYER]) + 1.0); + my = (float(abs(dy))/float(s[CPI_Y_MULITIPLYER]) + 1.0); + + printf("motion,%X,%X %.4f,%.4f %X,%X\n\r", -dx, dy, mx, my, int(- (dx * mx)), int(dy * my) ); + + mouse->move( - (dx * mx), (dy * my) ); + //printf("rest_coutner,%d\n\r", rest_counter); + //rest_counter = 0; + } + } + + + // Load the current profile. + // This rights the first 10 16bit values of the s array from the selected profile. + // + // Base is calculated... + // selected profile * profile length * 2 + profile base + // + // (3 * 7 * 2) + 64 (multiplying by two because they are 16bit values. + // TODO: should i move this to a function? + if( profile_load ){ + // for( int i = 0; i < PROFILE_LEN; i++ ){ + // //s[i] = get_setting( eeprom, i, (s[PROFILE_CURRENT] * PROFILE_LEN) + PROFILE_BASE ); + // } + // sensor.setResolution( s[CPI_X], s[CPI_Y] ); + profile_load = false; + } + } +} + +void program( Ser25LCxxx *eeprom ){ + + + //USBHID *hid = new USBHID( 64, 64, 0x192f, 0x0, 0x0); + USBHID *hid = new USBHID(); + //This report will contain data to be sent + HID_REPORT send_rep; + HID_REPORT recv_rep; + + send_rep.length = 64; + uint16_t base; + uint16_t len; + //Fill the report + for (int i = 0; i < send_rep.length; i++) { + send_rep.data[i] = rand() & 0xff; + } + + //Send the report + //hid->send(&send_rep); + + uint8_t *tmp; + + printf("Entering loop\n\r"); + while (1) { + if( hid->readNB(&recv_rep)) { + printf("Receaved some data.\n\r"); + switch ((recv_rep.data[0])){ + case SET: + //set_setting( eeprom, recv_rep.data[1], UINT16(recv_rep.data[2],recv_rep.data[3])); + break; + case GET: + //tmp = get_setting( eeprom, recv_rep.data[1] ); + + //send_rep.data[0] = (int)tmp; + //send_rep.data[1] = (int)(tmp >> 8); + + //hid->send(&send_rep); + + break; + case CLEAR: + //clear_setting( eeprom, recv_rep.data[1] ); + break; + case INIT: + eeprom->clearMem(); + break; + case LOAD_DATA: + printf("LOADING DATA\n\r"); + base = UINT16( recv_rep.data[1], recv_rep.data[2] ); + len = recv_rep.data[3]; + printf("BASE: %X LEN: %X\n\r", base, len); + load_data( eeprom, base, len, &recv_rep.data[4] ); + wait(0.1); + tmp = get_data( eeprom, base, len ); + printf("BASE: %X LEN: %X\n\r", base, len); + for( uint16_t i=0; i < (len); i++){ + printf("%X\n\r", tmp[i]); + send_rep.data[i] = tmp[i]; //FIXME + } + hid->send(&send_rep); + delete( tmp); + break; + case GET_DATA: + //base = UINT16( recv_rep.data[1], recv_rep.data[2] ); + //len = UINT16( recv_rep.data[3], recv_rep.data[4] ); + //tmp = get_data( Ser25LCxxx *eeprom, uint16_t base, uint16_t len ){ + default: + // FIXME: error handling. + break; } } } } -void program(){ - - // We are now does with the eeprom - //delete eeprom; -} - -void motionCallback(){ - motion_triggered = true; -} - -void btn_hr_press(){ - high_rez_active = true; - sensor->setResolution( s[CPI_HR_DEFAULT] ); -} -void btn_hr_release(){ - high_rez_active = false; - sensor->setResolution( s[CPI_DEFAULT] ); -} - -void btn_z_press(){ - z_axis_active = true; - sensor->setResolution( s[CPI_Z_DEFAULT] ); -} -void btn_z_release(){ - z_axis_active = false; - sensor->setResolution( s[CPI_DEFAULT] ); -} - void btn_l_press(){ + printf("button,left,press\n\r"); mouse->press(MOUSE_LEFT); } void btn_l_release(){ + printf("button,left,release\n\r"); mouse->release(MOUSE_LEFT); } void btn_m_press(){ - mouse->press(MOUSE_MIDDLE); + //mouse->press(MOUSE_MIDDLE); } void btn_m_release(){ - mouse->release(MOUSE_MIDDLE); + //mouse->release(MOUSE_MIDDLE); } void btn_r_press(){ + printf("button,right,press\n\r"); mouse->press(MOUSE_RIGHT); } + void btn_r_release(){ + printf("button,right,release\n\r"); mouse->release(MOUSE_RIGHT); } +void btn_f_press(){ + printf("button,forword,press\n\r"); + mouse->press(MOUSE_FORWORD); +} +void btn_f_release(){ + printf("button,forword,release\n\r"); + mouse->release(MOUSE_FORWORD); +} + +void btn_b_press(){ + printf("button,back,press\n\r"); + mouse->press(MOUSE_BACK); +} + +void btn_b_release(){ + printf("button,back,release\n\r"); + mouse->release(MOUSE_BACK); +} + +void btn_hr_press(){ + printf("button,high_res,press\n\r"); + set_res_hr = true; + set_res_default = false; + high_rez_active = true; +} +void btn_hr_release(){ + printf("button,high_res,release\n\r"); + set_res_hr = false; + set_res_default = true; + high_rez_active = false; +} + +void btn_z_press(){ + printf("button,z,press\n\r"); + set_res_z = true; + set_res_default = false; + z_axis_active = true; +} +void btn_z_release(){ + printf("button,z,release\n\r"); + set_res_z = false; + set_res_default = true; + z_axis_active = false; +} + +void prfl_a_set(){ + s[PROFILE_CURRENT] = 0; + profile_load = true; +} + +void prfl_b_set(){ + s[PROFILE_CURRENT] = 1; + profile_load = true; +} + +void prfl_c_set(){ + s[PROFILE_CURRENT] = 2; + profile_load = true; +} + +void prfl_d_set(){ + s[PROFILE_CURRENT] = 3; + profile_load = true; +} + +void prfl_e_set(){ + s[PROFILE_CURRENT] = 4; + profile_load = true; +} + +void prfl_stub(){ +} + +void debug_out(){ +printf("motion_triggerd %d\n\r" , motion_triggered); +printf("z_axis_active %d\n\r", z_axis_active); +printf("high_rez_active %d\n\r", high_rez_active); +printf("profile_load %d\n\r", profile_load); // Always inishally load the profile even if it might be the same. +printf("set_res_hr %d\n\r", set_res_hr); +printf("set_res_z %d\n\r" , set_res_z); +printf("set_res_default %d\n\r", set_res_default); +} /* * The settings are kept in the first 'N' addresses of the of the EEPROM. @@ -220,24 +468,29 @@ */ -void set_setting( Ser25LCxxx *eeprom, uint16_t attrib, uint16_t val ){ +int set_setting( Ser25LCxxx *eeprom, uint16_t attrib, uint16_t val, uint16_t base_address ){ - int hl[2]; + uint8_t hl[2]; // TODO: Its working but is it working the way i think its working hl[0] = (int)val; hl[1] = (int)(val >> 8); + + printf("Set Setting %d: L[%X] H[%X]\n\r", attrib, hl[0], hl[1] ); - eeprom->write( attrib * 2, 0x2, hl ); - + if ( eeprom->write( attrib * 2, 0x2, hl )){ + return true; + } + return false; } -uint16_t get_setting( Ser25LCxxx *eeprom, uint16_t attrib ){ +uint16_t get_setting( Ser25LCxxx *eeprom, uint16_t attrib, uint16_t base_address ){ uint16_t val; - int *hl; + uint8_t *hl; - hl = eeprom->read( (attrib * 2), 0x2 ); + hl = eeprom->read( (attrib * 2) + base_address, 0x2 ); + printf("Get Setting %d: L[%X] H[%X]\n\r", attrib, hl[0], hl[1] ); val = UINT16( hl[1], hl[0] ); if( val != 0xFFFF ){ return val; @@ -246,43 +499,20 @@ return s[attrib]; } -void clear_setting( Ser25LCxxx *eeprom, uint16_t attrib ){ - int val[2]; +void clear_setting( Ser25LCxxx *eeprom, uint16_t attrib, uint16_t base_address ){ + uint8_t val[2]; val[0] = val[1] = 0xFF; - eeprom->write( (attrib * 2) , 0x2, val ); + eeprom->write( (attrib * 2) + base_address , 0x2, val ); } + /* * Getting and setting the firmware is a bit easer as it is all 8bit. */ -void set_adns_firmware( Ser25LCxxx *eeprom, uint16_t offset, uint16_t len, uint8_t* val ){ - eeprom->write( (ADNS_FW_OFFSET + offset) , len, (int*)val ); -} - -uint8_t* get_adns_firmware( Ser25LCxxx *eeprom, uint16_t offset, uint16_t len ){ - return (uint8_t*)eeprom->read( (ADNS_FW_OFFSET + offset), len ); +void load_data( Ser25LCxxx *eeprom, uint16_t base, uint16_t len, const uint8_t* data ){ + eeprom->write( base , len, data ); } -/* - * Same deal as the trackball settings. - */ - -void set_adns_meta( Ser25LCxxx *eeprom, uint16_t attrib, uint16_t val ){ - - int hl[2]; - - // TODO: Its working but is it working the way i think its working - hl[0] = (int)val; - hl[1] = (int)(val >> 8); - - eeprom->write( (ADNS_META_OFFSET + (attrib * 2 )), 0x2, hl ); -} - -uint16_t get_adns_meta( Ser25LCxxx *eeprom, uint16_t attrib ){ - uint16_t val; - int *hl; - - hl = eeprom->read( (ADNS_META_OFFSET + (attrib * 2 )), 0x2 ); - val = UINT16( hl[1], hl[0] ); - return val; +uint8_t* get_data( Ser25LCxxx *eeprom, uint16_t base, uint16_t len ){ + return (uint8_t*)eeprom->read( base, len ); } \ No newline at end of file
--- a/main.h Mon Jan 14 04:27:55 2013 +0000 +++ b/main.h Thu Mar 14 13:48:14 2013 +0000 @@ -1,111 +1,202 @@ -/* Copyright (c) 2012-2013 Chris Majoros(chris@majoros.us), MIT License -* -* Permission is hereby granted, free of charge, to any person obtaining a copy of this software -* and associated documentation files (the "Software"), to deal in the Software without -* restriction, including without limitation the rights to use, copy, modify, merge, publish, -* distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the -* Software is furnished to do so, subject to the following conditions: -* -* The above copyright notice and this permission notice shall be included in all copies or -* substantial portions of the Software. -* -* 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 AND -* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, -* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, -* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. -*/ +/* + * loststone is free sofware: you can redistribute it and/or modify + * it under the terms of the GNU General Public License 3 as published by + * the Free Software Foundation. + * + * loststone is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with loststone. If not, see <http://www.gnu.org/licenses/gpl.txt>. + * + * Copyright (c) 2012-2013 Chris Majoros(chris@majoros.us), GNU3 + */ #include "mbed.h" #include "USBHID.h" #include "USBMouse.h" - -#include <math.h> -#include <stdint.h> - - -#define PINDETECT_PIN_ASSTERED 0 //setAssertValue -#define PINDETECT_SAMPLE_PERIOD 100 //setSampleFrequency -#define PINDETECT_ASSERT_COUNT 10 //setSamplesTillAssert -#define PINDETECT_HOLD_COUNT 500 - -#include "PinDetect.h" - -#define ADNS9500_SROM_91 - -#define DEBUG - -#include "adns9500.hpp" #include "Ser25lcxxx.h" -enum cli_actions { - SET = 0x01, - GET = 0x02, - CLEAR = 0x03, - INIT = 0x04, -}; +#include <stdint.h> -enum settings { - CPI_DEFAULT = 0x00, - CPI_MAX = 0x01, - CPI_MIN = 0x02, - CPI_STEP = 0x03, - CPI_Z_DEFAULT = 0x04, - CPI_HR_DEFAULT = 0x05, - - VID = 0x06, - PID = 0x07, +#define ADNS9500_SROM_91 +#define ADNS9500_CRCHI (0xBE) +#define ADNS9500_CRCLO (0xEF) +#define ADNS9500_ID (0x56) +#define ADNS6010_FIRMWARE_CRC (0xBEEF) +#define ADNS9500_FIRMWARE_LEN 3070 - LED_SHOW = 0x08, - SETTINGS_OFFSET = 0x00 -}; +#include "adns9500.hpp" -enum ands_meta { - ADNS_CRC = 0x0, - ADNS_ID = 0x1, - ADNS_FW_LEN = 0x2, - ADNS_FW_OFFSET = 0xF000, - ADNS_META_OFFSET = 0xEFF0 -}; #define UINT16(ub, lb) (uint16_t)(((ub & 0xff) << 8) | (lb & 0xff)) #define INT16(ub, lb) (int16_t)(((ub & 0xff) << 8) | (lb & 0xff)) - -//This report will contain data to be sent -HID_REPORT send_rep; -HID_REPORT recv_rep; + +#define SETTINGS_BASE 0x00 +#define PROFILE_BASE 0xff +#define PROFILE_LEN 0x13 + +#define MBED + +typedef void (*fn)(void); + +enum cli_actions { + SET = 0x01, + GET = 0x02, + LOAD_DATA = 0x03, + GET_DATA = 0x04, + CLEAR = 0x05, + INIT = 0x06 +}; + +enum cli_replies { + retval = 0x01, + message = 0x02 +}; -PinDetect btn_l(P1_25); -PinDetect btn_m(P1_19); -PinDetect btn_r(P0_20); -PinDetect btn_z(P0_2); -PinDetect btn_hr(P1_26); +enum buttons { + BUTTON_LEFT = 0x00, //explisitly showing we start at zero + BUTTON_MIDDLE, + BUTTON_RIGHT, + BUTTON_FORWORD, + BUTTON_BACK, + BUTTON_Z, + BUTTON_HIGH_RES, +}; +enum settings { + CPI_X = 0x00, //explisitly showing we start at zero + CPI_Y, + CPI_X_MULITIPLYER, + CPI_Y_MULITIPLYER, + CPI_MAX, // Not currently used. + CPI_MIN, // Not currently used. + CPI_STEP, // Not currently used. + CPI_Z, + CPI_H, + CPI_HR_X, + CPI_HR_Y, + + BTN_A, + BTN_B, + BTN_C, + BTN_D, + BTN_E, + BTN_F, + BTN_G, + + LED_ACTION, // Not currently used + + VID, + PID, + RELEASE, + + PROFILE_DEFAULT, + PROFILE_CURRENT, + + + + ADNS_CRC, + ADNS_ID, + ADNS_FW_LEN, + ADNS_FW_OFFSET, +}; + -DigitalIn btn_program(P0_4); + + +#ifdef MBED +DigitalIn run_mode(p36); + +DigitalIn motion_in(p14); + +DigitalOut activity(p35); + +InterruptIn debug(p29); + +InterruptIn btn_a(p21); +InterruptIn btn_b(p22); +InterruptIn btn_c(p23); +InterruptIn btn_d(p24); +InterruptIn btn_e(p25); +InterruptIn btn_f(p26); +InterruptIn btn_g(p27); -adns9500::ADNS9500 *sensor; +InterruptIn prfl_a(p20); +InterruptIn prfl_b(p19); +InterruptIn prfl_c(p18); +InterruptIn prfl_d(p17); +InterruptIn prfl_e(p16); +#elif +DigitalIn run_mode(P1_29); + +DigitalIn motion_in(P0_22); + +DigitalOut activity(P1_28); + +InterruptIn btn_a(P0_18); +InterruptIn btn_b(P0_16); +InterruptIn btn_c(P0_17); +InterruptIn btn_d(P0_23); +InterruptIn btn_e(P1_15); +InterruptIn btn_f(P1_??); +InterruptIn btn_g(P1_??); + +InterruptIn prfl_a(P0_4); +InterruptIn prfl_b(P0_5); +InterruptIn prfl_c(P0_21); +InterruptIn prfl_d(P1_23); +InterruptIn prfl_e(P1_24); +#endif + +// We are global for the callbacks USBMouse *mouse; -bool motion_triggered = false; -bool z_axis_active = false; -bool high_rez_active = false; +bool motion_triggered = true; +bool z_axis_active = false; +bool high_rez_active = false; +bool profile_load = true; // Always inishally load the profile even if it might be the same. +bool set_res_hr = false; +bool set_res_z = false; +bool set_res_default = false; +//uint32_t rest_counter; -uint16_t s[9] = { - 1080, // CPI_DEFAULT +uint16_t s[28] = { + 540, // CPI_X + 540, // CPI_Y + 40, // CPI_X_MULITIPLYER + 40, // CPI_Y_MULITIPLYER 5040, // CPI_MAX 0, // CPI_MIN 90, // CPI_STEP - 90, // CPI_Z_DEFAULT - 180, // CPI_HR_DEFULT - 0x192f, // VID - 0x0000, // PID - 0, // LED_SHOW + 0, // CPI_Z + 0, // CPI_H + 360, // CPI_HR_X + 360, // CPI_HR_Y + BUTTON_LEFT, + BUTTON_MIDDLE, + BUTTON_RIGHT, + BUTTON_Z, + BUTTON_HIGH_RES, + BUTTON_FORWORD, + BUTTON_BACK, + 0x00, // LED_ACTION + 0x192f, // VID (No default, must be set) + 0x0000, // PID (No default, must be set) + 0x00, // PROFILE_DEFAULT + 0x00, // PROFILE_CURRENT + 0x0000, // RELEASE + 0xffff, // ADNS_CRC (No default, must be set) + 0xffff, // ADNS_ID (No default, must be set) + 0xffff, // ADNS_FW_LEN (No default, must be set) + 0xea60 // ADNS_FW_OFFSET }; -uint16_t a[3]; + -void track(); -void program(); +void track( Ser25LCxxx *eeprom ); +void program( Ser25LCxxx *eeprom ); void motionCallback( void ); @@ -124,12 +215,25 @@ void btn_r_press( void ); void btn_r_release( void ); -void set_setting( Ser25LCxxx *eeprom, uint16_t attrib, uint16_t val ); -uint16_t get_setting( Ser25LCxxx *eeprom, uint16_t attrib); -void clear_setting( Ser25LCxxx *eeprom, uint16_t attrib); +void btn_f_press( void ); +void btn_f_release( void ); + +void btn_b_press( void ); +void btn_b_release( void ); -void set_adns_firmware( Ser25LCxxx *eeprom, uint16_t offset, uint16_t len, uint8_t* val ); -uint8_t* get_adns_firmware( Ser25LCxxx *eeprom, uint16_t offset, uint16_t len ); +void prfl_a_set( void ); +void prfl_b_set( void ); +void prfl_c_set( void ); +void prfl_d_set( void ); +void prfl_e_set( void ); -void set_adns_meta( Ser25LCxxx *eeprom, uint16_t attrib, uint16_t val ); -uint16_t get_adns_meta( Ser25LCxxx *eeprom, uint16_t attrib ); \ No newline at end of file +void prfl_stub( void ); +void debug_out(void); + +int set_setting( Ser25LCxxx *eeprom, uint16_t attrib, uint16_t val, uint16_t base_address ); +uint16_t get_setting( Ser25LCxxx *eeprom, uint16_t attrib, uint16_t base_address ); +void clear_setting( Ser25LCxxx *eeprom, uint16_t attrib, uint16_t base_address ); + +void load_data( Ser25LCxxx *eeprom, uint16_t base, uint16_t len, const uint8_t* data ); + +uint8_t* get_data( Ser25LCxxx *eeprom, uint16_t base, uint16_t len ); \ No newline at end of file